aboutsummaryrefslogtreecommitdiff
path: root/gcc/simplify-rtx.c
diff options
context:
space:
mode:
authorJeff Law <law@redhat.com>2020-03-23 17:55:20 -0600
committerJeff Law <law@redhat.com>2020-03-23 17:59:34 -0600
commit75fb811dfaa29d60a897924b0d1629577b90eee7 (patch)
treed92865643c0d3d33c9b3db1acdbdb35a651729d8 /gcc/simplify-rtx.c
parent1f6c1c82eb5001a844b5ac535f6aba4a3257031f (diff)
downloadgcc-75fb811dfaa29d60a897924b0d1629577b90eee7.zip
gcc-75fb811dfaa29d60a897924b0d1629577b90eee7.tar.gz
gcc-75fb811dfaa29d60a897924b0d1629577b90eee7.tar.bz2
Verify the code used for the optimized comparison is valid for the comparison's mode.
PR rtl-optimization/90275 PR target/94238 PR target/94144 * simplify-rtx.c (comparison_code_valid_for_mode): New function. (simplify_logical_relational_operation): Use it. PR target/94144 PR target/94238 * gcc.c-torture/compile/pr94144.c: New test. * gcc.c-torture/compile/pr94238.c: New test.
Diffstat (limited to 'gcc/simplify-rtx.c')
-rw-r--r--gcc/simplify-rtx.c51
1 files changed, 51 insertions, 0 deletions
diff --git a/gcc/simplify-rtx.c b/gcc/simplify-rtx.c
index dd3d851..28c2dc6 100644
--- a/gcc/simplify-rtx.c
+++ b/gcc/simplify-rtx.c
@@ -2215,6 +2215,53 @@ mask_to_comparison (int mask)
}
}
+/* Return true if CODE is valid for comparisons of mode MODE, false
+ otherwise.
+
+ It is always safe to return false, even if the code was valid for the
+ given mode as that will merely suppress optimizations. */
+
+static bool
+comparison_code_valid_for_mode (enum rtx_code code, enum machine_mode mode)
+{
+ switch (code)
+ {
+ /* These are valid for integral, floating and vector modes. */
+ case NE:
+ case EQ:
+ case GE:
+ case GT:
+ case LE:
+ case LT:
+ return (INTEGRAL_MODE_P (mode)
+ || FLOAT_MODE_P (mode)
+ || VECTOR_MODE_P (mode));
+
+ /* These are valid for floating point modes. */
+ case LTGT:
+ case UNORDERED:
+ case ORDERED:
+ case UNEQ:
+ case UNGE:
+ case UNGT:
+ case UNLE:
+ case UNLT:
+ return FLOAT_MODE_P (mode);
+
+ /* These are filtered out in simplify_logical_operation, but
+ we check for them too as a matter of safety. They are valid
+ for integral and vector modes. */
+ case GEU:
+ case GTU:
+ case LEU:
+ case LTU:
+ return INTEGRAL_MODE_P (mode) || VECTOR_MODE_P (mode);
+
+ default:
+ gcc_unreachable ();
+ }
+}
+
/* Simplify a logical operation CODE with result mode MODE, operating on OP0
and OP1, which should be both relational operations. Return 0 if no such
simplification is possible. */
@@ -2252,6 +2299,10 @@ simplify_logical_relational_operation (enum rtx_code code, machine_mode mode,
code = mask_to_comparison (mask);
+ /* Many comparison codes are only valid for certain mode classes. */
+ if (!comparison_code_valid_for_mode (code, mode))
+ return 0;
+
op0 = XEXP (op1, 0);
op1 = XEXP (op1, 1);