@@ -216,3 +216,147 @@ define i1 @lshr_add_ule_non_monotonic(i32 %x, i32 %y, i32 %z) {
216216 %cmp = icmp ule i32 %op1 , %op2
217217 ret i1 %cmp
218218}
219+
220+ define i1 @mul_nuw_nonzero_rhs_monotonic (i8 %x , i8 %c ) {
221+ ; CHECK-LABEL: define i1 @mul_nuw_nonzero_rhs_monotonic(
222+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
223+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[C]], 0
224+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
225+ ; CHECK-NEXT: ret i1 true
226+ ;
227+ %c_nonzero = icmp ne i8 %c , 0
228+ call void @llvm.assume (i1 %c_nonzero )
229+
230+ %prod = mul nuw i8 %x , %c
231+ %cmp = icmp uge i8 %prod , %x
232+ ret i1 %cmp
233+ }
234+
235+ define i1 @mul_nuw_nonzero_rhs_commuted_monotonic (i8 %x , i8 %c ) {
236+ ; CHECK-LABEL: define i1 @mul_nuw_nonzero_rhs_commuted_monotonic(
237+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
238+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[C]], 0
239+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
240+ ; CHECK-NEXT: ret i1 true
241+ ;
242+ %c_nonzero = icmp ne i8 %c , 0
243+ call void @llvm.assume (i1 %c_nonzero )
244+
245+ %prod = mul nuw i8 %c , %x
246+ %cmp = icmp uge i8 %prod , %x
247+ ret i1 %cmp
248+ }
249+
250+ define i1 @mul_nuw_nonzero_rhs_monotonic_inverse_predicate (i8 %x , i8 %c ) {
251+ ; CHECK-LABEL: define i1 @mul_nuw_nonzero_rhs_monotonic_inverse_predicate(
252+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
253+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[C]], 0
254+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
255+ ; CHECK-NEXT: ret i1 false
256+ ;
257+ %c_nonzero = icmp ne i8 %c , 0
258+ call void @llvm.assume (i1 %c_nonzero )
259+
260+ %prod = mul nuw i8 %x , %c
261+ %cmp = icmp ult i8 %prod , %x
262+ ret i1 %cmp
263+ }
264+
265+ define i1 @mul_nuw_nonzero_lhs_monotonic (i8 %x , i8 %c ) {
266+ ; CHECK-LABEL: define i1 @mul_nuw_nonzero_lhs_monotonic(
267+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
268+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[X]], 0
269+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
270+ ; CHECK-NEXT: ret i1 true
271+ ;
272+ %c_nonzero = icmp ne i8 %x , 0
273+ call void @llvm.assume (i1 %c_nonzero )
274+
275+ %prod = mul nuw i8 %x , %c
276+ %cmp = icmp uge i8 %prod , %c
277+ ret i1 %cmp
278+ }
279+
280+ define i1 @mul_nuw_nonzero_lhs_rhs_monotonic (i8 %x , i8 %c ) {
281+ ; CHECK-LABEL: define i1 @mul_nuw_nonzero_lhs_rhs_monotonic(
282+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
283+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[C]], 0
284+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
285+ ; CHECK-NEXT: [[X_NONZERO:%.*]] = icmp ne i8 [[X]], 0
286+ ; CHECK-NEXT: call void @llvm.assume(i1 [[X_NONZERO]])
287+ ; CHECK-NEXT: ret i1 true
288+ ;
289+ %c_nonzero = icmp ne i8 %c , 0
290+ call void @llvm.assume (i1 %c_nonzero )
291+
292+ %x_nonzero = icmp ne i8 %x , 0
293+ call void @llvm.assume (i1 %x_nonzero )
294+
295+ %prod = mul nuw i8 %x , %c
296+ %cmp = icmp uge i8 %prod , %x
297+ ret i1 %cmp
298+ }
299+
300+
301+ define i1 @negative_mul_non_nsw (i8 %x , i8 %c ) {
302+ ; CHECK-LABEL: define i1 @negative_mul_non_nsw(
303+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
304+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[C]], 0
305+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
306+ ; CHECK-NEXT: [[X3:%.*]] = mul i8 [[X]], [[C]]
307+ ; CHECK-NEXT: [[CMP:%.*]] = icmp uge i8 [[X3]], [[X]]
308+ ; CHECK-NEXT: ret i1 [[CMP]]
309+ ;
310+ %c_nonzero = icmp ne i8 %c , 0
311+ call void @llvm.assume (i1 %c_nonzero )
312+
313+ %prod = mul i8 %x , %c
314+ %cmp = icmp uge i8 %prod , %x
315+ ret i1 %cmp
316+ }
317+
318+ define i1 @negative_mul_no_nonzero (i8 %x , i8 %c ) {
319+ ; CHECK-LABEL: define i1 @negative_mul_no_nonzero(
320+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
321+ ; CHECK-NEXT: [[X3:%.*]] = mul nsw i8 [[X]], [[C]]
322+ ; CHECK-NEXT: [[CMP:%.*]] = icmp uge i8 [[X3]], [[X]]
323+ ; CHECK-NEXT: ret i1 [[CMP]]
324+ ;
325+ %prod = mul nsw i8 %x , %c
326+ %cmp = icmp uge i8 %prod , %x
327+ ret i1 %cmp
328+ }
329+
330+ define i1 @negative_mul_lhs_maybe_zero (i8 %x , i8 %c ) {
331+ ; CHECK-LABEL: define i1 @negative_mul_lhs_maybe_zero(
332+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
333+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[C]], 0
334+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
335+ ; CHECK-NEXT: [[X3:%.*]] = mul nuw i8 [[X]], [[C]]
336+ ; CHECK-NEXT: [[CMP:%.*]] = icmp uge i8 [[X3]], [[C]]
337+ ; CHECK-NEXT: ret i1 [[CMP]]
338+ ;
339+ %c_nonzero = icmp ne i8 %c , 0
340+ call void @llvm.assume (i1 %c_nonzero )
341+
342+ %prod = mul nuw i8 %x , %c
343+ %cmp = icmp uge i8 %prod , %c
344+ ret i1 %cmp
345+ }
346+
347+ define i1 @negative_mul_rhs_maybe_zero (i8 %x , i8 %c ) {
348+ ; CHECK-LABEL: define i1 @negative_mul_rhs_maybe_zero(
349+ ; CHECK-SAME: i8 [[X:%.*]], i8 [[C:%.*]]) {
350+ ; CHECK-NEXT: [[C_NONZERO:%.*]] = icmp ne i8 [[X]], 0
351+ ; CHECK-NEXT: call void @llvm.assume(i1 [[C_NONZERO]])
352+ ; CHECK-NEXT: [[X3:%.*]] = mul nuw i8 [[X]], [[C]]
353+ ; CHECK-NEXT: [[CMP:%.*]] = icmp uge i8 [[X3]], [[X]]
354+ ; CHECK-NEXT: ret i1 [[CMP]]
355+ ;
356+ %c_nonzero = icmp ne i8 %x , 0
357+ call void @llvm.assume (i1 %c_nonzero )
358+
359+ %prod = mul nuw i8 %x , %c
360+ %cmp = icmp uge i8 %prod , %x
361+ ret i1 %cmp
362+ }
0 commit comments