[clang] 0cab8d2 - Reapply [IR] Mark and/or constant expressions as undesirable

Nikita Popov via cfe-commits cfe-commits at lists.llvm.org
Tue Jul 25 06:31:56 PDT 2023


Author: Nikita Popov
Date: 2023-07-25T15:31:45+02:00
New Revision: 0cab8d20417c0e2ccc1ffc5505e080126f5de8e6

URL: https://github.com/llvm/llvm-project/commit/0cab8d20417c0e2ccc1ffc5505e080126f5de8e6
DIFF: https://github.com/llvm/llvm-project/commit/0cab8d20417c0e2ccc1ffc5505e080126f5de8e6.diff

LOG: Reapply [IR] Mark and/or constant expressions as undesirable

This reapplies the change for and, but also marks or as undesirable
at the same time. Only handling one of them can cause infinite
combine loops due to the asymmetric handling.

-----

In preparation for removing support for and/or expressions, mark
them as undesirable. As such, we will no longer implicitly create
such expressions, but they still exist.

Added: 
    

Modified: 
    clang/test/CodeGen/catch-nullptr-and-nonzero-offset.c
    llvm/lib/IR/ConstantFold.cpp
    llvm/lib/IR/Constants.cpp
    llvm/test/CodeGen/Hexagon/atomic-opaque-basic.ll
    llvm/test/Transforms/InstCombine/and-xor-or.ll
    llvm/test/Transforms/InstCombine/and.ll
    llvm/test/Transforms/InstCombine/bswap-fold.ll
    llvm/test/Transforms/InstSimplify/ConstProp/constant-expr.ll
    llvm/test/Transforms/InstSimplify/compare.ll

Removed: 
    


################################################################################
diff  --git a/clang/test/CodeGen/catch-nullptr-and-nonzero-offset.c b/clang/test/CodeGen/catch-nullptr-and-nonzero-offset.c
index 551ccc4810bcd3..0e0a9b157464a6 100644
--- a/clang/test/CodeGen/catch-nullptr-and-nonzero-offset.c
+++ b/clang/test/CodeGen/catch-nullptr-and-nonzero-offset.c
@@ -303,7 +303,8 @@ char *one_zero(void) {
 char *one_one_OK(void) {
   // CHECK:                           define{{.*}} ptr @one_one_OK()
   // CHECK-NEXT:                      [[ENTRY:.*]]:
-  // CHECK-SANITIZE-C-NEXT:             br i1 and (i1 icmp ne (ptr inttoptr (i64 1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 1) to i64), i64 1), i64 1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             %[[AND:.*]] = and i1 icmp ne (ptr inttoptr (i64 1 to ptr), ptr null), icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 1) to i64), i64 1), i64 1), i64 0), !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             br i1 %[[AND]], label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE-CPP-NEXT:           br i1 xor (i1 icmp eq (ptr inttoptr (i64 1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 1) to i64), i64 1), i64 1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE:                  [[HANDLER_POINTER_OVERFLOW]]:
   // CHECK-SANITIZE-NORECOVER-NEXT:     call void @__ubsan_handle_pointer_overflow_abort(ptr @[[LINE_1100]], i64 1, i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 1) to i64), i64 1), i64 1))
@@ -321,7 +322,8 @@ char *one_one_OK(void) {
 char *one_allones_BAD(void) {
   // CHECK:                           define{{.*}} ptr @one_allones_BAD()
   // CHECK-NEXT:                      [[ENTRY:.*]]:
-  // CHECK-SANITIZE-C-NEXT:             br i1 and (i1 icmp ne (ptr inttoptr (i64 1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 -1) to i64), i64 1), i64 1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             %[[AND:.*]] = and i1 icmp ne (ptr inttoptr (i64 1 to ptr), ptr null), icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 -1) to i64), i64 1), i64 1), i64 0), !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             br i1 %[[AND]], label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE-CPP-NEXT:           br i1 xor (i1 icmp eq (ptr inttoptr (i64 1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 -1) to i64), i64 1), i64 1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE:                  [[HANDLER_POINTER_OVERFLOW]]:
   // CHECK-SANITIZE-NORECOVER-NEXT:     call void @__ubsan_handle_pointer_overflow_abort(ptr @[[LINE_1200]], i64 1, i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 1 to ptr), i64 -1) to i64), i64 1), i64 1))
@@ -390,7 +392,8 @@ char *allones_zero_OK(void) {
 char *allones_one_BAD(void) {
   // CHECK: define{{.*}} ptr @allones_one_BAD()
   // CHECK-NEXT: [[ENTRY:.*]]:
-  // CHECK-SANITIZE-C-NEXT:             br i1 and (i1 icmp ne (ptr inttoptr (i64 -1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 1) to i64), i64 -1), i64 -1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             %[[AND:.*]] = and i1 icmp ne (ptr inttoptr (i64 -1 to ptr), ptr null), icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 1) to i64), i64 -1), i64 -1), i64 0), !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             br i1 %[[AND]], label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE-CPP-NEXT:           br i1 xor (i1 icmp eq (ptr inttoptr (i64 -1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 1) to i64), i64 -1), i64 -1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE:                  [[HANDLER_POINTER_OVERFLOW]]:
   // CHECK-SANITIZE-NORECOVER-NEXT:     call void @__ubsan_handle_pointer_overflow_abort(ptr @[[LINE_1500]], i64 -1, i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 1) to i64), i64 -1), i64 -1))
@@ -408,7 +411,8 @@ char *allones_one_BAD(void) {
 char *allones_allones_OK(void) {
   // CHECK: define{{.*}} ptr @allones_allones_OK()
   // CHECK-NEXT: [[ENTRY:.*]]:
-  // CHECK-SANITIZE-C-NEXT:             br i1 and (i1 icmp ne (ptr inttoptr (i64 -1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 -1) to i64), i64 -1), i64 -1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             %[[AND:.*]] = and i1 icmp ne (ptr inttoptr (i64 -1 to ptr), ptr null), icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 -1) to i64), i64 -1), i64 -1), i64 0), !nosanitize
+  // CHECK-SANITIZE-C-NEXT:             br i1 %[[AND]], label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE-CPP-NEXT:           br i1 xor (i1 icmp eq (ptr inttoptr (i64 -1 to ptr), ptr null), i1 icmp ne (i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 -1) to i64), i64 -1), i64 -1), i64 0)), label %[[CONT:.*]], label %[[HANDLER_POINTER_OVERFLOW:[^,]+]],{{.*}} !nosanitize
   // CHECK-SANITIZE:                  [[HANDLER_POINTER_OVERFLOW]]:
   // CHECK-SANITIZE-NORECOVER-NEXT:     call void @__ubsan_handle_pointer_overflow_abort(ptr @[[LINE_1600]], i64 -1, i64 add (i64 sub (i64 ptrtoint (ptr getelementptr inbounds (i8, ptr inttoptr (i64 -1 to ptr), i64 -1) to i64), i64 -1), i64 -1))

diff  --git a/llvm/lib/IR/ConstantFold.cpp b/llvm/lib/IR/ConstantFold.cpp
index 4c3325063c09d0..40b21876281142 100644
--- a/llvm/lib/IR/ConstantFold.cpp
+++ b/llvm/lib/IR/ConstantFold.cpp
@@ -1241,8 +1241,6 @@ Constant *llvm::ConstantFoldBinaryInstruction(unsigned Opcode, Constant *C1,
     case Instruction::Add:
     case Instruction::Sub:
       return ConstantExpr::getXor(C1, C2);
-    case Instruction::Mul:
-      return ConstantExpr::getAnd(C1, C2);
     case Instruction::Shl:
     case Instruction::LShr:
     case Instruction::AShr:

diff  --git a/llvm/lib/IR/Constants.cpp b/llvm/lib/IR/Constants.cpp
index c69c7c095f7856..8ea799f0232c56 100644
--- a/llvm/lib/IR/Constants.cpp
+++ b/llvm/lib/IR/Constants.cpp
@@ -2288,6 +2288,8 @@ bool ConstantExpr::isDesirableBinOp(unsigned Opcode) {
   case Instruction::FMul:
   case Instruction::FDiv:
   case Instruction::FRem:
+  case Instruction::And:
+  case Instruction::Or:
     return false;
   case Instruction::Add:
   case Instruction::Sub:
@@ -2295,8 +2297,6 @@ bool ConstantExpr::isDesirableBinOp(unsigned Opcode) {
   case Instruction::Shl:
   case Instruction::LShr:
   case Instruction::AShr:
-  case Instruction::And:
-  case Instruction::Or:
   case Instruction::Xor:
     return true;
   default:

diff  --git a/llvm/test/CodeGen/Hexagon/atomic-opaque-basic.ll b/llvm/test/CodeGen/Hexagon/atomic-opaque-basic.ll
index 61a877ae0ae73f..858bb20da7e38e 100644
--- a/llvm/test/CodeGen/Hexagon/atomic-opaque-basic.ll
+++ b/llvm/test/CodeGen/Hexagon/atomic-opaque-basic.ll
@@ -63,34 +63,30 @@ define void @f1() #0 {
 ; CHECK:         .cfi_startproc
 ; CHECK-NEXT:  // %bb.0: // %entry
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r2 = ##g0
-; CHECK-NEXT:     r0 = #255
+; CHECK-NEXT:     r3 = ##g0
+; CHECK-NEXT:     r1:0 = combine(#1,##255)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r1 = and(r2,#3)
+; CHECK-NEXT:     r2 = and(r3,#3)
+; CHECK-NEXT:     r3 = and(r3,#-4)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r1 = asl(r1,#3)
-; CHECK-NEXT:    }
-; CHECK-NEXT:    {
-; CHECK-NEXT:     r4 = r1
+; CHECK-NEXT:     r2 = asl(r2,#3)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r4 = insert(r2,#2,#3)
-; CHECK-NEXT:     r2 = and(r2,#-4)
+; CHECK-NEXT:     r4 = asl(r0,r2)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r3 = lsl(#1,r4)
-; CHECK-NEXT:     r4 = asl(r0,r4)
+; CHECK-NEXT:     r4 = sub(#-1,r4)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    .p2align 4
 ; CHECK-NEXT:  .LBB1_1: // %cmpxchg.start
 ; CHECK-NEXT:    // =>This Inner Loop Header: Depth=1
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r5 = memw_locked(r2)
+; CHECK-NEXT:     r5 = memw_locked(r3)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r6 = lsr(r5,r1)
+; CHECK-NEXT:     r6 = lsr(r5,r2)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
 ; CHECK-NEXT:     p0 = !bitsclr(r6,r0)
@@ -99,13 +95,13 @@ define void @f1() #0 {
 ; CHECK-NEXT:  .LBB1_2: // %cmpxchg.trystore
 ; CHECK-NEXT:    // in Loop: Header=BB1_1 Depth=1
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r6 = r3
+; CHECK-NEXT:     r5 = and(r5,r4)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     r6 |= and(r5,~r4)
+; CHECK-NEXT:     r5 |= asl(r1,r2)
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
-; CHECK-NEXT:     memw_locked(r2,p0) = r6
+; CHECK-NEXT:     memw_locked(r3,p0) = r5
 ; CHECK-NEXT:    }
 ; CHECK-NEXT:    {
 ; CHECK-NEXT:     if (!p0) jump:nt .LBB1_1

diff  --git a/llvm/test/Transforms/InstCombine/and-xor-or.ll b/llvm/test/Transforms/InstCombine/and-xor-or.ll
index e03a768ac36d1e..a3479758fd9617 100644
--- a/llvm/test/Transforms/InstCombine/and-xor-or.ll
+++ b/llvm/test/Transforms/InstCombine/and-xor-or.ll
@@ -4762,7 +4762,9 @@ define i8 @canonicalize_logic_first_xor_bad_constants2(i8 %x) {
 define i32 @canonicalize_logic_first_constexpr(i32 %x) {
 ; CHECK-LABEL: define {{[^@]+}}@canonicalize_logic_first_constexpr
 ; CHECK-SAME: (i32 [[X:%.*]]) {
-; CHECK-NEXT:    ret i32 and (i32 add (i32 ptrtoint (ptr @g to i32), i32 48), i32 -10)
+; CHECK-NEXT:    [[TMP1:%.*]] = and i32 ptrtoint (ptr @g to i32), -10
+; CHECK-NEXT:    [[R:%.*]] = add i32 [[TMP1]], 48
+; CHECK-NEXT:    ret i32 [[R]]
 ;
   %a = add i32 ptrtoint (ptr @g to i32), 48
   %r = and i32 %a, -10
@@ -4772,7 +4774,9 @@ define i32 @canonicalize_logic_first_constexpr(i32 %x) {
 define i32 @canonicalize_logic_first_constexpr_nuw(i32 %x) {
 ; CHECK-LABEL: define {{[^@]+}}@canonicalize_logic_first_constexpr_nuw
 ; CHECK-SAME: (i32 [[X:%.*]]) {
-; CHECK-NEXT:    ret i32 and (i32 add (i32 ptrtoint (ptr @g to i32), i32 48), i32 -10)
+; CHECK-NEXT:    [[TMP1:%.*]] = and i32 ptrtoint (ptr @g to i32), -10
+; CHECK-NEXT:    [[R:%.*]] = add i32 [[TMP1]], 48
+; CHECK-NEXT:    ret i32 [[R]]
 ;
   %a = add nuw i32 ptrtoint (ptr @g to i32), 48
   %r = and i32 %a, -10

diff  --git a/llvm/test/Transforms/InstCombine/and.ll b/llvm/test/Transforms/InstCombine/and.ll
index 51fc00cf83ec57..3e2adcbb71c5bc 100644
--- a/llvm/test/Transforms/InstCombine/and.ll
+++ b/llvm/test/Transforms/InstCombine/and.ll
@@ -2432,7 +2432,9 @@ define i8 @negate_lowbitmask_use2(i8 %x, i8 %y) {
 
 define i64 @test_and_or_constexpr_infloop() {
 ; CHECK-LABEL: @test_and_or_constexpr_infloop(
-; CHECK-NEXT:    ret i64 or (i64 and (i64 ptrtoint (ptr @g to i64), i64 -8), i64 1)
+; CHECK-NEXT:    [[AND:%.*]] = and i64 ptrtoint (ptr @g to i64), -8
+; CHECK-NEXT:    [[OR:%.*]] = or i64 [[AND]], 1
+; CHECK-NEXT:    ret i64 [[OR]]
 ;
   %and = and i64 ptrtoint (ptr @g to i64), -8
   %or = or i64 %and, 1

diff  --git a/llvm/test/Transforms/InstCombine/bswap-fold.ll b/llvm/test/Transforms/InstCombine/bswap-fold.ll
index 844ae1ee3ca303..a9061d3c95ce98 100644
--- a/llvm/test/Transforms/InstCombine/bswap-fold.ll
+++ b/llvm/test/Transforms/InstCombine/bswap-fold.ll
@@ -786,7 +786,8 @@ define i64 @bs_all_operand64_multiuse_both(i64 %a, i64 %b) #0 {
 
 define void @bs_and_constexpr(ptr %out, i64 %a) {
 ; CHECK-LABEL: @bs_and_constexpr(
-; CHECK-NEXT:    [[RES:%.*]] = call i64 @llvm.bswap.i64(i64 and (i64 ptrtoint (ptr @gp to i64), i64 4095))
+; CHECK-NEXT:    [[EXP:%.*]] = and i64 ptrtoint (ptr @gp to i64), 4095
+; CHECK-NEXT:    [[RES:%.*]] = call i64 @llvm.bswap.i64(i64 [[EXP]])
 ; CHECK-NEXT:    store i64 [[RES]], ptr [[OUT:%.*]], align 8
 ; CHECK-NEXT:    ret void
 ;
@@ -800,7 +801,8 @@ define void @bs_and_constexpr(ptr %out, i64 %a) {
 
 define void @bs_and_bs_constexpr(ptr %out, i64 %a) {
 ; CHECK-LABEL: @bs_and_bs_constexpr(
-; CHECK-NEXT:    store i64 and (i64 ptrtoint (ptr @gp to i64), i64 -67835469387268096), ptr [[OUT:%.*]], align 8
+; CHECK-NEXT:    [[TMP1:%.*]] = and i64 ptrtoint (ptr @gp to i64), -67835469387268096
+; CHECK-NEXT:    store i64 [[TMP1]], ptr [[OUT:%.*]], align 8
 ; CHECK-NEXT:    ret void
 ;
   %gpi = ptrtoint ptr @gp to i64

diff  --git a/llvm/test/Transforms/InstSimplify/ConstProp/constant-expr.ll b/llvm/test/Transforms/InstSimplify/ConstProp/constant-expr.ll
index bdecda847d3727..55ee7b3a6cadc2 100644
--- a/llvm/test/Transforms/InstSimplify/ConstProp/constant-expr.ll
+++ b/llvm/test/Transforms/InstSimplify/ConstProp/constant-expr.ll
@@ -9,7 +9,7 @@
 @B = global i1 sub (i1 icmp ult (ptr @X, ptr @Y), i1 icmp ult (ptr @X, ptr @Z)), align 2
 ; CHECK: @B = global i1 xor (i1 icmp ult (ptr @X, ptr @Y), i1 icmp ult (ptr @X, ptr @Z))
 @C = global i1 mul (i1 icmp ult (ptr @X, ptr @Y), i1 icmp ult (ptr @X, ptr @Z))
-; CHECK: @C = global i1 and (i1 icmp ult (ptr @X, ptr @Y), i1 icmp ult (ptr @X, ptr @Z))
+; CHECK: @C = global i1 mul (i1 icmp ult (ptr @X, ptr @Y), i1 icmp ult (ptr @X, ptr @Z))
 
 @H = global i1 icmp ule (ptr @X, ptr @Y)
 ; CHECK: @H = global i1 icmp ule (ptr @X, ptr @Y)

diff  --git a/llvm/test/Transforms/InstSimplify/compare.ll b/llvm/test/Transforms/InstSimplify/compare.ll
index c62399c119c901..c6c104a41c8be7 100644
--- a/llvm/test/Transforms/InstSimplify/compare.ll
+++ b/llvm/test/Transforms/InstSimplify/compare.ll
@@ -490,7 +490,8 @@ define i1 @or(i32 %x) {
 define i1 @or_constexp(i32 %x) {
 ; CHECK-LABEL: @or_constexp(
 ; CHECK-NEXT:  entry:
-; CHECK-NEXT:    [[O:%.*]] = or i32 [[X:%.*]], and (i32 ptrtoint (ptr @GV to i32), i32 32)
+; CHECK-NEXT:    [[TMP0:%.*]] = and i32 ptrtoint (ptr @GV to i32), 32
+; CHECK-NEXT:    [[O:%.*]] = or i32 [[X:%.*]], [[TMP0]]
 ; CHECK-NEXT:    [[C:%.*]] = icmp eq i32 [[O]], 0
 ; CHECK-NEXT:    ret i1 [[C]]
 ;


        


More information about the cfe-commits mailing list