Message ID | 20180316201722.GI8577@tucnak |
---|---|
State | New |
Headers | show |
Series | Fix postreload constant merging (PR target/84899) | expand |
On 03/16/2018 02:17 PM, Jakub Jelinek wrote: > Hi! > > The following testcase ICEs on powerpc-linux, because we merge > SImode constants 0x7fffffff and 1 into 0x80000000, which is not valid SImode > CONST_INT - -0x80000000 is. Fixed by calling trunc_int_for_mode, and to > avoid UB in the compiler do the addition in unsigned type. > > Bootstrapped/regtested on x86_64-linux and i686-linux and tested on the > testcase with powerpc64-linux cross with -m32, ok for trunk? > > 2018-03-16 Jakub Jelinek <jakub@redhat.com> > > PR target/84899 > * postreload.c (reload_combine_recognize_pattern): Perform > INTVAL addition in unsigned HOST_WIDE_INT type to avoid UB and > truncate_int_for_mode the result for the destination's mode. > > * gcc.dg/pr84899.c: New test. OK. jeff
--- gcc/postreload.c.jj 2018-01-03 10:19:55.572534024 +0100 +++ gcc/postreload.c 2018-03-16 18:19:17.819417570 +0100 @@ -1157,11 +1157,13 @@ reload_combine_recognize_pattern (rtx_in value in PREV, the constant loading instruction. */ validate_change (prev, &SET_DEST (prev_set), index_reg, 1); if (reg_state[regno].offset != const0_rtx) - validate_change (prev, - &SET_SRC (prev_set), - GEN_INT (INTVAL (SET_SRC (prev_set)) - + INTVAL (reg_state[regno].offset)), - 1); + { + HOST_WIDE_INT c + = trunc_int_for_mode (UINTVAL (SET_SRC (prev_set)) + + UINTVAL (reg_state[regno].offset), + GET_MODE (index_reg)); + validate_change (prev, &SET_SRC (prev_set), GEN_INT (c), 1); + } /* Now for every use of REG that we have recorded, replace REG with REG_SUM. */ --- gcc/testsuite/gcc.dg/pr84899.c.jj 2018-03-16 18:22:39.243512333 +0100 +++ gcc/testsuite/gcc.dg/pr84899.c 2018-03-16 18:22:22.353504390 +0100 @@ -0,0 +1,12 @@ +/* PR target/84899 */ +/* { dg-do compile } */ +/* { dg-options "-O -funroll-all-loops -fno-move-loop-invariants" } */ + +void +foo (int x) +{ + int a = 1 / x, b = 0; + + while ((a + b + 1) < x) + b = __INT_MAX__; +}