mirror of
https://forge.sourceware.org/marek/gcc.git
synced 2026-02-22 12:00:11 -05:00
middle-end/104402 - split out _Complex compares from COND_EXPRs
This makes sure we always have a _Complex compare split to a
different stmt for the compare operand in a COND_EXPR on GIMPLE.
Complex lowering doesn't handle this and the change is something
we want for all kind of compares at some point.
2022-02-07 Richard Biener <rguenther@suse.de>
PR middle-end/104402
* gimple-expr.c (is_gimple_condexpr): _Complex typed
compares are not valid.
* tree-cfg.c (verify_gimple_assign_ternary): For COND_EXPR
check is_gimple_condexpr.
* gcc.dg/torture/pr104402.c: New testcase.
(cherry picked from commit 70430001b7)
This commit is contained in:
@@ -612,12 +612,16 @@ is_gimple_lvalue (tree t)
|
||||
/* Helper for is_gimple_condexpr and is_gimple_condexpr_for_cond. */
|
||||
|
||||
static bool
|
||||
is_gimple_condexpr_1 (tree t, bool allow_traps)
|
||||
is_gimple_condexpr_1 (tree t, bool allow_traps, bool allow_cplx)
|
||||
{
|
||||
return (is_gimple_val (t) || (COMPARISON_CLASS_P (t)
|
||||
&& (allow_traps || !tree_could_throw_p (t))
|
||||
&& is_gimple_val (TREE_OPERAND (t, 0))
|
||||
&& is_gimple_val (TREE_OPERAND (t, 1))));
|
||||
tree op0;
|
||||
return (is_gimple_val (t)
|
||||
|| (COMPARISON_CLASS_P (t)
|
||||
&& (allow_traps || !tree_could_throw_p (t))
|
||||
&& ((op0 = TREE_OPERAND (t, 0)), true)
|
||||
&& (allow_cplx || TREE_CODE (TREE_TYPE (op0)) != COMPLEX_TYPE)
|
||||
&& is_gimple_val (op0)
|
||||
&& is_gimple_val (TREE_OPERAND (t, 1))));
|
||||
}
|
||||
|
||||
/* Return true if T is a GIMPLE condition. */
|
||||
@@ -625,7 +629,9 @@ is_gimple_condexpr_1 (tree t, bool allow_traps)
|
||||
bool
|
||||
is_gimple_condexpr (tree t)
|
||||
{
|
||||
return is_gimple_condexpr_1 (t, true);
|
||||
/* Always split out _Complex type compares since complex lowering
|
||||
doesn't handle this case. */
|
||||
return is_gimple_condexpr_1 (t, true, false);
|
||||
}
|
||||
|
||||
/* Like is_gimple_condexpr, but does not allow T to trap. */
|
||||
@@ -633,7 +639,7 @@ is_gimple_condexpr (tree t)
|
||||
bool
|
||||
is_gimple_condexpr_for_cond (tree t)
|
||||
{
|
||||
return is_gimple_condexpr_1 (t, false);
|
||||
return is_gimple_condexpr_1 (t, false, true);
|
||||
}
|
||||
|
||||
/* Return true if T is a gimple address. */
|
||||
|
||||
8
gcc/testsuite/gcc.dg/torture/pr104402.c
Normal file
8
gcc/testsuite/gcc.dg/torture/pr104402.c
Normal file
@@ -0,0 +1,8 @@
|
||||
/* { dg-do compile } */
|
||||
|
||||
_Complex int a;
|
||||
char b;
|
||||
void c() {
|
||||
if (b != 2 + (long)(a != 0 ^ 0))
|
||||
__builtin_abort();
|
||||
}
|
||||
@@ -4243,10 +4243,11 @@ verify_gimple_assign_ternary (gassign *stmt)
|
||||
/* Fallthrough. */
|
||||
case COND_EXPR:
|
||||
if (!is_gimple_val (rhs1)
|
||||
&& verify_gimple_comparison (TREE_TYPE (rhs1),
|
||||
TREE_OPERAND (rhs1, 0),
|
||||
TREE_OPERAND (rhs1, 1),
|
||||
TREE_CODE (rhs1)))
|
||||
&& (!is_gimple_condexpr (rhs1)
|
||||
|| verify_gimple_comparison (TREE_TYPE (rhs1),
|
||||
TREE_OPERAND (rhs1, 0),
|
||||
TREE_OPERAND (rhs1, 1),
|
||||
TREE_CODE (rhs1))))
|
||||
return true;
|
||||
if (!useless_type_conversion_p (lhs_type, rhs2_type)
|
||||
|| !useless_type_conversion_p (lhs_type, rhs3_type))
|
||||
|
||||
Reference in New Issue
Block a user