brintos

brintos / llvm-project-archived public Read only

0
0
Text · 28.6 KiB · bb0d38a Raw
991 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py2; RUN: llc -mtriple=aarch64-none-elf < %s | FileCheck %s --check-prefixes=CHECK,CHECK-SD3; RUN: llc -mtriple=aarch64-none-elf -global-isel < %s | FileCheck %s --check-prefixes=CHECK,CHECK-GI4 5; Add pure 12-bit immediates:6define i32 @add_small_i32(i32 %val32) {7; CHECK-LABEL: add_small_i32:8; CHECK:       // %bb.0:9; CHECK-NEXT:    add w0, w0, #409510; CHECK-NEXT:    ret11  %newval32 = add i32 %val32, 409512  ret i32 %newval3213}14 15define i64 @add_small_i64(i64 %val64) {16; CHECK-LABEL: add_small_i64:17; CHECK:       // %bb.0:18; CHECK-NEXT:    add x0, x0, #5219; CHECK-NEXT:    ret20  %newval64 = add i64 %val64, 5221  ret i64 %newval6422}23 24define void @add_small_imm(ptr %p, ptr %q, i32 %b, ptr %addr) {25; CHECK-LABEL: add_small_imm:26; CHECK:       // %bb.0: // %entry27; CHECK-NEXT:    ldrb w8, [x0]28; CHECK-NEXT:    add w9, w8, w229; CHECK-NEXT:    add x8, x8, #1230; CHECK-NEXT:    str w9, [x3]31; CHECK-NEXT:    str x8, [x1]32; CHECK-NEXT:    ret33entry:34  %t = load i8, ptr %p35  %promoted = zext i8 %t to i6436  %zextt = zext i8 %t to i3237  %add = add nuw i32 %zextt, %b38  %add2 = add nuw i64 %promoted, 1239  store i32 %add, ptr %addr40  store i64 %add2, ptr %q41  ret void42}43 44; Add 12-bit immediates, shifted left by 12 bits45define i32 @add_med_i32(i32 %val32) {46; CHECK-LABEL: add_med_i32:47; CHECK:       // %bb.0:48; CHECK-NEXT:    add w0, w0, #3567, lsl #12 // =1461043249; CHECK-NEXT:    ret50  %newval32 = add i32 %val32, 14610432 ; =0xdef00051  ret i32 %newval3252}53 54define i64 @add_med_i64(i64 %val64) {55; CHECK-LABEL: add_med_i64:56; CHECK:       // %bb.0:57; CHECK-NEXT:    add x0, x0, #4095, lsl #12 // =1677312058; CHECK-NEXT:    ret59  %newval64 = add i64 %val64, 16773120 ; =0xfff00060  ret i64 %newval6461}62 63; Subtract 12-bit immediates64define i32 @sub_small_i32(i32 %val32) {65; CHECK-LABEL: sub_small_i32:66; CHECK:       // %bb.0:67; CHECK-NEXT:    sub w0, w0, #409568; CHECK-NEXT:    ret69  %newval32 = sub i32 %val32, 409570  ret i32 %newval3271}72 73define i64 @sub_small_i64(i64 %val64) {74; CHECK-LABEL: sub_small_i64:75; CHECK:       // %bb.0:76; CHECK-NEXT:    sub x0, x0, #5277; CHECK-NEXT:    ret78  %newval64 = sub i64 %val64, 5279  ret i64 %newval6480}81 82; Subtract 12-bit immediates, shifted left by 12 bits83define i32 @sub_med_i32(i32 %val32) {84; CHECK-LABEL: sub_med_i32:85; CHECK:       // %bb.0:86; CHECK-NEXT:    sub w0, w0, #3567, lsl #12 // =1461043287; CHECK-NEXT:    ret88  %newval32 = sub i32 %val32, 14610432 ; =0xdef00089  ret i32 %newval3290}91 92define i64 @sub_med_i64(i64 %val64) {93; CHECK-LABEL: sub_med_i64:94; CHECK:       // %bb.0:95; CHECK-NEXT:    sub x0, x0, #4095, lsl #12 // =1677312096; CHECK-NEXT:    ret97  %newval64 = sub i64 %val64, 16773120 ; =0xfff00098  ret i64 %newval6499}100 101define i64 @add_two_parts_imm_i64(i64 %a) {102; CHECK-LABEL: add_two_parts_imm_i64:103; CHECK:       // %bb.0:104; CHECK-NEXT:    add x8, x0, #2730, lsl #12 // =11182080105; CHECK-NEXT:    add x0, x8, #1365106; CHECK-NEXT:    ret107  %b = add i64 %a, 11183445108  ret i64 %b109}110 111define i32 @add_two_parts_imm_i32(i32 %a) {112; CHECK-LABEL: add_two_parts_imm_i32:113; CHECK:       // %bb.0:114; CHECK-NEXT:    add w8, w0, #2730, lsl #12 // =11182080115; CHECK-NEXT:    add w0, w8, #1365116; CHECK-NEXT:    ret117  %b = add i32 %a, 11183445118  ret i32 %b119}120 121define i64 @add_two_parts_imm_i64_neg(i64 %a) {122; CHECK-LABEL: add_two_parts_imm_i64_neg:123; CHECK:       // %bb.0:124; CHECK-NEXT:    sub x8, x0, #2730, lsl #12 // =11182080125; CHECK-NEXT:    sub x0, x8, #1365126; CHECK-NEXT:    ret127  %b = add i64 %a, -11183445128  ret i64 %b129}130 131define i32 @add_two_parts_imm_i32_neg(i32 %a) {132; CHECK-LABEL: add_two_parts_imm_i32_neg:133; CHECK:       // %bb.0:134; CHECK-NEXT:    sub w8, w0, #2730, lsl #12 // =11182080135; CHECK-NEXT:    sub w0, w8, #1365136; CHECK-NEXT:    ret137  %b = add i32 %a, -11183445138  ret i32 %b139}140 141define i64 @sub_two_parts_imm_i64(i64 %a) {142; CHECK-LABEL: sub_two_parts_imm_i64:143; CHECK:       // %bb.0:144; CHECK-NEXT:    sub x8, x0, #2730, lsl #12 // =11182080145; CHECK-NEXT:    sub x0, x8, #1365146; CHECK-NEXT:    ret147  %b = sub i64 %a, 11183445148  ret i64 %b149}150 151define i32 @sub_two_parts_imm_i32(i32 %a) {152; CHECK-LABEL: sub_two_parts_imm_i32:153; CHECK:       // %bb.0:154; CHECK-NEXT:    sub w8, w0, #2730, lsl #12 // =11182080155; CHECK-NEXT:    sub w0, w8, #1365156; CHECK-NEXT:    ret157  %b = sub i32 %a, 11183445158  ret i32 %b159}160 161define i64 @sub_two_parts_imm_i64_neg(i64 %a) {162; CHECK-LABEL: sub_two_parts_imm_i64_neg:163; CHECK:       // %bb.0:164; CHECK-NEXT:    add x8, x0, #2730, lsl #12 // =11182080165; CHECK-NEXT:    add x0, x8, #1365166; CHECK-NEXT:    ret167  %b = sub i64 %a, -11183445168  ret i64 %b169}170 171define i32 @sub_two_parts_imm_i32_neg(i32 %a) {172; CHECK-LABEL: sub_two_parts_imm_i32_neg:173; CHECK:       // %bb.0:174; CHECK-NEXT:    add w8, w0, #2730, lsl #12 // =11182080175; CHECK-NEXT:    add w0, w8, #1365176; CHECK-NEXT:    ret177  %b = sub i32 %a, -11183445178  ret i32 %b179}180 181define i32 @add_27962026(i32 %a) {182; CHECK-LABEL: add_27962026:183; CHECK:       // %bb.0:184; CHECK-NEXT:    mov w8, #43690 // =0xaaaa185; CHECK-NEXT:    movk w8, #426, lsl #16186; CHECK-NEXT:    add w0, w0, w8187; CHECK-NEXT:    ret188  %b = add i32 %a, 27962026189  ret i32 %b190}191 192define i32 @add_65534(i32 %a) {193; CHECK-LABEL: add_65534:194; CHECK:       // %bb.0:195; CHECK-NEXT:    mov w8, #65534 // =0xfffe196; CHECK-NEXT:    add w0, w0, w8197; CHECK-NEXT:    ret198  %b = add i32 %a, 65534199  ret i32 %b200}201 202declare i32 @foox(i32)203 204define void @add_in_loop(i32 %0) {205; CHECK-LABEL: add_in_loop:206; CHECK:       // %bb.0:207; CHECK-NEXT:    stp x30, x19, [sp, #-16]! // 16-byte Folded Spill208; CHECK-NEXT:    .cfi_def_cfa_offset 16209; CHECK-NEXT:    .cfi_offset w19, -8210; CHECK-NEXT:    .cfi_offset w30, -16211; CHECK-NEXT:    mov w19, #43690 // =0xaaaa212; CHECK-NEXT:    movk w19, #170, lsl #16213; CHECK-NEXT:  .LBB19_1: // =>This Inner Loop Header: Depth=1214; CHECK-NEXT:    add w0, w0, w19215; CHECK-NEXT:    bl foox216; CHECK-NEXT:    b .LBB19_1217  br label %22182:219  %3 = phi i32 [ %0, %1 ], [ %5, %2 ]220  %4 = add nsw i32 %3, 11184810221  %5 = tail call i32 @foox(i32 %4) #2222  br label %2223}224 225define void @testing(ptr %var_i32, ptr %var2_i32) {226; CHECK-SD-LABEL: testing:227; CHECK-SD:       // %bb.0:228; CHECK-SD-NEXT:    ldr w8, [x0]229; CHECK-SD-NEXT:    cmp w8, #4095230; CHECK-SD-NEXT:    b.ne .LBB20_6231; CHECK-SD-NEXT:  // %bb.1: // %test2232; CHECK-SD-NEXT:    ldr w9, [x1]233; CHECK-SD-NEXT:    add w10, w8, #1234; CHECK-SD-NEXT:    str w10, [x0]235; CHECK-SD-NEXT:    cmp w9, #3567, lsl #12 // =14610432236; CHECK-SD-NEXT:    b.lo .LBB20_6237; CHECK-SD-NEXT:  // %bb.2: // %test3238; CHECK-SD-NEXT:    add w10, w8, #2239; CHECK-SD-NEXT:    cmp w8, #123240; CHECK-SD-NEXT:    str w10, [x0]241; CHECK-SD-NEXT:    b.lt .LBB20_6242; CHECK-SD-NEXT:  // %bb.3: // %test4243; CHECK-SD-NEXT:    add w10, w8, #3244; CHECK-SD-NEXT:    cmp w9, #321245; CHECK-SD-NEXT:    str w10, [x0]246; CHECK-SD-NEXT:    b.gt .LBB20_6247; CHECK-SD-NEXT:  // %bb.4: // %test5248; CHECK-SD-NEXT:    add w10, w8, #4249; CHECK-SD-NEXT:    cmn w9, #443250; CHECK-SD-NEXT:    str w10, [x0]251; CHECK-SD-NEXT:    b.ge .LBB20_6252; CHECK-SD-NEXT:  // %bb.5: // %test6253; CHECK-SD-NEXT:    add w8, w8, #5254; CHECK-SD-NEXT:    str w8, [x0]255; CHECK-SD-NEXT:  .LBB20_6: // %common.ret256; CHECK-SD-NEXT:    ret257;258; CHECK-GI-LABEL: testing:259; CHECK-GI:       // %bb.0:260; CHECK-GI-NEXT:    ldr w8, [x0]261; CHECK-GI-NEXT:    cmp w8, #4095262; CHECK-GI-NEXT:    b.ne .LBB20_6263; CHECK-GI-NEXT:  // %bb.1: // %test2264; CHECK-GI-NEXT:    ldr w9, [x1]265; CHECK-GI-NEXT:    add w10, w8, #1266; CHECK-GI-NEXT:    str w10, [x0]267; CHECK-GI-NEXT:    cmp w9, #3567, lsl #12 // =14610432268; CHECK-GI-NEXT:    b.lo .LBB20_6269; CHECK-GI-NEXT:  // %bb.2: // %test3270; CHECK-GI-NEXT:    add w10, w8, #2271; CHECK-GI-NEXT:    cmp w8, #123272; CHECK-GI-NEXT:    str w10, [x0]273; CHECK-GI-NEXT:    b.lt .LBB20_6274; CHECK-GI-NEXT:  // %bb.3: // %test4275; CHECK-GI-NEXT:    add w10, w8, #3276; CHECK-GI-NEXT:    cmp w9, #321277; CHECK-GI-NEXT:    str w10, [x0]278; CHECK-GI-NEXT:    b.gt .LBB20_6279; CHECK-GI-NEXT:  // %bb.4: // %test5280; CHECK-GI-NEXT:    add w10, w8, #4281; CHECK-GI-NEXT:    cmn w9, #444282; CHECK-GI-NEXT:    str w10, [x0]283; CHECK-GI-NEXT:    b.gt .LBB20_6284; CHECK-GI-NEXT:  // %bb.5: // %test6285; CHECK-GI-NEXT:    add w8, w8, #5286; CHECK-GI-NEXT:    str w8, [x0]287; CHECK-GI-NEXT:  .LBB20_6: // %common.ret288; CHECK-GI-NEXT:    ret289  %val = load i32, ptr %var_i32290  %val2 = load i32, ptr %var2_i32291 292  %cmp_pos_small = icmp ne i32 %val, 4095293  br i1 %cmp_pos_small, label %ret, label %test2294 295test2:296  %newval2 = add i32 %val, 1297  store i32 %newval2, ptr %var_i32298  %cmp_pos_big = icmp ult i32 %val2, 14610432299  br i1 %cmp_pos_big, label %ret, label %test3300 301test3:302  %newval3 = add i32 %val, 2303  store i32 %newval3, ptr %var_i32304  %cmp_pos_slt = icmp slt i32 %val, 123305  br i1 %cmp_pos_slt, label %ret, label %test4306 307test4:308  %newval4 = add i32 %val, 3309  store i32 %newval4, ptr %var_i32310  %cmp_pos_sgt = icmp sgt i32 %val2, 321311  br i1 %cmp_pos_sgt, label %ret, label %test5312 313test5:314  %newval5 = add i32 %val, 4315  store i32 %newval5, ptr %var_i32316  %cmp_neg_uge = icmp sgt i32 %val2, -444317  br i1 %cmp_neg_uge, label %ret, label %test6318 319test6:320  %newval6 = add i32 %val, 5321  store i32 %newval6, ptr %var_i32322  ret void323 324ret:325  ret void326}327 328declare {i32, i1} @llvm.sadd.with.overflow.i32(i32 %a, i32 %b)329 330define i1 @sadd_add(i32 %a, i32 %b, ptr %p) {331; CHECK-LABEL: sadd_add:332; CHECK:       // %bb.0:333; CHECK-NEXT:    mvn w8, w0334; CHECK-NEXT:    adds w8, w8, w1335; CHECK-NEXT:    cset w0, vs336; CHECK-NEXT:    add w8, w8, #1337; CHECK-NEXT:    str w8, [x2]338; CHECK-NEXT:    ret339  %nota = xor i32 %a, -1340  %a0 = call {i32, i1} @llvm.sadd.with.overflow.i32(i32 %nota, i32 %b)341  %e0 = extractvalue {i32, i1} %a0, 0342  %e1 = extractvalue {i32, i1} %a0, 1343  %res = add i32 %e0, 1344  store i32 %res, ptr %p345  ret i1 %e1346}347 348declare {i8, i1} @llvm.uadd.with.overflow.i8(i8 %a, i8 %b)349 350define i1 @uadd_add(i8 %a, i8 %b, ptr %p) {351; CHECK-SD-LABEL: uadd_add:352; CHECK-SD:       // %bb.0:353; CHECK-SD-NEXT:    mov w8, #255 // =0xff354; CHECK-SD-NEXT:    bic w8, w8, w0355; CHECK-SD-NEXT:    add w8, w8, w1, uxtb356; CHECK-SD-NEXT:    lsr w0, w8, #8357; CHECK-SD-NEXT:    add w8, w8, #1358; CHECK-SD-NEXT:    strb w8, [x2]359; CHECK-SD-NEXT:    ret360;361; CHECK-GI-LABEL: uadd_add:362; CHECK-GI:       // %bb.0:363; CHECK-GI-NEXT:    mvn w8, w0364; CHECK-GI-NEXT:    and w9, w1, #0xff365; CHECK-GI-NEXT:    add w8, w9, w8, uxtb366; CHECK-GI-NEXT:    cmp w8, w8, uxtb367; CHECK-GI-NEXT:    add w8, w8, #1368; CHECK-GI-NEXT:    cset w0, ne369; CHECK-GI-NEXT:    strb w8, [x2]370; CHECK-GI-NEXT:    ret371  %nota = xor i8 %a, -1372  %a0 = call {i8, i1} @llvm.uadd.with.overflow.i8(i8 %nota, i8 %b)373  %e0 = extractvalue {i8, i1} %a0, 0374  %e1 = extractvalue {i8, i1} %a0, 1375  %res = add i8 %e0, 1376  store i8 %res, ptr %p377  ret i1 %e1378}379 380; This is a unique edge case that will generate the following MIR381;   MOVi32imm -1000000382;   SUBREG_TO_REG 0, killed %1, %subreg.sub_32383; When using a 64-bit unsigned for the "-1000000" immediate, the code384; must make sure to zero out the top 32 bits since SUBREG_TO_REG is385; zero extending the value386define i64 @addl_0x80000000(i64 %a) {387; CHECK-LABEL: addl_0x80000000:388; CHECK:       // %bb.0:389; CHECK-NEXT:    mov w8, #48576 // =0xbdc0390; CHECK-NEXT:    movk w8, #65520, lsl #16391; CHECK-NEXT:    add x0, x0, x8392; CHECK-NEXT:    ret393  %b = add i64 %a, 4293967296394  ret i64 %b395}396 397; ADDS and SUBS Optimizations398; Checks with all types first, then checks that only EQ and NE optimize399define i1 @eq_i(i32 %0) {400; CHECK-LABEL: eq_i:401; CHECK:       // %bb.0:402; CHECK-NEXT:    sub w8, w0, #273, lsl #12 // =1118208403; CHECK-NEXT:    cmp w8, #273404; CHECK-NEXT:    cset w0, eq405; CHECK-NEXT:    ret406  %2 = icmp eq i32 %0, 1118481407  ret i1 %2408}409 410define i1 @eq_l(i64 %0) {411; CHECK-LABEL: eq_l:412; CHECK:       // %bb.0:413; CHECK-NEXT:    sub x8, x0, #273, lsl #12 // =1118208414; CHECK-NEXT:    cmp x8, #273415; CHECK-NEXT:    cset w0, eq416; CHECK-NEXT:    ret417  %2 = icmp eq i64 %0, 1118481418  ret i1 %2419}420 421define i1 @ne_i(i32 %0) {422; CHECK-LABEL: ne_i:423; CHECK:       // %bb.0:424; CHECK-NEXT:    sub w8, w0, #273, lsl #12 // =1118208425; CHECK-NEXT:    cmp w8, #273426; CHECK-NEXT:    cset w0, ne427; CHECK-NEXT:    ret428  %2 = icmp ne i32 %0, 1118481429  ret i1 %2430}431 432define i1 @ne_l(i64 %0) {433; CHECK-LABEL: ne_l:434; CHECK:       // %bb.0:435; CHECK-NEXT:    sub x8, x0, #273, lsl #12 // =1118208436; CHECK-NEXT:    cmp x8, #273437; CHECK-NEXT:    cset w0, ne438; CHECK-NEXT:    ret439  %2 = icmp ne i64 %0, 1118481440  ret i1 %2441}442 443define i1 @eq_in(i32 %0) {444; CHECK-LABEL: eq_in:445; CHECK:       // %bb.0:446; CHECK-NEXT:    add w8, w0, #273, lsl #12 // =1118208447; CHECK-NEXT:    cmn w8, #273448; CHECK-NEXT:    cset w0, eq449; CHECK-NEXT:    ret450  %2 = icmp eq i32 %0, -1118481451  ret i1 %2452}453 454define i1 @eq_ln(i64 %0) {455; CHECK-LABEL: eq_ln:456; CHECK:       // %bb.0:457; CHECK-NEXT:    add x8, x0, #273, lsl #12 // =1118208458; CHECK-NEXT:    cmn x8, #273459; CHECK-NEXT:    cset w0, eq460; CHECK-NEXT:    ret461  %2 = icmp eq i64 %0, -1118481462  ret i1 %2463}464 465define i1 @ne_in(i32 %0) {466; CHECK-LABEL: ne_in:467; CHECK:       // %bb.0:468; CHECK-NEXT:    add w8, w0, #273, lsl #12 // =1118208469; CHECK-NEXT:    cmn w8, #273470; CHECK-NEXT:    cset w0, ne471; CHECK-NEXT:    ret472  %2 = icmp ne i32 %0, -1118481473  ret i1 %2474}475 476define i1 @ne_ln(i64 %0) {477; CHECK-LABEL: ne_ln:478; CHECK:       // %bb.0:479; CHECK-NEXT:    add x8, x0, #273, lsl #12 // =1118208480; CHECK-NEXT:    cmn x8, #273481; CHECK-NEXT:    cset w0, ne482; CHECK-NEXT:    ret483  %2 = icmp ne i64 %0, -1118481484  ret i1 %2485}486 487define i1 @reject_eq(i32 %0) {488; CHECK-LABEL: reject_eq:489; CHECK:       // %bb.0:490; CHECK-NEXT:    mov w8, #51712 // =0xca00491; CHECK-NEXT:    movk w8, #15258, lsl #16492; CHECK-NEXT:    cmp w0, w8493; CHECK-NEXT:    cset w0, eq494; CHECK-NEXT:    ret495  %2 = icmp eq i32 %0, 1000000000496  ret i1 %2497}498 499define i1 @reject_non_eqne_csinc(i32 %0) {500; CHECK-LABEL: reject_non_eqne_csinc:501; CHECK:       // %bb.0:502; CHECK-NEXT:    mov w8, #4369 // =0x1111503; CHECK-NEXT:    movk w8, #17, lsl #16504; CHECK-NEXT:    cmp w0, w8505; CHECK-NEXT:    cset w0, lo506; CHECK-NEXT:    ret507  %2 = icmp ult i32 %0, 1118481508  ret i1 %2509}510 511define i32 @accept_csel(i32 %0) {512; CHECK-SD-LABEL: accept_csel:513; CHECK-SD:       // %bb.0:514; CHECK-SD-NEXT:    sub w9, w0, #273, lsl #12 // =1118208515; CHECK-SD-NEXT:    mov w8, #17 // =0x11516; CHECK-SD-NEXT:    cmp w9, #273517; CHECK-SD-NEXT:    mov w9, #11 // =0xb518; CHECK-SD-NEXT:    csel w0, w9, w8, eq519; CHECK-SD-NEXT:    ret520;521; CHECK-GI-LABEL: accept_csel:522; CHECK-GI:       // %bb.0:523; CHECK-GI-NEXT:    sub w8, w0, #273, lsl #12 // =1118208524; CHECK-GI-NEXT:    mov w9, #17 // =0x11525; CHECK-GI-NEXT:    mov w10, #11 // =0xb526; CHECK-GI-NEXT:    cmp w8, #273527; CHECK-GI-NEXT:    csel w0, w10, w9, eq528; CHECK-GI-NEXT:    ret529  %2 = icmp eq i32 %0, 1118481530  %3 = select i1 %2, i32 11, i32 17531  ret i32 %3532}533 534define i32 @reject_non_eqne_csel(i32 %0) {535; CHECK-SD-LABEL: reject_non_eqne_csel:536; CHECK-SD:       // %bb.0:537; CHECK-SD-NEXT:    mov w8, #4369 // =0x1111538; CHECK-SD-NEXT:    mov w9, #11 // =0xb539; CHECK-SD-NEXT:    movk w8, #17, lsl #16540; CHECK-SD-NEXT:    cmp w0, w8541; CHECK-SD-NEXT:    mov w8, #17 // =0x11542; CHECK-SD-NEXT:    csel w0, w9, w8, lo543; CHECK-SD-NEXT:    ret544;545; CHECK-GI-LABEL: reject_non_eqne_csel:546; CHECK-GI:       // %bb.0:547; CHECK-GI-NEXT:    mov w8, #4369 // =0x1111548; CHECK-GI-NEXT:    mov w9, #17 // =0x11549; CHECK-GI-NEXT:    mov w10, #11 // =0xb550; CHECK-GI-NEXT:    movk w8, #17, lsl #16551; CHECK-GI-NEXT:    cmp w0, w8552; CHECK-GI-NEXT:    csel w0, w10, w9, lo553; CHECK-GI-NEXT:    ret554  %2 = icmp ult i32 %0, 1118481555  %3 = select i1 %2, i32 11, i32 17556  ret i32 %3557}558 559declare void @fooy()560 561define void @accept_branch(i32 %0) {562; CHECK-LABEL: accept_branch:563; CHECK:       // %bb.0:564; CHECK-NEXT:    sub w8, w0, #291, lsl #12 // =1191936565; CHECK-NEXT:    cmp w8, #1110566; CHECK-NEXT:    b.eq .LBB36_2567; CHECK-NEXT:  // %bb.1:568; CHECK-NEXT:    ret569; CHECK-NEXT:  .LBB36_2:570; CHECK-NEXT:    b fooy571  %2 = icmp ne i32 %0, 1193046572  br i1 %2, label %4, label %35733:                                                ; preds = %1574  tail call void @fooy()575  br label %45764:                                                ; preds = %3, %1577  ret void578}579 580define void @reject_non_eqne_branch(i32 %0) {581; CHECK-LABEL: reject_non_eqne_branch:582; CHECK:       // %bb.0:583; CHECK-NEXT:    mov w8, #13398 // =0x3456584; CHECK-NEXT:    movk w8, #18, lsl #16585; CHECK-NEXT:    cmp w0, w8586; CHECK-NEXT:    b.le .LBB37_2587; CHECK-NEXT:  // %bb.1:588; CHECK-NEXT:    ret589; CHECK-NEXT:  .LBB37_2:590; CHECK-NEXT:    b fooy591  %2 = icmp sgt i32 %0, 1193046592  br i1 %2, label %4, label %35933:                                                ; preds = %1594  tail call void @fooy()595  br label %45964:                                                ; preds = %3, %1597  ret void598}599 600define i32 @reject_multiple_usages(i32 %0) {601; CHECK-SD-LABEL: reject_multiple_usages:602; CHECK-SD:       // %bb.0:603; CHECK-SD-NEXT:    mov w8, #4369 // =0x1111604; CHECK-SD-NEXT:    mov w9, #3 // =0x3605; CHECK-SD-NEXT:    mov w10, #17 // =0x11606; CHECK-SD-NEXT:    movk w8, #17, lsl #16607; CHECK-SD-NEXT:    mov w11, #12 // =0xc608; CHECK-SD-NEXT:    cmp w0, w8609; CHECK-SD-NEXT:    mov w8, #9 // =0x9610; CHECK-SD-NEXT:    csel w8, w8, w9, eq611; CHECK-SD-NEXT:    csel w9, w11, w10, hi612; CHECK-SD-NEXT:    mov w10, #53312 // =0xd040613; CHECK-SD-NEXT:    movk w10, #2, lsl #16614; CHECK-SD-NEXT:    add w8, w8, w9615; CHECK-SD-NEXT:    mov w9, #26304 // =0x66c0616; CHECK-SD-NEXT:    cmp w0, w10617; CHECK-SD-NEXT:    movk w9, #1433, lsl #16618; CHECK-SD-NEXT:    csel w0, w8, w9, hi619; CHECK-SD-NEXT:    ret620;621; CHECK-GI-LABEL: reject_multiple_usages:622; CHECK-GI:       // %bb.0:623; CHECK-GI-NEXT:    mov w8, #4369 // =0x1111624; CHECK-GI-NEXT:    mov w9, #3 // =0x3625; CHECK-GI-NEXT:    mov w10, #9 // =0x9626; CHECK-GI-NEXT:    movk w8, #17, lsl #16627; CHECK-GI-NEXT:    mov w11, #12 // =0xc628; CHECK-GI-NEXT:    cmp w0, w8629; CHECK-GI-NEXT:    mov w8, #17 // =0x11630; CHECK-GI-NEXT:    csel w9, w10, w9, eq631; CHECK-GI-NEXT:    csel w8, w11, w8, hi632; CHECK-GI-NEXT:    mov w10, #53312 // =0xd040633; CHECK-GI-NEXT:    movk w10, #2, lsl #16634; CHECK-GI-NEXT:    add w8, w9, w8635; CHECK-GI-NEXT:    mov w9, #26304 // =0x66c0636; CHECK-GI-NEXT:    movk w9, #1433, lsl #16637; CHECK-GI-NEXT:    cmp w0, w10638; CHECK-GI-NEXT:    csel w0, w8, w9, hi639; CHECK-GI-NEXT:    ret640  %2 = icmp eq i32 %0, 1118481641  %3 = icmp ugt i32 %0, 1118481642  %4 = select i1 %2, i32 9, i32 3643  %5 = select i1 %3, i32 12, i32 17644  %6 = add i32 %4, %5645  %7 = icmp ugt i32 %0, 184384646  %8 = select i1 %7, i32 %6, i32 93939392647  ret i32 %8648}649 650; Unique case found in ClangBuiltLinux where the DstReg is not Virtual and651; caused an assertion failure652define dso_local i32 @neigh_periodic_work_tbl_1() {653; CHECK-LABEL: neigh_periodic_work_tbl_1:654; CHECK:       // %bb.0: // %entry655; CHECK-NEXT:    adrp x8, neigh_periodic_work_tbl_1656; CHECK-NEXT:    add x8, x8, :lo12:neigh_periodic_work_tbl_1657; CHECK-NEXT:    add x8, x8, #18, lsl #12 // =73728658; CHECK-NEXT:    cmn x8, #1272659; CHECK-NEXT:    b.mi .LBB39_2660; CHECK-NEXT:  // %bb.1: // %if.end661; CHECK-NEXT:    ret662; CHECK-NEXT:  .LBB39_2: // %for.cond663; CHECK-NEXT:    // =>This Inner Loop Header: Depth=1664; CHECK-NEXT:    b .LBB39_2665entry:666  %cmp = icmp slt i64 add (i64 ptrtoint (ptr @neigh_periodic_work_tbl_1 to i64), i64 75000), 0667  br i1 %cmp, label %for.cond, label %if.end668for.cond:                                         ; preds = %entry, %for.cond669  br label %for.cond670if.end:                                           ; preds = %entry671  ret i32 undef672}673 674@jiffies = dso_local local_unnamed_addr global i32 0, align 4675@primary_crng = dso_local local_unnamed_addr global i32 0, align 4676@input_pool = dso_local global i32 0, align 4677declare dso_local i32 @crng_reseed(...) local_unnamed_addr678; Function Attrs: nounwind uwtable679define dso_local i32 @_extract_crng_crng() {680; CHECK-LABEL: _extract_crng_crng:681; CHECK:       // %bb.0: // %entry682; CHECK-NEXT:    adrp x8, _extract_crng_crng683; CHECK-NEXT:    add x8, x8, :lo12:_extract_crng_crng684; CHECK-NEXT:    tbnz x8, #63, .LBB40_2685; CHECK-NEXT:  // %bb.1: // %lor.lhs.false686; CHECK-NEXT:    adrp x9, jiffies687; CHECK-NEXT:    ldrsw x9, [x9, :lo12:jiffies]688; CHECK-NEXT:    sub x8, x8, x9689; CHECK-NEXT:    add x8, x8, #18, lsl #12 // =73728690; CHECK-NEXT:    cmn x8, #1272691; CHECK-NEXT:    b.pl .LBB40_3692; CHECK-NEXT:  .LBB40_2: // %if.then693; CHECK-NEXT:    adrp x8, primary_crng694; CHECK-NEXT:    ldr w8, [x8, :lo12:primary_crng]695; CHECK-NEXT:    cmp w8, #0696; CHECK-NEXT:    adrp x8, input_pool697; CHECK-NEXT:    add x8, x8, :lo12:input_pool698; CHECK-NEXT:    csel x0, xzr, x8, eq699; CHECK-NEXT:    b crng_reseed700; CHECK-NEXT:  .LBB40_3: // %if.end701; CHECK-NEXT:    ret702entry:703  %cmp2 = icmp slt ptr @_extract_crng_crng, null704  br i1 %cmp2, label %if.then, label %lor.lhs.false705lor.lhs.false:                                    ; preds = %entry706  %0 = load i32, ptr @jiffies, align 4707  %idx.ext = sext i32 %0 to i64708  %idx.neg = sub nsw i64 0, %idx.ext709  %add.ptr = getelementptr i8, ptr getelementptr (i8, ptr @_extract_crng_crng, i64 75000), i64 %idx.neg710  %cmp = icmp slt ptr %add.ptr, null711  br i1 %cmp, label %if.then, label %if.end712if.then:                                          ; preds = %lor.lhs.false, %entry713  %1 = load i32, ptr @primary_crng, align 4714  %tobool.not = icmp eq i32 %1, 0715  %cond = select i1 %tobool.not, ptr null, ptr @input_pool716  %call = tail call i32 @crng_reseed(ptr noundef %cond)717  br label %if.end718if.end:                                           ; preds = %if.then, %lor.lhs.false719  ret i32 undef720}721 722; ((X << C) - Y) + Z --> (Z - Y) + (X << C)723define i32 @commute_subop0(i32 %x, i32 %y, i32 %z) {724; CHECK-SD-LABEL: commute_subop0:725; CHECK-SD:       // %bb.0:726; CHECK-SD-NEXT:    sub w8, w2, w1727; CHECK-SD-NEXT:    add w0, w8, w0, lsl #3728; CHECK-SD-NEXT:    ret729;730; CHECK-GI-LABEL: commute_subop0:731; CHECK-GI:       // %bb.0:732; CHECK-GI-NEXT:    lsl w8, w0, #3733; CHECK-GI-NEXT:    sub w8, w8, w1734; CHECK-GI-NEXT:    add w0, w8, w2735; CHECK-GI-NEXT:    ret736  %shl = shl i32 %x, 3737  %sub = sub i32 %shl, %y738  %add = add i32 %sub, %z739  ret i32 %add740}741 742; ((X >> C) - Y) + Z --> (Z - Y) + (X >> C)743define i32 @commute_subop0_lshr(i32 %x, i32 %y, i32 %z) {744; CHECK-SD-LABEL: commute_subop0_lshr:745; CHECK-SD:       // %bb.0:746; CHECK-SD-NEXT:    sub w8, w2, w1747; CHECK-SD-NEXT:    add w0, w8, w0, lsr #3748; CHECK-SD-NEXT:    ret749;750; CHECK-GI-LABEL: commute_subop0_lshr:751; CHECK-GI:       // %bb.0:752; CHECK-GI-NEXT:    lsr w8, w0, #3753; CHECK-GI-NEXT:    sub w8, w8, w1754; CHECK-GI-NEXT:    add w0, w8, w2755; CHECK-GI-NEXT:    ret756  %lshr = lshr i32 %x, 3757  %sub = sub i32 %lshr, %y758  %add = add i32 %sub, %z759  ret i32 %add760}761 762; ((X >> C) - Y) + Z --> (Z - Y) + (X >> C)763define i32 @commute_subop0_ashr(i32 %x, i32 %y, i32 %z) {764; CHECK-SD-LABEL: commute_subop0_ashr:765; CHECK-SD:       // %bb.0:766; CHECK-SD-NEXT:    sub w8, w2, w1767; CHECK-SD-NEXT:    add w0, w8, w0, asr #3768; CHECK-SD-NEXT:    ret769;770; CHECK-GI-LABEL: commute_subop0_ashr:771; CHECK-GI:       // %bb.0:772; CHECK-GI-NEXT:    asr w8, w0, #3773; CHECK-GI-NEXT:    sub w8, w8, w1774; CHECK-GI-NEXT:    add w0, w8, w2775; CHECK-GI-NEXT:    ret776  %ashr = ashr i32 %x, 3777  %sub = sub i32 %ashr, %y778  %add = add i32 %sub, %z779  ret i32 %add780}781 782; ((sext X) - Y) + Z --> (Z - Y) + (sext X)783define i64 @commute_subop0_sext(i32 %x, i64 %y, i64 %z) {784; CHECK-SD-LABEL: commute_subop0_sext:785; CHECK-SD:       // %bb.0:786; CHECK-SD-NEXT:    sub x8, x2, x1787; CHECK-SD-NEXT:    add x0, x8, w0, sxtw788; CHECK-SD-NEXT:    ret789;790; CHECK-GI-LABEL: commute_subop0_sext:791; CHECK-GI:       // %bb.0:792; CHECK-GI-NEXT:    // kill: def $w0 killed $w0 def $x0793; CHECK-GI-NEXT:    sxtw x8, w0794; CHECK-GI-NEXT:    sub x8, x8, x1795; CHECK-GI-NEXT:    add x0, x8, x2796; CHECK-GI-NEXT:    ret797  %sext = sext i32 %x to i64798  %sub = sub i64 %sext, %y799  %add = add i64 %sub, %z800  ret i64 %add801}802 803; ((sext_inreg X) - Y) + Z --> (Z - Y) + (sext_inreg X)804define i64 @commute_subop0_sext_inreg(i64 %x, i64 %y, i64 %z) {805; CHECK-SD-LABEL: commute_subop0_sext_inreg:806; CHECK-SD:       // %bb.0:807; CHECK-SD-NEXT:    sub x8, x2, x1808; CHECK-SD-NEXT:    add x0, x8, w0, sxth809; CHECK-SD-NEXT:    ret810;811; CHECK-GI-LABEL: commute_subop0_sext_inreg:812; CHECK-GI:       // %bb.0:813; CHECK-GI-NEXT:    sxth x8, w0814; CHECK-GI-NEXT:    sub x8, x8, x1815; CHECK-GI-NEXT:    add x0, x8, x2816; CHECK-GI-NEXT:    ret817  %shl = shl i64 %x, 48818  %ashr = ashr i64 %shl, 48819  %sub = sub i64 %ashr, %y820  %add = add i64 %sub, %z821  ret i64 %add822}823 824; ((zext X) - Y) + Z --> (Z - Y) + (zext X)825define i32 @commute_subop0_zext(i16 %x, i32 %y, i32 %z) {826; CHECK-SD-LABEL: commute_subop0_zext:827; CHECK-SD:       // %bb.0:828; CHECK-SD-NEXT:    sub w8, w2, w1829; CHECK-SD-NEXT:    add w0, w8, w0, uxth830; CHECK-SD-NEXT:    ret831;832; CHECK-GI-LABEL: commute_subop0_zext:833; CHECK-GI:       // %bb.0:834; CHECK-GI-NEXT:    and w8, w0, #0xffff835; CHECK-GI-NEXT:    sub w8, w8, w1836; CHECK-GI-NEXT:    add w0, w8, w2837; CHECK-GI-NEXT:    ret838  %zext = zext i16 %x to i32839  %sub = sub i32 %zext, %y840  %add = add i32 %sub, %z841  ret i32 %add842}843 844 845; ((anyext X) - Y) + Z --> (Z - Y) + (anyext X)846define i8 @commute_subop0_anyext(i16 %a, i16 %b, i32 %c) {847; CHECK-SD-LABEL: commute_subop0_anyext:848; CHECK-SD:       // %bb.0:849; CHECK-SD-NEXT:    mov w8, #111 // =0x6f850; CHECK-SD-NEXT:    sub w9, w2, w1851; CHECK-SD-NEXT:    madd w8, w0, w8, w9852; CHECK-SD-NEXT:    lsl w8, w8, #3853; CHECK-SD-NEXT:    sub w0, w8, #1776854; CHECK-SD-NEXT:    ret855;856; CHECK-GI-LABEL: commute_subop0_anyext:857; CHECK-GI:       // %bb.0:858; CHECK-GI-NEXT:    mov w8, #111 // =0x6f859; CHECK-GI-NEXT:    add w9, w1, #222860; CHECK-GI-NEXT:    mul w8, w0, w8861; CHECK-GI-NEXT:    and w8, w8, #0xffff862; CHECK-GI-NEXT:    sub w8, w8, w9, uxth863; CHECK-GI-NEXT:    add w8, w8, w2864; CHECK-GI-NEXT:    lsl w0, w8, #3865; CHECK-GI-NEXT:    ret866  %aa = mul i16 %a, 111867  %bb = add i16 %b, 222868  %a_32 = zext i16 %aa to i32869  %b_32 = zext i16 %bb to i32870  %sub = sub i32 %a_32, %b_32871  %add = add i32 %sub, %c872  %trunc = trunc i32 %add to i8873  %r = shl i8 %trunc, 3874  ret i8 %r875}876 877; ((X and C) - Y) + Z --> (Z - Y) + (X and C)878define i32 @commute_subop0_and(i32 %x, i32 %y, i32 %z) {879; CHECK-SD-LABEL: commute_subop0_and:880; CHECK-SD:       // %bb.0:881; CHECK-SD-NEXT:    sub w8, w2, w1882; CHECK-SD-NEXT:    add w0, w8, w0, uxtb883; CHECK-SD-NEXT:    ret884;885; CHECK-GI-LABEL: commute_subop0_and:886; CHECK-GI:       // %bb.0:887; CHECK-GI-NEXT:    and w8, w0, #0xff888; CHECK-GI-NEXT:    sub w8, w8, w1889; CHECK-GI-NEXT:    add w0, w8, w2890; CHECK-GI-NEXT:    ret891  %and = and i32 %x, 255892  %sub = sub i32 %and, %y893  %add = add i32 %sub, %z894  ret i32 %add895}896 897; Z + ((X << C) - Y) --> (Z - Y) + (X << C)898define i32 @commute_subop0_cadd(i32 %x, i32 %y, i32 %z) {899; CHECK-SD-LABEL: commute_subop0_cadd:900; CHECK-SD:       // %bb.0:901; CHECK-SD-NEXT:    sub w8, w2, w1902; CHECK-SD-NEXT:    add w0, w8, w0, lsl #3903; CHECK-SD-NEXT:    ret904;905; CHECK-GI-LABEL: commute_subop0_cadd:906; CHECK-GI:       // %bb.0:907; CHECK-GI-NEXT:    lsl w8, w0, #3908; CHECK-GI-NEXT:    sub w8, w8, w1909; CHECK-GI-NEXT:    add w0, w2, w8910; CHECK-GI-NEXT:    ret911  %shl = shl i32 %x, 3912  %sub = sub i32 %shl, %y913  %add = add i32 %z, %sub914  ret i32 %add915}916 917; Y + ((X << C) - X) --> (Y - X) + (X << C)918define i32 @commute_subop0_mul(i32 %x, i32 %y) {919; CHECK-SD-LABEL: commute_subop0_mul:920; CHECK-SD:       // %bb.0:921; CHECK-SD-NEXT:    sub w8, w1, w0922; CHECK-SD-NEXT:    add w0, w8, w0, lsl #3923; CHECK-SD-NEXT:    ret924;925; CHECK-GI-LABEL: commute_subop0_mul:926; CHECK-GI:       // %bb.0:927; CHECK-GI-NEXT:    lsl w8, w0, #3928; CHECK-GI-NEXT:    sub w8, w8, w0929; CHECK-GI-NEXT:    add w0, w8, w1930; CHECK-GI-NEXT:    ret931  %mul = mul i32 %x, 7932  %add = add i32 %mul, %y933  ret i32 %add934}935 936; negative case for ((X << C) - Y) + Z --> (Z - Y) + (X << C)937; Y can't be constant to avoid dead loop938define i32 @commute_subop0_zconst(i32 %x, i32 %y) {939; CHECK-LABEL: commute_subop0_zconst:940; CHECK:       // %bb.0:941; CHECK-NEXT:    lsl w8, w0, #3942; CHECK-NEXT:    sub w8, w8, w1943; CHECK-NEXT:    add w0, w8, #1944; CHECK-NEXT:    ret945  %shl = shl i32 %x, 3946  %sub = sub i32 %shl, %y947  %add = add i32 %sub, 1948  ret i32 %add949}950 951; negative case for ((X << C) - Y) + Z --> (Z - Y) + (X << C)952; Y can't be shift C also to avoid dead loop953define i32 @commute_subop0_zshiftc_oneuse(i32 %x, i32 %y, i32 %z) {954; CHECK-LABEL: commute_subop0_zshiftc_oneuse:955; CHECK:       // %bb.0:956; CHECK-NEXT:    lsl w8, w0, #3957; CHECK-NEXT:    sub w8, w8, w1958; CHECK-NEXT:    add w0, w8, w2, lsl #2959; CHECK-NEXT:    ret960  %xshl = shl i32 %x, 3961  %sub = sub i32 %xshl, %y962  %zshl = shl i32 %z, 2963  %add = add i32 %sub, %zshl964  ret i32 %add965}966 967define i32 @commute_subop0_zshiftc(i32 %x, i32 %y, i32 %z) {968; CHECK-SD-LABEL: commute_subop0_zshiftc:969; CHECK-SD:       // %bb.0:970; CHECK-SD-NEXT:    lsl w8, w2, #2971; CHECK-SD-NEXT:    sub w9, w8, w1972; CHECK-SD-NEXT:    add w9, w9, w0, lsl #3973; CHECK-SD-NEXT:    eor w0, w8, w9974; CHECK-SD-NEXT:    ret975;976; CHECK-GI-LABEL: commute_subop0_zshiftc:977; CHECK-GI:       // %bb.0:978; CHECK-GI-NEXT:    lsl w8, w0, #3979; CHECK-GI-NEXT:    lsl w9, w2, #2980; CHECK-GI-NEXT:    sub w8, w8, w1981; CHECK-GI-NEXT:    add w8, w8, w9982; CHECK-GI-NEXT:    eor w0, w9, w8983; CHECK-GI-NEXT:    ret984  %xshl = shl i32 %x, 3985  %sub = sub i32 %xshl, %y986  %zshl = shl i32 %z, 2987  %add = add i32 %sub, %zshl988  %r = xor i32 %zshl, %add989  ret i32 %r990}991