This makes sure to not generate a shift of pointer types in
simplification of X < (cast) (1 << Y).

Bootstrap and regtest pending on x86_64-unknown-linux-gnu.

2021-08-11  Richard Biener  <rguent...@suse.de>

        PR middle-end/101858
        * fold-const.c (fold_binary_loc): Guard simplification
        of  X < (cast) (1 << Y) to integer types.

        * gcc.dg/pr101858.c: New testcase.
---
 gcc/fold-const.c                | 2 ++
 gcc/testsuite/gcc.dg/pr101858.c | 9 +++++++++
 2 files changed, 11 insertions(+)
 create mode 100644 gcc/testsuite/gcc.dg/pr101858.c

diff --git a/gcc/fold-const.c b/gcc/fold-const.c
index 0f701287ba1..3917e97dfb0 100644
--- a/gcc/fold-const.c
+++ b/gcc/fold-const.c
@@ -12497,6 +12497,8 @@ fold_binary_loc (location_t loc, enum tree_code code, 
tree type,
         we can't optimize this.  E.g. (unsigned long long) (1 << Y) for Y
         31 might be 0xffffffff80000000.  */
       if ((code == LT_EXPR || code == GE_EXPR)
+         && (INTEGRAL_TYPE_P (TREE_TYPE (arg0))
+             || VECTOR_INTEGER_TYPE_P (TREE_TYPE (arg0)))
          && TYPE_UNSIGNED (TREE_TYPE (arg0))
          && CONVERT_EXPR_P (arg1)
          && TREE_CODE (TREE_OPERAND (arg1, 0)) == LSHIFT_EXPR
diff --git a/gcc/testsuite/gcc.dg/pr101858.c b/gcc/testsuite/gcc.dg/pr101858.c
new file mode 100644
index 00000000000..61fcca60982
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr101858.c
@@ -0,0 +1,9 @@
+/* { dg-do compile } */
+/* { dg-options "-w" } */
+
+int foo(int a)
+{
+  if (a < (int*)((__INTPTR_TYPE__)1 << a))
+    a = 0;
+  return a;
+}
-- 
2.31.1

Reply via email to