From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 48) id B0983386F82B; Mon, 20 Apr 2020 14:36:14 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org B0983386F82B DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1587393374; bh=lerQXYK2wFX8LOEFXEZrHvA1gPtWqexl1mtQjZtm/pU=; h=From:To:Subject:Date:In-Reply-To:References:From; b=GlUe3PuWmBd6b6697oc6rLt+54vNkCKjFiq7j0zoa5a6dTqVRRxfiXqUk67z0xxoz NtPiDMqi/yLUImK9seO9qKCVkUgXQSxS+Jaq/O6z8gK/V/2Gg5cHQJ4RnWtqMgtmkw WVhxRdGbp7E3aKeIs+ccl4vTQ4fiYrTFNTiA7bVU= From: "tkoenig at gcc dot gnu.org" To: gcc-bugs@gcc.gnu.org Subject: [Bug fortran/93956] Wrong array creation with p => array_dt(1:n)%component Date: Mon, 20 Apr 2020 14:36:14 +0000 X-Bugzilla-Reason: CC X-Bugzilla-Type: changed X-Bugzilla-Watch-Reason: None X-Bugzilla-Product: gcc X-Bugzilla-Component: fortran X-Bugzilla-Version: 9.1.1 X-Bugzilla-Keywords: wrong-code X-Bugzilla-Severity: normal X-Bugzilla-Who: tkoenig at gcc dot gnu.org X-Bugzilla-Status: NEW X-Bugzilla-Resolution: X-Bugzilla-Priority: P3 X-Bugzilla-Assigned-To: unassigned at gcc dot gnu.org X-Bugzilla-Target-Milestone: --- X-Bugzilla-Flags: X-Bugzilla-Changed-Fields: Message-ID: In-Reply-To: References: Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable X-Bugzilla-URL: http://gcc.gnu.org/bugzilla/ Auto-Submitted: auto-generated MIME-Version: 1.0 X-BeenThere: gcc-bugs@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-bugs mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 20 Apr 2020 14:36:14 -0000 https://gcc.gnu.org/bugzilla/show_bug.cgi?id=3D93956 --- Comment #4 from Thomas Koenig --- Taking the slightly modified test case program array_temps implicit none type :: tt integer :: u =3D 1 integer :: v =3D 2 end type tt type(tt), dimension(:), pointer :: r integer :: n integer, dimension(:), pointer :: p n =3D 10 allocate(r(1:n)) p =3D> get(r) call foo(p, n) print *,sum(p) deallocate(r) contains subroutine foo(a, n) integer, dimension(:), intent(in) :: a integer, intent(in) :: n print *, sum(a(1:n)), n end subroutine foo function get(x) result(q) type(tt), dimension(:), target, intent(in) :: x integer, dimension(:), pointer :: q q =3D> x(:)%v end function get end program array_temps and looking at -fdump-tree-original shows something strange. get looks good: { integer(kind=3D8) D.3946; integer(kind=3D8) D.3947; D.3946 =3D ubound.0; __result->span =3D 8; __result->dtype =3D {.elem_len=3D4, .rank=3D1, .type=3D1}; D.3947 =3D stride.1; __result->dim[0].lbound =3D 1; __result->dim[0].ubound =3D D.3946; __result->dim[0].stride =3D NON_LVALUE_EXPR ; __result->data =3D (void *) &(*x.0)[0].v; __result->offset =3D -NON_LVALUE_EXPR ; } so the result for span is set. The call to get and foo does not look to bad, either: { struct array01_integer(kind=3D4) ptrtemp.15; struct array01_tt * D.4002; struct tt[0:] * ifm.16; integer(kind=3D8) D.4004; integer(kind=3D8) D.4005; ptrtemp.15.span =3D 4; D.4002 =3D &r; ifm.16 =3D (struct tt[0:] *) D.4002->data; D.4004 =3D (D.4002->dim[0].ubound - D.4002->dim[0].lbound) + 1; D.4005 =3D -NON_LVALUE_EXPR dim[0].stride>; get (&ptrtemp.15, D.4002); p =3D ptrtemp.15; } foo (&p, &n); But it seems that foo does not use the span at all. OK, so what about the test case program array_temps implicit none type :: tt integer :: u =3D 1 integer :: v =3D 2 end type tt type(tt), dimension(:), pointer :: r integer :: n integer, dimension(:), pointer :: p n =3D 10 allocate(r(1:n)) p =3D> r%v call foo(p, n) print *,sum(p) deallocate(r) contains subroutine foo(a, n) integer, dimension(:), intent(in) :: a integer, intent(in) :: n print *, sum(a(1:n)), n end subroutine foo end program array_temps ? There, we actually convert the argument on call to foo: p =3D r; p.data =3D (void *) &(*(struct tt[0:] *) r.data)[0].v; p.span =3D r.span; p.dim[0].ubound =3D p.dim[0].ubound + (1 - p.dim[0].lbound); p.offset =3D p.offset - (1 - p.dim[0].lbound) * p.dim[0].stride; p.dim[0].lbound =3D 1; { integer(kind=3D4)[0:] * D.3975; integer(kind=3D8) D.3976; integer(kind=3D8) D.3977; integer(kind=3D8) D.3978; integer(kind=3D8) D.3979; struct array01_integer(kind=3D4) atmp.11; logical(kind=3D4) D.3987; integer(kind=3D8) D.3988; void * restrict D.3989; void * restrict D.3990; integer(kind=3D8) D.3991; integer(kind=3D4)[0:] * D.3995; integer(kind=3D8) D.3996; integer(kind=3D8) D.3997; integer(kind=3D8) D.3998; integer(kind=3D8) D.3999; D.3975 =3D (integer(kind=3D4)[0:] *) p.data; D.3976 =3D p.offset; D.3977 =3D p.dim[0].lbound; D.3978 =3D p.dim[0].ubound; D.3979 =3D D.3978 - D.3977; typedef integer(kind=3D4) [0:]; atmp.11.dtype =3D {.elem_len=3D4, .rank=3D1, .type=3D1}; atmp.11.dim[0].stride =3D 1; atmp.11.dim[0].lbound =3D 0; atmp.11.dim[0].ubound =3D D.3979; D.3987 =3D D.3979 < 0; D.3988 =3D D.3979 + 1; atmp.11.span =3D 4; D.3989 =3D (void * restrict) __builtin_malloc (D.3987 ? 1 : MAX_EXPR <(unsigned long) (D.3988 * 4), 1>); D.3990 =3D D.3989; atmp.11.data =3D D.3990; atmp.11.offset =3D 0; D.3991 =3D NON_LVALUE_EXPR ; { integer(kind=3D8) S.12; integer(kind=3D8) D.3993; D.3993 =3D p.dim[0].stride; S.12 =3D 0; while (1) { if (S.12 > D.3979) goto L.3; (*(integer(kind=3D4)[0:] * restrict) atmp.11.data)[S.12] =3D *((integer(kind=3D4) *) D.3975 + (sizetype) (((S.12 + D.3991) * D.3993 + D.= 3976) * p.span)); S.12 =3D S.12 + 1; } L.3:; } foo (&atmp.11, &n); __builtin_free ((void *) atmp.11.data); This is not ideal from a performance perspective, but at least it generated correct code. So, it appears that somewhere, that conversion goes missing (and it would also be enough just to convert the descriptor, no real need to copy the data).=