; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 5 ; RUN: opt < %s -passes=instcombine -S | FileCheck %s declare void @use(i8) define i1 @fold_sext_to_and(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = and i8 [[X]], -127 ; CHECK-NEXT: [[TMP3:%.*]] = icmp eq i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 %2 = and i32 %1, -2147483647 %3 = icmp eq i32 %2, 1 ret i1 %3 } define i1 @fold_sext_to_and1(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and1( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = and i8 [[X]], -127 ; CHECK-NEXT: [[TMP3:%.*]] = icmp ne i8 [[TMP1]], 1 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 %2 = and i32 %1, -2147483647 %3 = icmp ne i32 %2, 1 ret i1 %3 } define i1 @fold_sext_to_and2(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and2( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = and i8 [[X]], -126 ; CHECK-NEXT: [[TMP3:%.*]] = icmp eq i8 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 %2 = and i32 %1, 1073741826 %3 = icmp eq i32 %2, 2 ret i1 %3 } define i1 @fold_sext_to_and3(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and3( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = and i8 [[X]], -126 ; CHECK-NEXT: [[TMP3:%.*]] = icmp ne i8 [[TMP1]], 2 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 %2 = and i32 %1, 1073741826 %3 = icmp ne i32 %2, 2 ret i1 %3 } define i1 @fold_sext_to_and_multi_use(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_multi_use( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = sext i8 [[X]] to i32 ; CHECK-NEXT: call void @use(i32 [[TMP1]]) ; CHECK-NEXT: [[TMP2:%.*]] = and i8 [[X]], -127 ; CHECK-NEXT: [[TMP3:%.*]] = icmp eq i8 [[TMP2]], 1 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 call void @use(i32 %1) %2 = and i32 %1, -2147483647 %3 = icmp eq i32 %2, 1 ret i1 %3 } define i1 @fold_sext_to_and_multi_use1(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_multi_use1( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = sext i8 [[X]] to i32 ; CHECK-NEXT: call void @use(i32 [[TMP1]]) ; CHECK-NEXT: [[TMP2:%.*]] = and i8 [[X]], -127 ; CHECK-NEXT: [[TMP3:%.*]] = icmp ne i8 [[TMP2]], 1 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 call void @use(i32 %1) %2 = and i32 %1, -2147483647 %3 = icmp ne i32 %2, 1 ret i1 %3 } define i1 @fold_sext_to_and_multi_use2(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_multi_use2( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = sext i8 [[X]] to i32 ; CHECK-NEXT: call void @use(i32 [[TMP1]]) ; CHECK-NEXT: [[TMP2:%.*]] = and i8 [[X]], -126 ; CHECK-NEXT: [[TMP3:%.*]] = icmp eq i8 [[TMP2]], 2 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 call void @use(i32 %1) %2 = and i32 %1, 1073741826 %3 = icmp eq i32 %2, 2 ret i1 %3 } define i1 @fold_sext_to_and_multi_use3(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_multi_use3( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: [[TMP1:%.*]] = sext i8 [[X]] to i32 ; CHECK-NEXT: call void @use(i32 [[TMP1]]) ; CHECK-NEXT: [[TMP2:%.*]] = and i8 [[X]], -126 ; CHECK-NEXT: [[TMP3:%.*]] = icmp ne i8 [[TMP2]], 2 ; CHECK-NEXT: ret i1 [[TMP3]] ; %1 = sext i8 %x to i32 call void @use(i32 %1) %2 = and i32 %1, 1073741826 %3 = icmp ne i32 %2, 2 ret i1 %3 } ; Negative tests define i1 @fold_sext_to_and_wrong(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 false ; %1 = sext i8 %x to i32 %2 = and i32 %1, -2147483647 %3 = icmp eq i32 %2, -1 ret i1 %3 } define i1 @fold_sext_to_and_wrong2(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong2( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 false ; %1 = sext i8 %x to i32 %2 = and i32 %1, -2147483647 %3 = icmp eq i32 %2, 128 ret i1 %3 } define i1 @fold_sext_to_and_wrong3(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong3( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 false ; %1 = sext i8 %x to i32 %2 = and i32 %1, 128 %3 = icmp eq i32 %2, -2147483648 ret i1 %3 } define i1 @fold_sext_to_and_wrong4(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong4( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 false ; %1 = sext i8 %x to i32 %2 = and i32 %1, 128 %3 = icmp eq i32 %2, 1 ret i1 %3 } define i1 @fold_sext_to_and_wrong5(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong5( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 false ; %1 = sext i8 %x to i32 %2 = and i32 %1, -256 %3 = icmp eq i32 %2, 1 ret i1 %3 } define i1 @fold_sext_to_and_wrong6(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong6( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 true ; %1 = sext i8 %x to i32 %2 = and i32 %1, -2147483647 %3 = icmp ne i32 %2, -1 ret i1 %3 } define i1 @fold_sext_to_and_wrong7(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong7( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 true ; %1 = sext i8 %x to i32 %2 = and i32 %1, -2147483647 %3 = icmp ne i32 %2, 128 ret i1 %3 } define i1 @fold_sext_to_and_wrong8(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong8( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 true ; %1 = sext i8 %x to i32 %2 = and i32 %1, 128 %3 = icmp ne i32 %2, -2147483648 ret i1 %3 } define i1 @fold_sext_to_and_wrong9(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong9( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 true ; %1 = sext i8 %x to i32 %2 = and i32 %1, 128 %3 = icmp ne i32 %2, 1 ret i1 %3 } define i1 @fold_sext_to_and_wrong10(i8 %x) { ; CHECK-LABEL: define i1 @fold_sext_to_and_wrong10( ; CHECK-SAME: i8 [[X:%.*]]) { ; CHECK-NEXT: ret i1 true ; %1 = sext i8 %x to i32 %2 = and i32 %1, -256 %3 = icmp ne i32 %2, 1 ret i1 %3 }