Run DCE after a LoopFlatten test to reduce spurious output [nfc]
[llvm-project.git] / clang / test / CodeGen / ext-int-sanitizer.cpp
blob85ae26c72f45f55cddfa8271580665cea0e6e57c
1 // RUN: %clang_cc1 -triple x86_64-gnu-linux -fsanitize=array-bounds,enum,float-cast-overflow,integer-divide-by-zero,implicit-unsigned-integer-truncation,implicit-signed-integer-truncation,implicit-integer-sign-change,unsigned-integer-overflow,signed-integer-overflow,shift-base,shift-exponent -O3 -disable-llvm-passes -emit-llvm -o - %s | FileCheck %s
4 // CHECK: define{{.*}} void @_Z6BoundsRA10_KiDB15_
5 void Bounds(const int (&Array)[10], _BitInt(15) Index) {
6 int I1 = Array[Index];
7 // CHECK: %[[SEXT:.+]] = sext i15 %{{.+}} to i64
8 // CHECK: %[[CMP:.+]] = icmp ult i64 %[[SEXT]], 10
9 // CHECK: br i1 %[[CMP]]
10 // CHECK: call void @__ubsan_handle_out_of_bounds
13 // CHECK: define{{.*}} void @_Z4Enumv
14 void Enum() {
15 enum E1 { e1a = 0, e1b = 127 }
16 e1;
17 enum E2 { e2a = -1, e2b = 64 }
18 e2;
19 enum E3 { e3a = (1u << 31) - 1 }
20 e3;
22 _BitInt(34) a = e1;
23 // CHECK: %[[E1:.+]] = icmp ule i32 %{{.*}}, 127
24 // CHECK: br i1 %[[E1]]
25 // CHECK: call void @__ubsan_handle_load_invalid_value_abort
26 _BitInt(34) b = e2;
27 // CHECK: %[[E2HI:.*]] = icmp sle i32 {{.*}}, 127
28 // CHECK: %[[E2LO:.*]] = icmp sge i32 {{.*}}, -128
29 // CHECK: %[[E2:.*]] = and i1 %[[E2HI]], %[[E2LO]]
30 // CHECK: br i1 %[[E2]]
31 // CHECK: call void @__ubsan_handle_load_invalid_value_abort
32 _BitInt(34) c = e3;
33 // CHECK: %[[E3:.*]] = icmp ule i32 {{.*}}, 2147483647
34 // CHECK: br i1 %[[E3]]
35 // CHECK: call void @__ubsan_handle_load_invalid_value_abort
38 // CHECK: define{{.*}} void @_Z13FloatOverflowfd
39 void FloatOverflow(float f, double d) {
40 _BitInt(10) E = f;
41 // CHECK: fcmp ogt float %{{.+}}, -5.130000e+02
42 // CHECK: fcmp olt float %{{.+}}, 5.120000e+02
43 _BitInt(10) E2 = d;
44 // CHECK: fcmp ogt double %{{.+}}, -5.130000e+02
45 // CHECK: fcmp olt double %{{.+}}, 5.120000e+02
46 _BitInt(7) E3 = f;
47 // CHECK: fcmp ogt float %{{.+}}, -6.500000e+01
48 // CHECK: fcmp olt float %{{.+}}, 6.400000e+01
49 _BitInt(7) E4 = d;
50 // CHECK: fcmp ogt double %{{.+}}, -6.500000e+01
51 // CHECK: fcmp olt double %{{.+}}, 6.400000e+01
54 // CHECK: define{{.*}} void @_Z14UIntTruncationDU35_jy
55 void UIntTruncation(unsigned _BitInt(35) E, unsigned int i, unsigned long long ll) {
57 i = E;
58 // CHECK: %[[LOADE:.+]] = load i35
59 // CHECK: store i35 %[[LOADE]], ptr %[[EADDR:.+]]
60 // CHECK: %[[LOADE2:.+]] = load i35, ptr %[[EADDR]]
61 // CHECK: %[[CONV:.+]] = trunc i35 %[[LOADE2]] to i32
62 // CHECK: %[[EXT:.+]] = zext i32 %[[CONV]] to i35
63 // CHECK: %[[CHECK:.+]] = icmp eq i35 %[[EXT]], %[[LOADE2]]
64 // CHECK: br i1 %[[CHECK]]
65 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
67 E = ll;
68 // CHECK: %[[LOADLL:.+]] = load i64
69 // CHECK: %[[CONV:.+]] = trunc i64 %[[LOADLL]] to i35
70 // CHECK: %[[EXT:.+]] = zext i35 %[[CONV]] to i64
71 // CHECK: %[[CHECK:.+]] = icmp eq i64 %[[EXT]], %[[LOADLL]]
72 // CHECK: br i1 %[[CHECK]]
73 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
76 // CHECK: define{{.*}} void @_Z13IntTruncationDB35_DU42_ij
77 void IntTruncation(_BitInt(35) E, unsigned _BitInt(42) UE, int i, unsigned j) {
79 j = E;
80 // CHECK: %[[LOADE:.+]] = load i35
81 // CHECK: store i35 %[[LOADE]], ptr %[[EADDR:.+]]
82 // CHECK: %[[LOADE2:.+]] = load i35, ptr %[[EADDR]]
83 // CHECK: %[[CONV:.+]] = trunc i35 %[[LOADE2]] to i32
84 // CHECK: %[[EXT:.+]] = zext i32 %[[CONV]] to i35
85 // CHECK: %[[CHECK:.+]] = icmp eq i35 %[[EXT]], %[[LOADE2]]
86 // CHECK: br i1 %[[CHECK]]
87 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
89 j = UE;
90 // CHECK: %[[LOADUE:.+]] = load i42
91 // CHECK: %[[CONV:.+]] = trunc i42 %[[LOADUE]] to i32
92 // CHECK: %[[EXT:.+]] = zext i32 %[[CONV]] to i42
93 // CHECK: %[[CHECK:.+]] = icmp eq i42 %[[EXT]], %[[LOADUE]]
94 // CHECK: br i1 %[[CHECK]]
95 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
97 // Note: also triggers sign change check.
98 i = UE;
99 // CHECK: %[[LOADUE:.+]] = load i42
100 // CHECK: %[[CONV:.+]] = trunc i42 %[[LOADUE]] to i32
101 // CHECK: %[[NEG:.+]] = icmp slt i32 %[[CONV]], 0
102 // CHECK: %[[SIGNCHECK:.+]] = icmp eq i1 false, %[[NEG]]
103 // CHECK: %[[EXT:.+]] = sext i32 %[[CONV]] to i42
104 // CHECK: %[[CHECK:.+]] = icmp eq i42 %[[EXT]], %[[LOADUE]]
105 // CHECK: %[[CHECKBOTH:.+]] = and i1 %[[SIGNCHECK]], %[[CHECK]]
106 // CHECK: br i1 %[[CHECKBOTH]]
107 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
109 // Note: also triggers sign change check.
110 E = UE;
111 // CHECK: %[[LOADUE:.+]] = load i42
112 // CHECK: %[[CONV:.+]] = trunc i42 %[[LOADUE]] to i35
113 // CHECK: %[[NEG:.+]] = icmp slt i35 %[[CONV]], 0
114 // CHECK: %[[SIGNCHECK:.+]] = icmp eq i1 false, %[[NEG]]
115 // CHECK: %[[EXT:.+]] = sext i35 %[[CONV]] to i42
116 // CHECK: %[[CHECK:.+]] = icmp eq i42 %[[EXT]], %[[LOADUE]]
117 // CHECK: %[[CHECKBOTH:.+]] = and i1 %[[SIGNCHECK]], %[[CHECK]]
118 // CHECK: br i1 %[[CHECKBOTH]]
119 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
122 // CHECK: define{{.*}} void @_Z15SignChangeCheckDU39_DB39_
123 void SignChangeCheck(unsigned _BitInt(39) UE, _BitInt(39) E) {
124 UE = E;
125 // CHECK: %[[LOADEU:.+]] = load i39
126 // CHECK: %[[LOADE:.+]] = load i39
127 // CHECK: store i39 %[[LOADE]], ptr %[[EADDR:.+]]
128 // CHECK: %[[LOADE2:.+]] = load i39, ptr %[[EADDR]]
129 // CHECK: %[[NEG:.+]] = icmp slt i39 %[[LOADE2]], 0
130 // CHECK: %[[SIGNCHECK:.+]] = icmp eq i1 %[[NEG]], false
131 // CHECK: br i1 %[[SIGNCHECK]]
132 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
134 E = UE;
135 // CHECK: store i39 %[[LOADE2]], ptr %[[UEADDR:.+]]
136 // CHECK: %[[LOADUE2:.+]] = load i39, ptr %[[UEADDR]]
137 // CHECK: %[[NEG:.+]] = icmp slt i39 %[[LOADUE2]], 0
138 // CHECK: %[[SIGNCHECK:.+]] = icmp eq i1 false, %[[NEG]]
139 // CHECK: br i1 %[[SIGNCHECK]]
140 // CHECK: call void @__ubsan_handle_implicit_conversion_abort
143 // CHECK: define{{.*}} void @_Z9DivByZeroDB11_i
144 void DivByZero(_BitInt(11) E, int i) {
146 // Also triggers signed integer overflow.
147 E / E;
148 // CHECK: %[[EADDR:.+]] = alloca i11
149 // CHECK: %[[E:.+]] = load i11, ptr %[[EADDR]]
150 // CHECK: %[[E2:.+]] = load i11, ptr %[[EADDR]]
151 // CHECK: %[[NEZERO:.+]] = icmp ne i11 %[[E2]], 0
152 // CHECK: %[[NEMIN:.+]] = icmp ne i11 %[[E]], -1024
153 // CHECK: %[[NENEG1:.+]] = icmp ne i11 %[[E2]], -1
154 // CHECK: %[[OR:.+]] = or i1 %[[NEMIN]], %[[NENEG1]]
155 // CHECK: %[[AND:.+]] = and i1 %[[NEZERO]], %[[OR]]
156 // CHECK: br i1 %[[AND]]
157 // CHECK: call void @__ubsan_handle_divrem_overflow_abort
160 // TODO:
161 //-fsanitize=shift: (shift-base, shift-exponent) Shift operators where the amount shifted is greater or equal to the promoted bit-width of the left hand side or less than zero, or where the left hand side is negative. For a signed left shift, also checks for signed overflow in C, and for unsigned overflow in C++. You can use -fsanitize=shift-base or -fsanitize=shift-exponent to check only left-hand side or right-hand side of shift operation, respectively.
162 // CHECK: define{{.*}} void @_Z6ShiftsDB9_
163 void Shifts(_BitInt(9) E) {
164 E >> E;
165 // CHECK: %[[EADDR:.+]] = alloca i9
166 // CHECK: %[[LHSE:.+]] = load i9, ptr %[[EADDR]]
167 // CHECK: %[[RHSE:.+]] = load i9, ptr %[[EADDR]]
168 // CHECK: %[[CMP:.+]] = icmp ule i9 %[[RHSE]], 8
169 // CHECK: br i1 %[[CMP]]
170 // CHECK: call void @__ubsan_handle_shift_out_of_bounds_abort
172 E << E;
173 // CHECK: %[[LHSE:.+]] = load i9, ptr
174 // CHECK: %[[RHSE:.+]] = load i9, ptr
175 // CHECK: %[[CMP:.+]] = icmp ule i9 %[[RHSE]], 8
176 // CHECK: br i1 %[[CMP]]
177 // CHECK: %[[ZEROS:.+]] = sub nuw nsw i9 8, %[[RHSE]]
178 // CHECK: %[[CHECK:.+]] = lshr i9 %[[LHSE]], %[[ZEROS]]
179 // CHECK: %[[SKIPSIGN:.+]] = lshr i9 %[[CHECK]], 1
180 // CHECK: %[[CHECK:.+]] = icmp eq i9 %[[SKIPSIGN]]
181 // CHECK: %[[PHI:.+]] = phi i1 [ true, %{{.+}} ], [ %[[CHECK]], %{{.+}} ]
182 // CHECK: and i1 %[[CMP]], %[[PHI]]
183 // CHECK: call void @__ubsan_handle_shift_out_of_bounds_abort
186 // CHECK: define{{.*}} void @_Z21SignedIntegerOverflowDB93_DB4_DB31_
187 void SignedIntegerOverflow(_BitInt(93) BiggestE,
188 _BitInt(4) SmallestE,
189 _BitInt(31) JustRightE) {
190 BiggestE + BiggestE;
191 // CHECK: %[[LOADBIGGESTE2:.+]] = load i93
192 // CHECK: store i93 %[[LOADBIGGESTE2]], ptr %[[BIGGESTEADDR:.+]]
193 // CHECK: %[[LOAD1:.+]] = load i93, ptr %[[BIGGESTEADDR]]
194 // CHECK: %[[LOAD2:.+]] = load i93, ptr %[[BIGGESTEADDR]]
195 // CHECK: %[[OFCALL:.+]] = call { i93, i1 } @llvm.sadd.with.overflow.i93(i93 %[[LOAD1]], i93 %[[LOAD2]])
196 // CHECK: %[[EXRESULT:.+]] = extractvalue { i93, i1 } %[[OFCALL]], 0
197 // CHECK: %[[OFRESULT:.+]] = extractvalue { i93, i1 } %[[OFCALL]], 1
198 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
199 // CHECK: br i1 %[[CHECK]]
200 // CHECK: call void @__ubsan_handle_add_overflow_abort
202 SmallestE - SmallestE;
203 // CHECK: %[[LOAD1:.+]] = load i4, ptr
204 // CHECK: %[[LOAD2:.+]] = load i4, ptr
205 // CHECK: %[[OFCALL:.+]] = call { i4, i1 } @llvm.ssub.with.overflow.i4(i4 %[[LOAD1]], i4 %[[LOAD2]])
206 // CHECK: %[[EXRESULT:.+]] = extractvalue { i4, i1 } %[[OFCALL]], 0
207 // CHECK: %[[OFRESULT:.+]] = extractvalue { i4, i1 } %[[OFCALL]], 1
208 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
209 // CHECK: br i1 %[[CHECK]]
210 // CHECK: call void @__ubsan_handle_sub_overflow_abort
212 JustRightE * JustRightE;
213 // CHECK: %[[LOAD1:.+]] = load i31, ptr
214 // CHECK: %[[LOAD2:.+]] = load i31, ptr
215 // CHECK: %[[OFCALL:.+]] = call { i31, i1 } @llvm.smul.with.overflow.i31(i31 %[[LOAD1]], i31 %[[LOAD2]])
216 // CHECK: %[[EXRESULT:.+]] = extractvalue { i31, i1 } %[[OFCALL]], 0
217 // CHECK: %[[OFRESULT:.+]] = extractvalue { i31, i1 } %[[OFCALL]], 1
218 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
219 // CHECK: br i1 %[[CHECK]]
220 // CHECK: call void @__ubsan_handle_mul_overflow_abort
223 // CHECK: define{{.*}} void @_Z23UnsignedIntegerOverflowjDU23_DU35_
224 void UnsignedIntegerOverflow(unsigned u,
225 unsigned _BitInt(23) SmallE,
226 unsigned _BitInt(35) BigE) {
227 u = SmallE + SmallE;
228 // CHECK: %[[BIGGESTEADDR:.+]] = alloca i23
229 // CHECK: %[[LOADE1:.+]] = load i23, ptr %[[BIGGESTEADDR]]
230 // CHECK: %[[LOADE2:.+]] = load i23, ptr %[[BIGGESTEADDR]]
231 // CHECK: %[[OFCALL:.+]] = call { i23, i1 } @llvm.uadd.with.overflow.i23(i23 %[[LOADE1]], i23 %[[LOADE2]])
232 // CHECK: %[[EXRESULT:.+]] = extractvalue { i23, i1 } %[[OFCALL]], 0
233 // CHECK: %[[OFRESULT:.+]] = extractvalue { i23, i1 } %[[OFCALL]], 1
234 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
235 // CHECK: br i1 %[[CHECK]]
236 // CHECK: call void @__ubsan_handle_add_overflow_abort
238 SmallE = u + u;
239 // CHECK: %[[LOADU1:.+]] = load i32, ptr
240 // CHECK: %[[LOADU2:.+]] = load i32, ptr
241 // CHECK: %[[OFCALL:.+]] = call { i32, i1 } @llvm.uadd.with.overflow.i32(i32 %[[LOADU1]], i32 %[[LOADU2]])
242 // CHECK: %[[EXRESULT:.+]] = extractvalue { i32, i1 } %[[OFCALL]], 0
243 // CHECK: %[[OFRESULT:.+]] = extractvalue { i32, i1 } %[[OFCALL]], 1
244 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
245 // CHECK: br i1 %[[CHECK]]
246 // CHECK: call void @__ubsan_handle_add_overflow_abort
248 SmallE = SmallE + SmallE;
249 // CHECK: %[[LOADE1:.+]] = load i23, ptr
250 // CHECK: %[[LOADE2:.+]] = load i23, ptr
251 // CHECK: %[[OFCALL:.+]] = call { i23, i1 } @llvm.uadd.with.overflow.i23(i23 %[[LOADE1]], i23 %[[LOADE2]])
252 // CHECK: %[[EXRESULT:.+]] = extractvalue { i23, i1 } %[[OFCALL]], 0
253 // CHECK: %[[OFRESULT:.+]] = extractvalue { i23, i1 } %[[OFCALL]], 1
254 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
255 // CHECK: br i1 %[[CHECK]]
256 // CHECK: call void @__ubsan_handle_add_overflow_abort
258 SmallE = BigE + BigE;
259 // CHECK: %[[LOADE1:.+]] = load i35, ptr
260 // CHECK: %[[LOADE2:.+]] = load i35, ptr
261 // CHECK: %[[OFCALL:.+]] = call { i35, i1 } @llvm.uadd.with.overflow.i35(i35 %[[LOADE1]], i35 %[[LOADE2]])
262 // CHECK: %[[EXRESULT:.+]] = extractvalue { i35, i1 } %[[OFCALL]], 0
263 // CHECK: %[[OFRESULT:.+]] = extractvalue { i35, i1 } %[[OFCALL]], 1
264 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
265 // CHECK: br i1 %[[CHECK]]
266 // CHECK: call void @__ubsan_handle_add_overflow_abort
268 BigE = BigE + BigE;
269 // CHECK: %[[LOADE1:.+]] = load i35, ptr
270 // CHECK: %[[LOADE2:.+]] = load i35, ptr
271 // CHECK: %[[OFCALL:.+]] = call { i35, i1 } @llvm.uadd.with.overflow.i35(i35 %[[LOADE1]], i35 %[[LOADE2]])
272 // CHECK: %[[EXRESULT:.+]] = extractvalue { i35, i1 } %[[OFCALL]], 0
273 // CHECK: %[[OFRESULT:.+]] = extractvalue { i35, i1 } %[[OFCALL]], 1
274 // CHECK: %[[CHECK:.+]] = xor i1 %[[OFRESULT]], true
275 // CHECK: br i1 %[[CHECK]]
276 // CHECK: call void @__ubsan_handle_add_overflow_abort