http://gcc.gnu.org/bugzilla/show_bug.cgi?id=47844
--- Comment #8 from Dominique d'Humieres <dominiq at lps dot ens.fr> 2011-10-05 21:39:31 UTC --- > We could fix this in 4.7 by adding a sm field to array descriptors. I don't see why. I have looked at the dump.original of the following code: integer, target :: tgt(9) = [1,2,3,4,5,6,7,8,9] integer, pointer :: p(:) integer :: var(3) p => tgt(ubound(tgt,1)-4:lbound(tgt,1):-2) var = p print *, var ! prints 5 3 1 var = f(tgt) ! should assign 5 3 1 print *, var ! but prints 5 6 7 if(any(var/=[5,3,1])) call abort() contains function f(x) result(r) integer, target :: x(:) integer, pointer :: r(:) r => x(ubound(x,1)-4:lbound(x,1):-2) print *, r ! prints 5 3 1 end function f end The first assignment (var = p) is p.dtype = 265; p.dim[0].lbound = 1; p.dim[0].ubound = 3; p.dim[0].stride = -2; p.data = (void *) &tgt[4]; p.offset = 2; { integer(kind=8) D.1793; integer(kind=8) D.1792; integer(kind=8) D.1791; integer(kind=8) D.1790; integer(kind=4)[0:] * D.1789; D.1789 = (integer(kind=4)[0:] *) p.data; D.1790 = p.offset; D.1791 = p.dim[0].lbound; D.1792 = p.dim[0].ubound; D.1793 = D.1791 + -1; { integer(kind=8) D.1795; integer(kind=8) S.7; D.1795 = p.dim[0].stride; S.7 = 1; while (1) { if (S.7 > 3) goto L.1; var[S.7 + -1] = (*D.1789)[(S.7 + D.1793) * D.1795 + D.1790]; S.7 = S.7 + 1; } L.1:; } } while the second one (var = f(tgt)) is: f (&atmp.12, D.1804); { integer(kind=8) S.13; S.13 = 0; while (1) { if (S.13 > 2) goto L.2; var[S.13] = (*(integer(kind=4)[3] * restrict) atmp.12.data)[S.13]; S.13 = S.13 + 1; } L.2:; } As far I understand the dump, atmp.12 is set with the same values as p (through an awfully complicated process), but atmp.12.dim[0].stride is not used in the assignment.