mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-03-23 00:41:25 +08:00
ifcvt.c (noce_get_condition): Make certain that the condition is valid at JUMP.
* ifcvt.c (noce_get_condition): Make certain that the condition is valid at JUMP. From-SVN: r55560
This commit is contained in:
parent
c1740ae3c1
commit
30484ccf41
@ -1,3 +1,9 @@
|
||||
2002-07-18 Richard Henderson <rth@redhat.com>
|
||||
|
||||
PR optimization/7147
|
||||
* ifcvt.c (noce_get_condition): Make certain that the condition
|
||||
is valid at JUMP.
|
||||
|
||||
Thu Jul 18 13:44:51 2002 J"orn Rennecke <joern.rennecke@superh.com>
|
||||
|
||||
* sh.c (barrier_align, push): Shut up compiler warnings.
|
||||
@ -63,7 +69,7 @@ Wed Jul 17 19:23:32 2002 J"orn Rennecke <joern.rennecke@superh.com>
|
||||
suppress addition when either ct or cf are zero.
|
||||
|
||||
2002-06-17 Eric Botcazou <ebotcazou@multimania.com>
|
||||
Glen Nakamura <glen@imodulo.com>
|
||||
Glen Nakamura <glen@imodulo.com>
|
||||
|
||||
PR optimization/6713
|
||||
* loop.c (loop_givs_rescan): Explicitly delete the insn that
|
||||
|
68
gcc/ifcvt.c
68
gcc/ifcvt.c
@ -1496,45 +1496,73 @@ noce_try_abs (if_info)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Look for the condition for the jump first. We'd prefer to avoid
|
||||
get_condition if we can -- it tries to look back for the contents
|
||||
of an original compare. On targets that use normal integers for
|
||||
comparisons, e.g. alpha, this is wasteful. */
|
||||
/* Similar to get_condition, only the resulting condition must be
|
||||
valid at JUMP, instead of at EARLIEST. */
|
||||
|
||||
static rtx
|
||||
noce_get_condition (jump, earliest)
|
||||
rtx jump;
|
||||
rtx *earliest;
|
||||
{
|
||||
rtx cond;
|
||||
rtx set;
|
||||
|
||||
/* If the condition variable is a register and is MODE_INT, accept it.
|
||||
Otherwise, fall back on get_condition. */
|
||||
rtx cond, set, tmp, insn;
|
||||
bool reverse;
|
||||
|
||||
if (! any_condjump_p (jump))
|
||||
return NULL_RTX;
|
||||
|
||||
set = pc_set (jump);
|
||||
|
||||
/* If this branches to JUMP_LABEL when the condition is false,
|
||||
reverse the condition. */
|
||||
reverse = (GET_CODE (XEXP (SET_SRC (set), 2)) == LABEL_REF
|
||||
&& XEXP (XEXP (SET_SRC (set), 2), 0) == JUMP_LABEL (jump));
|
||||
|
||||
/* If the condition variable is a register and is MODE_INT, accept it. */
|
||||
|
||||
cond = XEXP (SET_SRC (set), 0);
|
||||
if (GET_CODE (XEXP (cond, 0)) == REG
|
||||
&& GET_MODE_CLASS (GET_MODE (XEXP (cond, 0))) == MODE_INT)
|
||||
tmp = XEXP (cond, 0);
|
||||
if (REG_P (tmp) && GET_MODE_CLASS (GET_MODE (tmp)) == MODE_INT)
|
||||
{
|
||||
*earliest = jump;
|
||||
|
||||
/* If this branches to JUMP_LABEL when the condition is false,
|
||||
reverse the condition. */
|
||||
if (GET_CODE (XEXP (SET_SRC (set), 2)) == LABEL_REF
|
||||
&& XEXP (XEXP (SET_SRC (set), 2), 0) == JUMP_LABEL (jump))
|
||||
if (reverse)
|
||||
cond = gen_rtx_fmt_ee (reverse_condition (GET_CODE (cond)),
|
||||
GET_MODE (cond), XEXP (cond, 0),
|
||||
XEXP (cond, 1));
|
||||
GET_MODE (cond), tmp, XEXP (cond, 1));
|
||||
return cond;
|
||||
}
|
||||
else
|
||||
cond = get_condition (jump, earliest);
|
||||
|
||||
return cond;
|
||||
/* Otherwise, fall back on canonicalize_condition to do the dirty
|
||||
work of manipulating MODE_CC values and COMPARE rtx codes. */
|
||||
|
||||
tmp = canonicalize_condition (jump, cond, reverse, earliest, NULL_RTX);
|
||||
if (!tmp)
|
||||
return NULL_RTX;
|
||||
|
||||
/* We are going to insert code before JUMP, not before EARLIEST.
|
||||
We must therefore be certain that the given condition is valid
|
||||
at JUMP by virtue of not having been modified since. */
|
||||
for (insn = *earliest; insn != jump; insn = NEXT_INSN (insn))
|
||||
if (INSN_P (insn) && modified_in_p (tmp, insn))
|
||||
break;
|
||||
if (insn == jump)
|
||||
return tmp;
|
||||
|
||||
/* The condition was modified. See if we can get a partial result
|
||||
that doesn't follow all the reversals. Perhaps combine can fold
|
||||
them together later. */
|
||||
tmp = XEXP (tmp, 0);
|
||||
if (!REG_P (tmp) || GET_MODE_CLASS (GET_MODE (tmp)) != MODE_INT)
|
||||
return NULL_RTX;
|
||||
tmp = canonicalize_condition (jump, cond, reverse, earliest, tmp);
|
||||
if (!tmp)
|
||||
return NULL_RTX;
|
||||
|
||||
/* For sanity's sake, re-validate the new result. */
|
||||
for (insn = *earliest; insn != jump; insn = NEXT_INSN (insn))
|
||||
if (INSN_P (insn) && modified_in_p (tmp, insn))
|
||||
return NULL_RTX;
|
||||
|
||||
return tmp;
|
||||
}
|
||||
|
||||
/* Return true if OP is ok for if-then-else processing. */
|
||||
|
36
gcc/testsuite/gcc.c-torture/execute/20020716-1.c
Normal file
36
gcc/testsuite/gcc.c-torture/execute/20020716-1.c
Normal file
@ -0,0 +1,36 @@
|
||||
extern void abort (void);
|
||||
extern void exit (int);
|
||||
|
||||
int sub1 (int val)
|
||||
{
|
||||
return val;
|
||||
}
|
||||
|
||||
int testcond (int val)
|
||||
{
|
||||
int flag1;
|
||||
|
||||
{
|
||||
int t1 = val;
|
||||
{
|
||||
int t2 = t1;
|
||||
{
|
||||
flag1 = sub1 (t2) ==0;
|
||||
goto lab1;
|
||||
};
|
||||
}
|
||||
lab1: ;
|
||||
}
|
||||
|
||||
if (flag1 != 0)
|
||||
return 0x4d0000;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main (void)
|
||||
{
|
||||
if (testcond (1))
|
||||
abort ();
|
||||
exit (0);
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user