diff options
author | Tobias Burnus <burnus@net-b.de> | 2018-10-12 20:18:13 +0200 |
---|---|---|
committer | Tobias Burnus <burnus@gcc.gnu.org> | 2018-10-12 20:18:13 +0200 |
commit | 47b92d22d3aea04ce6a936c768953dd0406f41c2 (patch) | |
tree | 3aa254da8f50163132eac6447ce9497870ab06cb | |
parent | b4439561c4019cf3bc4c59cc6260d7464917f1e5 (diff) | |
download | gcc-47b92d22d3aea04ce6a936c768953dd0406f41c2.zip gcc-47b92d22d3aea04ce6a936c768953dd0406f41c2.tar.gz gcc-47b92d22d3aea04ce6a936c768953dd0406f41c2.tar.bz2 |
Fix off-by-one issue with inline matmul
PR fortran/87597
* expr.c (gfc_simplify_expr): Avoid simplifying
the 'array' argument to lbound/ubound/lcobound/
ucobound.
PR fortran/87597
* gfortran.dg/inline_matmul_24.f90: New.
From-SVN: r265126
-rw-r--r-- | gcc/fortran/ChangeLog | 7 | ||||
-rw-r--r-- | gcc/fortran/expr.c | 15 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/testsuite/gfortran.dg/inline_matmul_24.f90 | 42 |
4 files changed, 68 insertions, 1 deletions
diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog index 2181363..4ee065a 100644 --- a/gcc/fortran/ChangeLog +++ b/gcc/fortran/ChangeLog @@ -1,3 +1,10 @@ +2018-10-12 Tobias Burnus <burnus@net-b.de> + + PR fortran/87597 + * expr.c (gfc_simplify_expr): Avoid simplifying + the 'array' argument to lbound/ubound/lcobound/ + ucobound. + 2018-10-12 Tobias Burnus <burnus@net-b.de> PR fortran/58787 diff --git a/gcc/fortran/expr.c b/gcc/fortran/expr.c index 1cfda5f..ca6f95d 100644 --- a/gcc/fortran/expr.c +++ b/gcc/fortran/expr.c @@ -1937,7 +1937,20 @@ gfc_simplify_expr (gfc_expr *p, int type) break; case EXPR_FUNCTION: - for (ap = p->value.function.actual; ap; ap = ap->next) + // For array-bound functions, we don't need to optimize + // the 'array' argument. In particular, if the argument + // is a PARAMETER, simplifying might convert an EXPR_VARIABLE + // into an EXPR_ARRAY; the latter has lbound = 1, the former + // can have any lbound. + ap = p->value.function.actual; + if (p->value.function.isym && + (p->value.function.isym->id == GFC_ISYM_LBOUND + || p->value.function.isym->id == GFC_ISYM_UBOUND + || p->value.function.isym->id == GFC_ISYM_LCOBOUND + || p->value.function.isym->id == GFC_ISYM_UCOBOUND)) + ap = ap->next; + + for ( ; ap; ap = ap->next) if (!gfc_simplify_expr (ap->expr, type)) return false; diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 4991c2e..3604fe6 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2018-10-12 Tobias Burnus <burnus@net-b.de> + + PR fortran/87597 + * gfortran.dg/inline_matmul_24.f90: New. + 2018-10-12 Tobias Burnus <burnus@net-b.de> PR fortran/58787 diff --git a/gcc/testsuite/gfortran.dg/inline_matmul_24.f90 b/gcc/testsuite/gfortran.dg/inline_matmul_24.f90 new file mode 100644 index 0000000..067f6da --- /dev/null +++ b/gcc/testsuite/gfortran.dg/inline_matmul_24.f90 @@ -0,0 +1,42 @@ +! { dg-do run } +! { dg-options "-ffrontend-optimize -fdump-tree-original" } +! +! PR fortran/87597 +! +! Contributed by gallmeister +! +! Before, for the inlined matmul, +! gamma5 was converted to an EXPR_ARRAY with lbound = 1 +! instead of the lbound = 0 as declared; leading to +! an off-by-one problem. +! +program testMATMUL + implicit none + complex, dimension(0:3,0:3), parameter :: gamma5 = reshape((/ 0., 0., 1., 0., & + 0., 0., 0., 1., & + 1., 0., 0., 0., & + 0., 1., 0., 0. /),(/4,4/)) + complex, dimension(0:3,0:3) :: A, B, D + integer :: i + + A = 0.0 + do i=0,3 + A(i,i) = i*1.0 + end do + + B = cmplx(7,-9) + B = matmul(A,gamma5) + + D = reshape([0, 0, 2, 0, & + 0, 0, 0, 3, & + 0, 0, 0, 0, & + 0, 1, 0, 0], [4, 4]) + write(*,*) B(0,:) + write(*,*) B(1,:) + write(*,*) B(2,:) + write(*,*) B(3,:) + if (any(B /= D)) then + call abort() + end if +end program testMATMUL +! { dg-final { scan-tree-dump-times "gamma5\[__var_1_do \\* 4 \\+ __var_2_do\]" 1 "optimized" } } |