[llvm] 097925a - [ConstraintElimination] Add test cases with @llvm.assume.

Florian Hahn via llvm-commits llvm-commits at lists.llvm.org
Wed Aug 25 13:00:39 PDT 2021


Author: Florian Hahn
Date: 2021-08-25T20:47:06+01:00
New Revision: 097925aab9cac3c381fd94e2e03733fdaf21f897

URL: https://github.com/llvm/llvm-project/commit/097925aab9cac3c381fd94e2e03733fdaf21f897
DIFF: https://github.com/llvm/llvm-project/commit/097925aab9cac3c381fd94e2e03733fdaf21f897.diff

LOG: [ConstraintElimination] Add test cases with @llvm.assume.

Added: 
    llvm/test/Transforms/ConstraintElimination/assumes.ll

Modified: 
    

Removed: 
    


################################################################################
diff  --git a/llvm/test/Transforms/ConstraintElimination/assumes.ll b/llvm/test/Transforms/ConstraintElimination/assumes.ll
new file mode 100644
index 0000000000000..37a1d3f335686
--- /dev/null
+++ b/llvm/test/Transforms/ConstraintElimination/assumes.ll
@@ -0,0 +1,272 @@
+; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
+; RUN: opt -constraint-elimination -S %s | FileCheck %s
+
+declare void @llvm.assume(i1)
+
+declare void @may_unwind()
+
+declare void @use(i1)
+
+define i1 @assume_dominates(i8 %a, i8 %b, i1 %c) {
+; CHECK-LABEL: @assume_dominates(
+; CHECK-NEXT:    [[ADD_1:%.*]] = add nuw nsw i8 [[A:%.*]], 1
+; CHECK-NEXT:    [[CMP_1:%.*]] = icmp ule i8 [[ADD_1]], [[B:%.*]]
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP_1]])
+; CHECK-NEXT:    br i1 [[C:%.*]], label [[THEN:%.*]], label [[ELSE:%.*]]
+; CHECK:       then:
+; CHECK-NEXT:    [[T_1:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    [[T_2:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_1:%.*]] = xor i1 [[T_1]], [[T_2]]
+; CHECK-NEXT:    [[ADD_2:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_1:%.*]] = icmp ule i8 [[ADD_2]], [[B]]
+; CHECK-NEXT:    [[RES_2:%.*]] = xor i1 [[RES_1]], [[C_1]]
+; CHECK-NEXT:    ret i1 [[RES_2]]
+; CHECK:       else:
+; CHECK-NEXT:    [[T_3:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    [[T_4:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_3:%.*]] = xor i1 [[T_3]], [[T_4]]
+; CHECK-NEXT:    [[ADD_2_1:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_2:%.*]] = icmp ule i8 [[ADD_2_1]], [[B]]
+; CHECK-NEXT:    [[RES_4:%.*]] = xor i1 [[RES_3]], [[C_2]]
+; CHECK-NEXT:    ret i1 [[RES_4]]
+;
+  %add.1 = add nsw nuw i8 %a, 1
+  %cmp.1 = icmp ule i8 %add.1, %b
+  call void @llvm.assume(i1 %cmp.1)
+  br i1 %c, label %then, label %else
+
+then:
+  %t.1 = icmp ule i8 %add.1, %b
+  %t.2 = icmp ule i8 %a, %b
+  %res.1 = xor i1 %t.1, %t.2
+  %add.2 = add nsw nuw i8 %a, 2
+  %c.1 = icmp ule i8 %add.2, %b
+  %res.2 = xor i1 %res.1, %c.1
+  ret i1 %res.2
+
+else:
+  %t.3 = icmp ule i8 %add.1, %b
+  %t.4 = icmp ule i8 %a, %b
+  %res.3 = xor i1 %t.3, %t.4
+  %add.2.1 = add nsw nuw i8 %a, 2
+  %c.2 = icmp ule i8 %add.2.1, %b
+  %res.4 = xor i1 %res.3, %c.2
+  ret i1 %res.4
+}
+
+define i1 @assume_same_bb(i8 %a, i8 %b, i1 %c) {
+; CHECK-LABEL: @assume_same_bb(
+; CHECK-NEXT:    [[ADD_1:%.*]] = add nuw nsw i8 [[A:%.*]], 1
+; CHECK-NEXT:    [[CMP_1:%.*]] = icmp ule i8 [[ADD_1]], [[B:%.*]]
+; CHECK-NEXT:    br i1 [[C:%.*]], label [[THEN:%.*]], label [[ELSE:%.*]]
+; CHECK:       then:
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP_1]])
+; CHECK-NEXT:    [[T_1:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    [[T_2:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_1:%.*]] = xor i1 [[T_1]], [[T_2]]
+; CHECK-NEXT:    [[ADD_2:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_1:%.*]] = icmp ule i8 [[ADD_2]], [[B]]
+; CHECK-NEXT:    [[RES_2:%.*]] = xor i1 [[RES_1]], [[C_1]]
+; CHECK-NEXT:    ret i1 [[RES_2]]
+; CHECK:       else:
+; CHECK-NEXT:    [[T_3:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    [[T_4:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_3:%.*]] = xor i1 [[T_3]], [[T_4]]
+; CHECK-NEXT:    [[ADD_2_1:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_2:%.*]] = icmp ule i8 [[ADD_2_1]], [[B]]
+; CHECK-NEXT:    [[RES_4:%.*]] = xor i1 [[RES_3]], [[C_2]]
+; CHECK-NEXT:    ret i1 [[RES_4]]
+;
+  %add.1 = add nsw nuw i8 %a, 1
+  %cmp.1 = icmp ule i8 %add.1, %b
+  br i1 %c, label %then, label %else
+
+then:
+  call void @llvm.assume(i1 %cmp.1)
+  %t.1 = icmp ule i8 %add.1, %b
+  %t.2 = icmp ule i8 %a, %b
+  %res.1 = xor i1 %t.1, %t.2
+  %add.2 = add nsw nuw i8 %a, 2
+  %c.1 = icmp ule i8 %add.2, %b
+  %res.2 = xor i1 %res.1, %c.1
+  ret i1 %res.2
+
+else:
+  %t.3 = icmp ule i8 %add.1, %b
+  %t.4 = icmp ule i8 %a, %b
+  %res.3 = xor i1 %t.3, %t.4
+  %add.2.1 = add nsw nuw i8 %a, 2
+  %c.2 = icmp ule i8 %add.2.1, %b
+  %res.4 = xor i1 %res.3, %c.2
+  ret i1 %res.4
+}
+
+
+define i1 @assume_same_bb2(i8 %a, i8 %b, i1 %c) {
+; CHECK-LABEL: @assume_same_bb2(
+; CHECK-NEXT:    [[ADD_1:%.*]] = add nuw nsw i8 [[A:%.*]], 1
+; CHECK-NEXT:    [[CMP_1:%.*]] = icmp ule i8 [[ADD_1]], [[B:%.*]]
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP_1]])
+; CHECK-NEXT:    [[T_1:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    [[T_2:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_1:%.*]] = xor i1 [[T_1]], [[T_2]]
+; CHECK-NEXT:    [[ADD_2:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_1:%.*]] = icmp ule i8 [[ADD_2]], [[B]]
+; CHECK-NEXT:    [[RES_2:%.*]] = xor i1 [[RES_1]], [[C_1]]
+; CHECK-NEXT:    br label [[EXIT:%.*]]
+; CHECK:       exit:
+; CHECK-NEXT:    ret i1 [[RES_2]]
+;
+  %add.1 = add nsw nuw i8 %a, 1
+  %cmp.1 = icmp ule i8 %add.1, %b
+  call void @llvm.assume(i1 %cmp.1)
+  %t.1 = icmp ule i8 %add.1, %b
+  %t.2 = icmp ule i8 %a, %b
+  %res.1 = xor i1 %t.1, %t.2
+  %add.2 = add nsw nuw i8 %a, 2
+  %c.1 = icmp ule i8 %add.2, %b
+  %res.2 = xor i1 %res.1, %c.1
+  br label %exit
+
+exit:
+  ret i1 %res.2
+}
+
+
+; TODO: Keep track of position of assume and may unwinding calls, simplify
+; conditions if possible.
+define i1 @assume_same_bb_after_may_exiting_call(i8 %a, i8 %b, i1 %c) {
+; CHECK-LABEL: @assume_same_bb_after_may_exiting_call(
+; CHECK-NEXT:    [[ADD_1:%.*]] = add nuw nsw i8 [[A:%.*]], 1
+; CHECK-NEXT:    [[CMP_1:%.*]] = icmp ule i8 [[ADD_1]], [[B:%.*]]
+; CHECK-NEXT:    call void @may_unwind()
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP_1]])
+; CHECK-NEXT:    [[T_1:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    [[T_2:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_1:%.*]] = xor i1 [[T_1]], [[T_2]]
+; CHECK-NEXT:    [[ADD_2:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_1:%.*]] = icmp ule i8 [[ADD_2]], [[B]]
+; CHECK-NEXT:    [[RES_2:%.*]] = xor i1 [[RES_1]], [[C_1]]
+; CHECK-NEXT:    br label [[EXIT:%.*]]
+; CHECK:       exit:
+; CHECK-NEXT:    ret i1 [[RES_2]]
+;
+  %add.1 = add nsw nuw i8 %a, 1
+  %cmp.1 = icmp ule i8 %add.1, %b
+  call void @may_unwind()
+  call void @llvm.assume(i1 %cmp.1)
+  %t.1 = icmp ule i8 %add.1, %b
+  %t.2 = icmp ule i8 %a, %b
+  %res.1 = xor i1 %t.1, %t.2
+  %add.2 = add nsw nuw i8 %a, 2
+  %c.1 = icmp ule i8 %add.2, %b
+  %res.2 = xor i1 %res.1, %c.1
+  br label %exit
+
+exit:
+  ret i1 %res.2
+}
+
+; TODO: Keep track of position of assume and may unwinding calls, simplify
+; conditions if possible.
+define i1 @assume_same_bb_before_may_exiting_call(i8 %a, i8 %b, i1 %c) {
+; CHECK-LABEL: @assume_same_bb_before_may_exiting_call(
+; CHECK-NEXT:    [[ADD_1:%.*]] = add nuw nsw i8 [[A:%.*]], 1
+; CHECK-NEXT:    [[CMP_1:%.*]] = icmp ule i8 [[ADD_1]], [[B:%.*]]
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP_1]])
+; CHECK-NEXT:    call void @may_unwind()
+; CHECK-NEXT:    [[T_1:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    [[T_2:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_1:%.*]] = xor i1 [[T_1]], [[T_2]]
+; CHECK-NEXT:    [[ADD_2:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_1:%.*]] = icmp ule i8 [[ADD_2]], [[B]]
+; CHECK-NEXT:    [[RES_2:%.*]] = xor i1 [[RES_1]], [[C_1]]
+; CHECK-NEXT:    br label [[EXIT:%.*]]
+; CHECK:       exit:
+; CHECK-NEXT:    ret i1 [[RES_2]]
+;
+  %add.1 = add nsw nuw i8 %a, 1
+  %cmp.1 = icmp ule i8 %add.1, %b
+  call void @llvm.assume(i1 %cmp.1)
+  call void @may_unwind()
+  %t.1 = icmp ule i8 %add.1, %b
+  %t.2 = icmp ule i8 %a, %b
+  %res.1 = xor i1 %t.1, %t.2
+  %add.2 = add nsw nuw i8 %a, 2
+  %c.1 = icmp ule i8 %add.2, %b
+  %res.2 = xor i1 %res.1, %c.1
+  br label %exit
+
+exit:
+  ret i1 %res.2
+}
+
+define i1 @assume_same_bb_after_condition(i8 %a, i8 %b, i1 %c) {
+; CHECK-LABEL: @assume_same_bb_after_condition(
+; CHECK-NEXT:    [[ADD_1:%.*]] = add nuw nsw i8 [[A:%.*]], 1
+; CHECK-NEXT:    [[T_1:%.*]] = icmp ule i8 [[ADD_1]], [[B:%.*]]
+; CHECK-NEXT:    [[T_2:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    [[RES_1:%.*]] = xor i1 [[T_1]], [[T_2]]
+; CHECK-NEXT:    [[ADD_2:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_1:%.*]] = icmp ule i8 [[ADD_2]], [[B]]
+; CHECK-NEXT:    [[RES_2:%.*]] = xor i1 [[RES_1]], [[C_1]]
+; CHECK-NEXT:    [[CMP_1:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP_1]])
+; CHECK-NEXT:    br label [[EXIT:%.*]]
+; CHECK:       exit:
+; CHECK-NEXT:    ret i1 [[RES_2]]
+;
+  %add.1 = add nsw nuw i8 %a, 1
+  %t.1 = icmp ule i8 %add.1, %b
+  %t.2 = icmp ule i8 %a, %b
+  %res.1 = xor i1 %t.1, %t.2
+  %add.2 = add nsw nuw i8 %a, 2
+  %c.1 = icmp ule i8 %add.2, %b
+  %res.2 = xor i1 %res.1, %c.1
+  %cmp.1 = icmp ule i8 %add.1, %b
+  call void @llvm.assume(i1 %cmp.1)
+  br label %exit
+
+exit:
+  ret i1 %res.2
+}
+
+; The function may exit before the assume if @may_unwind unwinds. Conditions
+; before the call cannot be simplified.
+define i1 @assume_same_bb_after_condition_may_unwind_between(i8 %a, i8 %b, i1 %c) {
+; CHECK-LABEL: @assume_same_bb_after_condition_may_unwind_between(
+; CHECK-NEXT:    [[ADD_1:%.*]] = add nuw nsw i8 [[A:%.*]], 1
+; CHECK-NEXT:    [[C_1:%.*]] = icmp ule i8 [[ADD_1]], [[B:%.*]]
+; CHECK-NEXT:    call void @use(i1 [[C_1]])
+; CHECK-NEXT:    [[C_2:%.*]] = icmp ule i8 [[A]], [[B]]
+; CHECK-NEXT:    call void @use(i1 [[C_2]])
+; CHECK-NEXT:    [[RES_1:%.*]] = xor i1 [[C_1]], [[C_2]]
+; CHECK-NEXT:    [[ADD_2:%.*]] = add nuw nsw i8 [[A]], 2
+; CHECK-NEXT:    [[C_3:%.*]] = icmp ule i8 [[ADD_2]], [[B]]
+; CHECK-NEXT:    call void @use(i1 [[C_3]])
+; CHECK-NEXT:    [[RES_2:%.*]] = xor i1 [[RES_1]], [[C_3]]
+; CHECK-NEXT:    [[CMP_1:%.*]] = icmp ule i8 [[ADD_1]], [[B]]
+; CHECK-NEXT:    call void @may_unwind()
+; CHECK-NEXT:    call void @llvm.assume(i1 [[CMP_1]])
+; CHECK-NEXT:    br label [[EXIT:%.*]]
+; CHECK:       exit:
+; CHECK-NEXT:    ret i1 [[RES_2]]
+;
+  %add.1 = add nsw nuw i8 %a, 1
+  %c.1 = icmp ule i8 %add.1, %b
+  call void @use(i1 %c.1)
+  %c.2 = icmp ule i8 %a, %b
+  call void @use(i1 %c.2)
+  %res.1 = xor i1 %c.1, %c.2
+  %add.2 = add nsw nuw i8 %a, 2
+  %c.3 = icmp ule i8 %add.2, %b
+  call void @use(i1 %c.3)
+  %res.2 = xor i1 %res.1, %c.3
+  %cmp.1 = icmp ule i8 %add.1, %b
+  call void @may_unwind()
+  call void @llvm.assume(i1 %cmp.1)
+  br label %exit
+
+exit:
+  ret i1 %res.2
+}


        


More information about the llvm-commits mailing list