------- Additional Comments From tobi at gcc dot gnu dot org 2005-03-19 11:51 ------- One further reduction, still the same misbehavior: real vx(1) num=2 do i=1,num call advance(vx) end do contains subroutine advance(bodies) real, dimension(:)::bodies bodies(1) = 1.0 end subroutine advance end gives the following, correct looking, .optimized dump:
;; Function MAIN__ (MAIN__) Analyzing Edge Insertions. MAIN__ () { <unnamed type> ivtmp.13; int4 prephitmp.12; int4 pretmp.11; int4 pretmp.10; struct array1_real4 & pretmp.9; real4[0:] * pretmp.8; int4 D.520; real4[0:] * bodies.0; int4 offset.2; int4 stride.1; int4 ubound.0; int4 D.519; int4 D.518; int4 D.517; int4 D.516; real4[0:] * D.515; int4 iftmp.4; struct array1_real4 & bodies; struct array1_real4 parm.3; logical4 D.499; int4 D.490; real4 vx[1]; int4 i; int4 num; real4[0:] * D.501; <bb 0>: pretmp.8 = (real4[0:] *) &vx[0]; pretmp.9 = (struct array1_real4 &) &parm.3; i = 1; <L0>:; parm.3.dtype = 281; parm.3.dim[0].lbound = 1; parm.3.dim[0].ubound = 1; parm.3.dim[0].stride = 1; parm.3.data = pretmp.8; parm.3.offset = 0; stride.1 = pretmp.9->dim[0].stride; if (stride.1 == 0) goto <L12>; else goto <L10>; <L12>:; stride.1 = 1; prephitmp.12 = -1; goto <bb 3> (<L4>); <L10>:; prephitmp.12 = -stride.1; <L4>:; (*(real4[0:] *) pretmp.9->data)[stride.1 + prephitmp.12] = 1.0e+0; if (i == 2) goto <L7>; else goto <L11>; <L11>:; i = i + 1; goto <bb 1> (<L0>); <L7>:; return; } With -fno-strict-aliasing the testcase doesn't segfault any longer. The differences in the .optimized dump are this: --- pr20538.f90.t67.optimized 2005-03-19 12:46:23.472057734 +0100 +++ pr20538.f90.t67.optimized.no-strict 2005-03-19 12:45:56.000775891 +0100 @@ -4,12 +4,12 @@ Analyzing Edge Insertions. MAIN__ () { - <unnamed type> ivtmp.13; - int4 prephitmp.12; - int4 pretmp.11; + <unnamed type> ivtmp.12; + int4 prephitmp.11; int4 pretmp.10; - struct array1_real4 & pretmp.9; - real4[0:] * pretmp.8; + int4 pretmp.9; + struct array1_real4 & pretmp.8; + real4[0:] * pretmp.7; int4 D.520; real4[0:] * bodies.0; int4 offset.2; @@ -31,8 +31,8 @@ MAIN__ () real4[0:] * D.501; <bb 0>: - pretmp.8 = (real4[0:] *) &vx[0]; - pretmp.9 = (struct array1_real4 &) &parm.3; + pretmp.7 = (real4[0:] *) &vx[0]; + pretmp.8 = (struct array1_real4 &) &parm.3; i = 1; <L0>:; @@ -40,21 +40,21 @@ MAIN__ () parm.3.dim[0].lbound = 1; parm.3.dim[0].ubound = 1; parm.3.dim[0].stride = 1; - parm.3.data = pretmp.8; + parm.3.data = pretmp.7; parm.3.offset = 0; - stride.1 = pretmp.9->dim[0].stride; + stride.1 = pretmp.8->dim[0].stride; if (stride.1 == 0) goto <L12>; else goto <L10>; <L12>:; stride.1 = 1; - prephitmp.12 = -1; + prephitmp.11 = -1; goto <bb 3> (<L4>); <L10>:; - prephitmp.12 = -stride.1; + prephitmp.11 = -stride.1; <L4>:; - (*(real4[0:] *) pretmp.9->data)[stride.1 + prephitmp.12] = 1.0e+0; + (*(real4[0:] *) pretmp.8->data)[stride.1 + prephitmp.11] = 1.0e+0; if (i == 2) goto <L7>; else goto <L11>; <L11>:; i.e. only a few temporaries got renamed in all places where they're used. -- http://gcc.gnu.org/bugzilla/show_bug.cgi?id=20538