blob: a2225e4954827ba97e51ed784ac8702978fa1049 [file] [log] [blame]
Florian Hahn106ae102020-02-17 16:35:57 +01001; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2; RUN: opt -codegenprepare -S < %s | FileCheck %s
3; RUN: opt -enable-debugify -codegenprepare -S < %s 2>&1 | FileCheck %s -check-prefix=DEBUG
4
5; Subset of tests from llvm/tests/Transforms/CodeGenPrepare/X86/overflow-intrinsics.ll
6; to test shouldFormOverflowOp on SPARC, where it is not profitable to create
7; overflow intrinsics if the math part is not used.
8
9target triple = "arm64-apple-iphoneos"
10
11define i64 @uaddo1_overflow_used(i64 %a, i64 %b) nounwind ssp {
12; CHECK-LABEL: @uaddo1_overflow_used(
13; CHECK-NEXT: [[TMP1:%.*]] = call { i64, i1 } @llvm.uadd.with.overflow.i64(i64 [[B:%.*]], i64 [[A:%.*]])
14; CHECK-NEXT: [[MATH:%.*]] = extractvalue { i64, i1 } [[TMP1]], 0
15; CHECK-NEXT: [[OV:%.*]] = extractvalue { i64, i1 } [[TMP1]], 1
16; CHECK-NEXT: [[Q:%.*]] = select i1 [[OV]], i64 [[B]], i64 42
17; CHECK-NEXT: ret i64 [[Q]]
18;
19 %add = add i64 %b, %a
20 %cmp = icmp ult i64 %add, %a
21 %Q = select i1 %cmp, i64 %b, i64 42
22 ret i64 %Q
23}
24
25define i64 @uaddo1_math_overflow_used(i64 %a, i64 %b, i64* %res) nounwind ssp {
26; CHECK-LABEL: @uaddo1_math_overflow_used(
27; CHECK-NEXT: [[TMP1:%.*]] = call { i64, i1 } @llvm.uadd.with.overflow.i64(i64 [[B:%.*]], i64 [[A:%.*]])
28; CHECK-NEXT: [[MATH:%.*]] = extractvalue { i64, i1 } [[TMP1]], 0
29; CHECK-NEXT: [[OV:%.*]] = extractvalue { i64, i1 } [[TMP1]], 1
30; CHECK-NEXT: [[Q:%.*]] = select i1 [[OV]], i64 [[B]], i64 42
31; CHECK-NEXT: store i64 [[MATH]], i64* [[RES:%.*]]
32; CHECK-NEXT: ret i64 [[Q]]
33;
34 %add = add i64 %b, %a
35 %cmp = icmp ult i64 %add, %a
36 %Q = select i1 %cmp, i64 %b, i64 42
37 store i64 %add, i64* %res
38 ret i64 %Q
39}
40
41define i64 @uaddo2_overflow_used(i64 %a, i64 %b) nounwind ssp {
42; CHECK-LABEL: @uaddo2_overflow_used(
43; CHECK-NEXT: [[TMP1:%.*]] = call { i64, i1 } @llvm.uadd.with.overflow.i64(i64 [[B:%.*]], i64 [[A:%.*]])
44; CHECK-NEXT: [[MATH:%.*]] = extractvalue { i64, i1 } [[TMP1]], 0
45; CHECK-NEXT: [[OV:%.*]] = extractvalue { i64, i1 } [[TMP1]], 1
46; CHECK-NEXT: [[Q:%.*]] = select i1 [[OV]], i64 [[B]], i64 42
47; CHECK-NEXT: ret i64 [[Q]]
48;
49 %add = add i64 %b, %a
50 %cmp = icmp ult i64 %add, %b
51 %Q = select i1 %cmp, i64 %b, i64 42
52 ret i64 %Q
53}
54
55define i64 @uaddo2_math_overflow_used(i64 %a, i64 %b, i64* %res) nounwind ssp {
56; CHECK-LABEL: @uaddo2_math_overflow_used(
57; CHECK-NEXT: [[TMP1:%.*]] = call { i64, i1 } @llvm.uadd.with.overflow.i64(i64 [[B:%.*]], i64 [[A:%.*]])
58; CHECK-NEXT: [[MATH:%.*]] = extractvalue { i64, i1 } [[TMP1]], 0
59; CHECK-NEXT: [[OV:%.*]] = extractvalue { i64, i1 } [[TMP1]], 1
60; CHECK-NEXT: [[Q:%.*]] = select i1 [[OV]], i64 [[B]], i64 42
61; CHECK-NEXT: store i64 [[MATH]], i64* [[RES:%.*]]
62; CHECK-NEXT: ret i64 [[Q]]
63;
64 %add = add i64 %b, %a
65 %cmp = icmp ult i64 %add, %b
66 %Q = select i1 %cmp, i64 %b, i64 42
67 store i64 %add, i64* %res
68 ret i64 %Q
69}
70
71define i64 @uaddo3_overflow_used(i64 %a, i64 %b) nounwind ssp {
72; CHECK-LABEL: @uaddo3_overflow_used(
73; CHECK-NEXT: [[TMP1:%.*]] = call { i64, i1 } @llvm.uadd.with.overflow.i64(i64 [[B:%.*]], i64 [[A:%.*]])
74; CHECK-NEXT: [[MATH:%.*]] = extractvalue { i64, i1 } [[TMP1]], 0
75; CHECK-NEXT: [[OV:%.*]] = extractvalue { i64, i1 } [[TMP1]], 1
76; CHECK-NEXT: [[Q:%.*]] = select i1 [[OV]], i64 [[B]], i64 42
77; CHECK-NEXT: ret i64 [[Q]]
78;
79 %add = add i64 %b, %a
80 %cmp = icmp ugt i64 %b, %add
81 %Q = select i1 %cmp, i64 %b, i64 42
82 ret i64 %Q
83}
84
85define i64 @uaddo3_math_overflow_used(i64 %a, i64 %b, i64* %res) nounwind ssp {
86; CHECK-LABEL: @uaddo3_math_overflow_used(
87; CHECK-NEXT: [[TMP1:%.*]] = call { i64, i1 } @llvm.uadd.with.overflow.i64(i64 [[B:%.*]], i64 [[A:%.*]])
88; CHECK-NEXT: [[MATH:%.*]] = extractvalue { i64, i1 } [[TMP1]], 0
89; CHECK-NEXT: [[OV:%.*]] = extractvalue { i64, i1 } [[TMP1]], 1
90; CHECK-NEXT: [[Q:%.*]] = select i1 [[OV]], i64 [[B]], i64 42
91; CHECK-NEXT: store i64 [[MATH]], i64* [[RES:%.*]]
92; CHECK-NEXT: ret i64 [[Q]]
93;
94 %add = add i64 %b, %a
95 %cmp = icmp ugt i64 %b, %add
96 %Q = select i1 %cmp, i64 %b, i64 42
97 store i64 %add, i64* %res
98 ret i64 %Q
99}
100
101define i1 @usubo_ult_i64_overflow_used(i64 %x, i64 %y, i64* %p) {
102; CHECK-LABEL: @usubo_ult_i64_overflow_used(
103; CHECK-NEXT: [[S:%.*]] = sub i64 [[X:%.*]], [[Y:%.*]]
104; CHECK-NEXT: [[OV:%.*]] = icmp ult i64 [[X]], [[Y]]
105; CHECK-NEXT: ret i1 [[OV]]
106;
107 %s = sub i64 %x, %y
108 %ov = icmp ult i64 %x, %y
109 ret i1 %ov
110}
111
112define i1 @usubo_ult_i64_math_overflow_used(i64 %x, i64 %y, i64* %p) {
113; CHECK-LABEL: @usubo_ult_i64_math_overflow_used(
114; CHECK-NEXT: [[S:%.*]] = sub i64 [[X:%.*]], [[Y:%.*]]
115; CHECK-NEXT: store i64 [[S]], i64* [[P:%.*]]
116; CHECK-NEXT: [[OV:%.*]] = icmp ult i64 [[X]], [[Y]]
117; CHECK-NEXT: ret i1 [[OV]]
118;
119 %s = sub i64 %x, %y
120 store i64 %s, i64* %p
121 %ov = icmp ult i64 %x, %y
122 ret i1 %ov
123}
124
125; Check that every instruction inserted by -codegenprepare has a debug location.
126; DEBUG: CheckModuleDebugify: PASS