From a896172d192d4b2ba73877ba164688dcbdb546c9 Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Wed, 28 May 2014 11:07:06 +0000 Subject: [PATCH] re PR tree-optimization/61335 (wrong code with -O2 -fbounds-check) 2014-05-28 Richard Biener PR tree-optimization/61335 * tree-vrp.c (vrp_visit_phi_node): If the compare of old and new range fails, drop to varying. * gfortran.dg/pr61335.f90: New testcase. From-SVN: r211012 --- gcc/ChangeLog | 6 ++ gcc/testsuite/ChangeLog | 5 ++ gcc/testsuite/gfortran.dg/pr61335.f90 | 117 ++++++++++++++++++++++++++ gcc/tree-vrp.c | 6 ++ 4 files changed, 134 insertions(+) create mode 100644 gcc/testsuite/gfortran.dg/pr61335.f90 diff --git a/gcc/ChangeLog b/gcc/ChangeLog index b0f47ae7642..518f5a3aa00 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,9 @@ +2014-05-28 Richard Biener + + PR tree-optimization/61335 + * tree-vrp.c (vrp_visit_phi_node): If the compare of old and + new range fails, drop to varying. + 2014-05-28 Tom de Vries * lra-int.h (struct lra_reg): Add field actual_call_used_reg_set. diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 572ba9d4753..1546ec21502 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2014-05-28 Richard Biener + + PR tree-optimization/61335 + * gfortran.dg/pr61335.f90: New testcase. + 2014-05-27 Eric Botcazou * gnat.dg/aliasing1.adb (dg-final): Robustify pattern matching. diff --git a/gcc/testsuite/gfortran.dg/pr61335.f90 b/gcc/testsuite/gfortran.dg/pr61335.f90 new file mode 100644 index 00000000000..7961f270515 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/pr61335.f90 @@ -0,0 +1,117 @@ +! { dg-do run } +! { dg-additional-options "-fbounds-check" } +MODULE cp_units + + INTEGER, PARAMETER :: default_string_length=80, dp=KIND(0.0D0) + + LOGICAL, PRIVATE, PARAMETER :: debug_this_module=.TRUE. + CHARACTER(len=*), PARAMETER, PRIVATE :: moduleN = 'cp_units' + INTEGER, SAVE, PRIVATE :: last_unit_id=0, last_unit_set_id=0 + + INTEGER, PARAMETER, PUBLIC :: cp_unit_max_kinds=8, cp_unit_basic_desc_length=15,& + cp_unit_desc_length=cp_unit_max_kinds*cp_unit_basic_desc_length, cp_ukind_max=9 + +CONTAINS + + FUNCTION cp_to_string(i) RESULT(res) + INTEGER, INTENT(in) :: i + CHARACTER(len=6) :: res + + INTEGER :: iostat + REAL(KIND=dp) :: tmp_r + + IF (i>999999 .OR. i<-99999) THEN + tmp_r=i + WRITE (res,fmt='(es6.1)',iostat=iostat) tmp_r + ELSE + WRITE (res,fmt='(i6)',iostat=iostat) i + END IF + IF (iostat/=0) THEN + STOP 7 + END IF + END FUNCTION cp_to_string + + SUBROUTINE cp_unit_create(string) + CHARACTER(len=*), INTENT(in) :: string + + CHARACTER(len=*), PARAMETER :: routineN = 'cp_unit_create', & + routineP = moduleN//':'//routineN + + CHARACTER(default_string_length) :: desc + CHARACTER(LEN=40) :: formatstr + INTEGER :: i_high, i_low, i_unit, & + len_string, next_power + INTEGER, DIMENSION(cp_unit_max_kinds) :: kind_id, power, unit_id + LOGICAL :: failure + + failure=.FALSE. + unit_id=cp_units_none + kind_id=cp_ukind_none + power=0 + i_low=1 + i_high=1 + len_string=LEN(string) + i_unit=0 + next_power=1 + DO WHILE(i_lowlen_string) EXIT + i_unit=i_unit+1 + IF (i_unit>cp_unit_max_kinds) THEN + EXIT + END IF + power(i_unit)=next_power + ! parse op + i_low=i_high + DO WHILE(i_low<=len_string) + IF (string(i_low:i_low)/=' ') EXIT + i_low=i_low+1 + END DO + i_high=i_low + DO WHILE(i_high<=len_string) + IF ( string(i_high:i_high)==' '.OR.string(i_high:i_high)=='^'.OR.& + string(i_high:i_high)=='*'.OR.string(i_high:i_high)=='/') EXIT + i_high=i_high+1 + END DO + IF (i_highlen_string) EXIT + + IF (i_high<=len_string) THEN + IF (string(i_low:i_high)=='^') THEN + i_low=i_high+1 + DO WHILE(i_low<=len_string) + IF (string(i_low:i_low)/=' ') EXIT + i_low=i_low+1 + END DO + i_high=i_low + DO WHILE(i_high<=len_string) + SELECT CASE(string(i_high:i_high)) + CASE('+','-','0','1','2','3','4','5','6','7','8','9') + i_high=i_high+1 + CASE default + EXIT + END SELECT + END DO + IF (i_high<=i_low.OR.i_low>len_string) THEN + write(6,*) "BUG : XXX"//string//"XXX integer expected" + STOP 1 + EXIT + END IF + END IF + ENDIF + END DO + END SUBROUTINE cp_unit_create + +END MODULE cp_units + +USE cp_units +CALL cp_unit_create("fs^-1") +END diff --git a/gcc/tree-vrp.c b/gcc/tree-vrp.c index afabc4cfbb8..67c70cb1132 100644 --- a/gcc/tree-vrp.c +++ b/gcc/tree-vrp.c @@ -8323,8 +8323,14 @@ vrp_visit_phi_node (gimple phi) && edges == old_edges && lhs_vr->type != VR_UNDEFINED) { + /* Compare old and new ranges, fall back to varying if the + values are not comparable. */ int cmp_min = compare_values (lhs_vr->min, vr_result.min); + if (cmp_min == -2) + goto varying; int cmp_max = compare_values (lhs_vr->max, vr_result.max); + if (cmp_max == -2) + goto varying; /* For non VR_RANGE or for pointers fall back to varying if the range changed. */