[llvm] [InstCombine] Improve handling of `not` and free inversion. (PR #66787)

via llvm-commits llvm-commits at lists.llvm.org
Sun Nov 19 10:52:04 PST 2023


================
@@ -0,0 +1,521 @@
+; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
+; RUN: opt < %s -passes=instcombine -S | FileCheck %s
+
+declare i8 @llvm.smin.i8(i8, i8)
+declare i8 @llvm.umin.i8(i8, i8)
+declare i8 @llvm.smax.i8(i8, i8)
+declare i8 @llvm.umax.i8(i8, i8)
+
+declare void @use.i8(i8)
+
+define i8 @xor_1(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @xor_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[BA:%.*]] = xor i8 [[B]], [[A:%.*]]
+; CHECK-NEXT:    [[NOT_BA:%.*]] = xor i8 [[BA]], -1
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ba = xor i8 %b, %a
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @xor_2(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @xor_2(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[AB:%.*]] = xor i8 [[B]], [[A:%.*]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ab = xor i8 %a, %b
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @xor_fail(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @xor_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[Y:%.*]]
+; CHECK-NEXT:    [[AB:%.*]] = xor i8 [[B]], [[A:%.*]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %b = select i1 %c, i8 %nx, i8 %y
+  %ab = xor i8 %a, %b
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @add_1(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @add_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[BA:%.*]] = add i8 [[B]], [[A:%.*]]
+; CHECK-NEXT:    [[NOT_BA:%.*]] = xor i8 [[BA]], -1
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ba = add i8 %b, %a
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @add_2(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @add_2(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[AB:%.*]] = add i8 [[B]], [[A:%.*]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ab = add i8 %a, %b
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @add_fail(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @add_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], [[A:%.*]]
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[AB:%.*]] = add i8 [[B]], [[A]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, %a
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ab = add i8 %a, %b
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @sub_1(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @sub_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[TMP1:%.*]] = xor i8 [[B]], -1
+; CHECK-NEXT:    [[NOT_BA:%.*]] = add i8 [[TMP1]], [[A:%.*]]
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ba = sub i8 %b, %a
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @sub_2(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @sub_2(
+; CHECK-NEXT:    [[TMP1:%.*]] = xor i8 [[Y:%.*]], -124
+; CHECK-NEXT:    [[B_NEG_V:%.*]] = select i1 [[C:%.*]], i8 [[X:%.*]], i8 [[TMP1]]
+; CHECK-NEXT:    [[B_NEG:%.*]] = add i8 [[B_NEG_V]], 1
+; CHECK-NEXT:    [[AB:%.*]] = add i8 [[B_NEG]], [[A:%.*]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ab = sub i8 %a, %b
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @sub_fail(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @sub_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    call void @use.i8(i8 [[NX]])
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[TMP1:%.*]] = xor i8 [[B]], -1
+; CHECK-NEXT:    [[NOT_BA:%.*]] = add i8 [[TMP1]], [[A:%.*]]
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  call void @use.i8(i8 %nx)
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ba = sub i8 %b, %a
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @ashr_1(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @ashr_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[BA:%.*]] = ashr i8 [[B]], [[A:%.*]]
+; CHECK-NEXT:    [[NOT_BA:%.*]] = xor i8 [[BA]], -1
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ba = ashr i8 %b, %a
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @ashr_2_fail(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @ashr_2_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[AB:%.*]] = ashr i8 [[A:%.*]], [[B]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ab = ashr i8 %a, %b
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @select_1(i1 %cc, i8 %na, i8 %aa, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @select_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[TMP1:%.*]] = xor i8 [[NA:%.*]], [[AA:%.*]]
+; CHECK-NEXT:    [[A:%.*]] = xor i8 [[TMP1]], 45
+; CHECK-NEXT:    [[AB:%.*]] = select i1 [[CC:%.*]], i8 [[A]], i8 [[B]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %nna = xor i8 %na, 45
+  %a = xor i8 %aa, %nna
+  %ab = select i1 %cc, i8 %a, i8 %b
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @select_2(i1 %cc, i8 %na, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @select_2(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[A:%.*]] = xor i8 [[NA:%.*]], 45
+; CHECK-NEXT:    [[BA:%.*]] = select i1 [[CC:%.*]], i8 [[B]], i8 [[A]]
+; CHECK-NEXT:    [[NOT_BA:%.*]] = xor i8 [[BA]], -1
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %a = xor i8 %na, 45
+  %ba = select i1 %cc, i8 %b, i8 %a
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i1 @select_logic_or_fail(i1 %cc, i1 %c, i1 %x, i8 %y) {
+; CHECK-LABEL: @select_logic_or_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i1 [[X:%.*]], true
+; CHECK-NEXT:    [[YY:%.*]] = icmp eq i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i1 [[NX]], i1 [[YY]]
+; CHECK-NEXT:    [[AB:%.*]] = select i1 [[CC:%.*]], i1 [[B]], i1 false
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i1 [[AB]], true
+; CHECK-NEXT:    ret i1 [[NOT_AB]]
+;
+  %nx = xor i1 %x, -1
+  %yy = icmp eq i8 %y, 123
+  %b = select i1 %c, i1 %nx, i1 %yy
+  %ab = select i1 %cc, i1 %b, i1 false
+  %not_ab = xor i1 %ab, -1
+  ret i1 %not_ab
+}
+
+define i1 @select_logic_and_fail(i1 %cc, i1 %c, i1 %x, i8 %y) {
+; CHECK-LABEL: @select_logic_and_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i1 [[X:%.*]], true
+; CHECK-NEXT:    [[YY:%.*]] = icmp eq i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i1 [[NX]], i1 [[YY]]
+; CHECK-NEXT:    [[AB:%.*]] = select i1 [[CC:%.*]], i1 true, i1 [[B]]
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i1 [[AB]], true
+; CHECK-NEXT:    ret i1 [[NOT_AB]]
+;
+  %nx = xor i1 %x, -1
+  %yy = icmp eq i8 %y, 123
+  %b = select i1 %c, i1 %nx, i1 %yy
+  %ab = select i1 %cc, i1 true, i1 %b
+  %not_ab = xor i1 %ab, -1
+  ret i1 %not_ab
+}
+
+define i8 @smin_1(i8 %aa, i8 %na, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @smin_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[NNA:%.*]] = xor i8 [[NA:%.*]], -1
+; CHECK-NEXT:    [[A:%.*]] = add i8 [[NNA]], [[AA:%.*]]
+; CHECK-NEXT:    [[AB:%.*]] = call i8 @llvm.smin.i8(i8 [[A]], i8 [[B]])
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %nna = xor i8 %na, -1
+  %a = add i8 %aa, %nna
+  %ab = call i8 @llvm.smin.i8(i8 %a, i8 %b)
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @smin_1_fail(i8 %a, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @smin_1_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[AB:%.*]] = call i8 @llvm.smin.i8(i8 [[A:%.*]], i8 [[B]])
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ab = call i8 @llvm.smin.i8(i8 %a, i8 %b)
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @umin_1_fail(i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @umin_1_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[Y:%.*]]
+; CHECK-NEXT:    [[BA:%.*]] = call i8 @llvm.umin.i8(i8 [[B]], i8 85)
+; CHECK-NEXT:    [[NOT_BA:%.*]] = xor i8 [[BA]], -1
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %b = select i1 %c, i8 %nx, i8 %y
+  %ba = call i8 @llvm.umin.i8(i8 %b, i8 85)
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @smax_1(i8 %aa, i8 %na, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @smax_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[NNA:%.*]] = xor i8 [[NA:%.*]], -1
+; CHECK-NEXT:    [[A:%.*]] = sub i8 [[NNA]], [[AA:%.*]]
+; CHECK-NEXT:    [[AB:%.*]] = call i8 @llvm.smax.i8(i8 [[A]], i8 [[B]])
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %nna = xor i8 %na, -1
+  %a = sub i8 %nna, %aa
+  %ab = call i8 @llvm.smax.i8(i8 %a, i8 %b)
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @smax_1_fail(i8 %aa, i8 %na, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @smax_1_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    call void @use.i8(i8 [[YY]])
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[NNA:%.*]] = xor i8 [[NA:%.*]], -1
+; CHECK-NEXT:    [[A:%.*]] = sub i8 [[NNA]], [[AA:%.*]]
+; CHECK-NEXT:    [[AB:%.*]] = call i8 @llvm.smax.i8(i8 [[A]], i8 [[B]])
+; CHECK-NEXT:    [[NOT_AB:%.*]] = xor i8 [[AB]], -1
+; CHECK-NEXT:    ret i8 [[NOT_AB]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  call void @use.i8(i8 %yy)
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %nna = xor i8 %na, -1
+  %a = sub i8 %nna, %aa
+  %ab = call i8 @llvm.smax.i8(i8 %a, i8 %b)
+  %not_ab = xor i8 %ab, -1
+  ret i8 %not_ab
+}
+
+define i8 @umax_1(i8 %na, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @umax_1(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    [[BA:%.*]] = call i8 @llvm.umax.i8(i8 [[B]], i8 85)
+; CHECK-NEXT:    [[NOT_BA:%.*]] = xor i8 [[BA]], -1
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  %ba = call i8 @llvm.umax.i8(i8 %b, i8 85)
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @umax_1_fail(i8 %na, i1 %c, i8 %x, i8 %y) {
+; CHECK-LABEL: @umax_1_fail(
+; CHECK-NEXT:    [[NX:%.*]] = xor i8 [[X:%.*]], -1
+; CHECK-NEXT:    [[YY:%.*]] = xor i8 [[Y:%.*]], 123
+; CHECK-NEXT:    [[B:%.*]] = select i1 [[C:%.*]], i8 [[NX]], i8 [[YY]]
+; CHECK-NEXT:    call void @use.i8(i8 [[B]])
+; CHECK-NEXT:    [[BA:%.*]] = call i8 @llvm.umax.i8(i8 [[B]], i8 85)
+; CHECK-NEXT:    [[NOT_BA:%.*]] = xor i8 [[BA]], -1
+; CHECK-NEXT:    ret i8 [[NOT_BA]]
+;
+  %nx = xor i8 %x, -1
+  %yy = xor i8 %y, 123
+  %b = select i1 %c, i8 %nx, i8 %yy
+  call void @use.i8(i8 %b)
+  %ba = call i8 @llvm.umax.i8(i8 %b, i8 85)
+  %not_ba = xor i8 %ba, -1
+  ret i8 %not_ba
+}
+
+define i8 @sub_both_freely_invertable_always(i8 %x, i8 %y) {
+; CHECK-LABEL: @sub_both_freely_invertable_always(
+; CHECK-NEXT:    [[XX:%.*]] = xor i8 [[X:%.*]], 123
+; CHECK-NEXT:    [[TMP1:%.*]] = xor i8 [[Y:%.*]], -46
+; CHECK-NEXT:    [[YY_NEG:%.*]] = add i8 [[TMP1]], 1
+; CHECK-NEXT:    [[R:%.*]] = add i8 [[YY_NEG]], [[XX]]
----------------
goldsteinn wrote:

Okay, update so that we ensure we save an inst.

https://github.com/llvm/llvm-project/pull/66787


More information about the llvm-commits mailing list