brintos

brintos / llvm-project-archived public Read only

0
0
Text · 9.1 KiB · 4a6c1d0 Raw
323 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py2; RUN: llc -mtriple=i686-- < %s | FileCheck %s --check-prefix=X863; RUN: llc -mtriple=x86_64-- < %s | FileCheck %s --check-prefix=X644 5; Optimize expanded SRL/SHL used as an input of6; SETCC comparing it with zero by removing rotation.7;8; See https://bugs.llvm.org/show_bug.cgi?id=501979define i128 @opt_setcc_lt_power_of_2(i128 %a) nounwind {10; X86-LABEL: opt_setcc_lt_power_of_2:11; X86:       # %bb.0:12; X86-NEXT:    pushl %ebp13; X86-NEXT:    movl %esp, %ebp14; X86-NEXT:    pushl %ebx15; X86-NEXT:    pushl %edi16; X86-NEXT:    pushl %esi17; X86-NEXT:    andl $-16, %esp18; X86-NEXT:    subl $16, %esp19; X86-NEXT:    movl 36(%ebp), %ecx20; X86-NEXT:    movl 32(%ebp), %edx21; X86-NEXT:    movl 28(%ebp), %edi22; X86-NEXT:    movl 24(%ebp), %esi23; X86-NEXT:    .p2align 424; X86-NEXT:  .LBB0_1: # %loop25; X86-NEXT:    # =>This Inner Loop Header: Depth=126; X86-NEXT:    addl $1, %esi27; X86-NEXT:    adcl $0, %edi28; X86-NEXT:    adcl $0, %edx29; X86-NEXT:    adcl $0, %ecx30; X86-NEXT:    movl %edx, %ebx31; X86-NEXT:    orl %ecx, %ebx32; X86-NEXT:    movl %esi, %eax33; X86-NEXT:    movl %edi, %esi34; X86-NEXT:    orl %edx, %esi35; X86-NEXT:    orl %ecx, %esi36; X86-NEXT:    shrdl $28, %ebx, %esi37; X86-NEXT:    movl %eax, %esi38; X86-NEXT:    jne .LBB0_139; X86-NEXT:  # %bb.2: # %exit40; X86-NEXT:    movl 8(%ebp), %eax41; X86-NEXT:    movl %esi, (%eax)42; X86-NEXT:    movl %edi, 4(%eax)43; X86-NEXT:    movl %edx, 8(%eax)44; X86-NEXT:    movl %ecx, 12(%eax)45; X86-NEXT:    leal -12(%ebp), %esp46; X86-NEXT:    popl %esi47; X86-NEXT:    popl %edi48; X86-NEXT:    popl %ebx49; X86-NEXT:    popl %ebp50; X86-NEXT:    retl $451;52; X64-LABEL: opt_setcc_lt_power_of_2:53; X64:       # %bb.0:54; X64-NEXT:    movq %rsi, %rdx55; X64-NEXT:    movq %rdi, %rax56; X64-NEXT:    .p2align 457; X64-NEXT:  .LBB0_1: # %loop58; X64-NEXT:    # =>This Inner Loop Header: Depth=159; X64-NEXT:    addq $1, %rax60; X64-NEXT:    adcq $0, %rdx61; X64-NEXT:    movq %rax, %rcx62; X64-NEXT:    shrq $60, %rcx63; X64-NEXT:    orq %rdx, %rcx64; X64-NEXT:    jne .LBB0_165; X64-NEXT:  # %bb.2: # %exit66; X64-NEXT:    retq67  br label %loop68 69loop:70  %phi.a = phi i128 [ %a, %0 ], [ %inc, %loop ]71  %inc = add i128 %phi.a, 172  %cmp = icmp ult i128 %inc, 115292150460684697673  br i1 %cmp, label %exit, label %loop74 75exit:76  ret i128 %inc77}78 79define i1 @opt_setcc_srl_eq_zero(i128 %a) nounwind {80; X86-LABEL: opt_setcc_srl_eq_zero:81; X86:       # %bb.0:82; X86-NEXT:    pushl %ebp83; X86-NEXT:    movl %esp, %ebp84; X86-NEXT:    andl $-16, %esp85; X86-NEXT:    subl $16, %esp86; X86-NEXT:    movl 16(%ebp), %eax87; X86-NEXT:    movl 12(%ebp), %ecx88; X86-NEXT:    orl 20(%ebp), %ecx89; X86-NEXT:    movl 8(%ebp), %edx90; X86-NEXT:    orl %eax, %edx91; X86-NEXT:    orl %ecx, %edx92; X86-NEXT:    orl %eax, %ecx93; X86-NEXT:    shldl $15, %edx, %ecx94; X86-NEXT:    sete %al95; X86-NEXT:    movl %ebp, %esp96; X86-NEXT:    popl %ebp97; X86-NEXT:    retl98;99; X64-LABEL: opt_setcc_srl_eq_zero:100; X64:       # %bb.0:101; X64-NEXT:    shrq $17, %rdi102; X64-NEXT:    orq %rsi, %rdi103; X64-NEXT:    sete %al104; X64-NEXT:    retq105   %srl = lshr i128 %a, 17106   %cmp = icmp eq i128 %srl, 0107   ret i1 %cmp108}109 110define i1 @opt_setcc_srl_ne_zero(i128 %a) nounwind {111; X86-LABEL: opt_setcc_srl_ne_zero:112; X86:       # %bb.0:113; X86-NEXT:    pushl %ebp114; X86-NEXT:    movl %esp, %ebp115; X86-NEXT:    andl $-16, %esp116; X86-NEXT:    subl $16, %esp117; X86-NEXT:    movl 16(%ebp), %eax118; X86-NEXT:    movl 12(%ebp), %ecx119; X86-NEXT:    orl 20(%ebp), %ecx120; X86-NEXT:    movl 8(%ebp), %edx121; X86-NEXT:    orl %eax, %edx122; X86-NEXT:    orl %ecx, %edx123; X86-NEXT:    orl %eax, %ecx124; X86-NEXT:    shldl $15, %edx, %ecx125; X86-NEXT:    setne %al126; X86-NEXT:    movl %ebp, %esp127; X86-NEXT:    popl %ebp128; X86-NEXT:    retl129;130; X64-LABEL: opt_setcc_srl_ne_zero:131; X64:       # %bb.0:132; X64-NEXT:    shrq $17, %rdi133; X64-NEXT:    orq %rsi, %rdi134; X64-NEXT:    setne %al135; X64-NEXT:    retq136   %srl = lshr i128 %a, 17137   %cmp = icmp ne i128 %srl, 0138   ret i1 %cmp139}140 141define i1 @opt_setcc_shl_eq_zero(i128 %a) nounwind {142; X86-LABEL: opt_setcc_shl_eq_zero:143; X86:       # %bb.0:144; X86-NEXT:    pushl %ebp145; X86-NEXT:    movl %esp, %ebp146; X86-NEXT:    andl $-16, %esp147; X86-NEXT:    subl $16, %esp148; X86-NEXT:    movl 16(%ebp), %eax149; X86-NEXT:    movl 20(%ebp), %ecx150; X86-NEXT:    shll $17, %ecx151; X86-NEXT:    orl 8(%ebp), %eax152; X86-NEXT:    orl 12(%ebp), %eax153; X86-NEXT:    orl %ecx, %eax154; X86-NEXT:    sete %al155; X86-NEXT:    movl %ebp, %esp156; X86-NEXT:    popl %ebp157; X86-NEXT:    retl158;159; X64-LABEL: opt_setcc_shl_eq_zero:160; X64:       # %bb.0:161; X64-NEXT:    shlq $17, %rsi162; X64-NEXT:    orq %rdi, %rsi163; X64-NEXT:    sete %al164; X64-NEXT:    retq165   %shl = shl i128 %a, 17166   %cmp = icmp eq i128 %shl, 0167   ret i1 %cmp168}169 170define i1 @opt_setcc_shl_ne_zero(i128 %a) nounwind {171; X86-LABEL: opt_setcc_shl_ne_zero:172; X86:       # %bb.0:173; X86-NEXT:    pushl %ebp174; X86-NEXT:    movl %esp, %ebp175; X86-NEXT:    andl $-16, %esp176; X86-NEXT:    subl $16, %esp177; X86-NEXT:    movl 16(%ebp), %eax178; X86-NEXT:    movl 20(%ebp), %ecx179; X86-NEXT:    shll $17, %ecx180; X86-NEXT:    orl 8(%ebp), %eax181; X86-NEXT:    orl 12(%ebp), %eax182; X86-NEXT:    orl %ecx, %eax183; X86-NEXT:    setne %al184; X86-NEXT:    movl %ebp, %esp185; X86-NEXT:    popl %ebp186; X86-NEXT:    retl187;188; X64-LABEL: opt_setcc_shl_ne_zero:189; X64:       # %bb.0:190; X64-NEXT:    shlq $17, %rsi191; X64-NEXT:    orq %rdi, %rsi192; X64-NEXT:    setne %al193; X64-NEXT:    retq194   %shl = shl i128 %a, 17195   %cmp = icmp ne i128 %shl, 0196   ret i1 %cmp197}198 199; Negative test: optimization should not be applied if shift has multiple users.200define i1 @opt_setcc_shl_eq_zero_multiple_shl_users(i128 %a) nounwind {201; X86-LABEL: opt_setcc_shl_eq_zero_multiple_shl_users:202; X86:       # %bb.0:203; X86-NEXT:    pushl %ebp204; X86-NEXT:    movl %esp, %ebp205; X86-NEXT:    pushl %ebx206; X86-NEXT:    pushl %edi207; X86-NEXT:    pushl %esi208; X86-NEXT:    andl $-16, %esp209; X86-NEXT:    subl $16, %esp210; X86-NEXT:    movl 8(%ebp), %eax211; X86-NEXT:    movl 12(%ebp), %ecx212; X86-NEXT:    movl 16(%ebp), %edx213; X86-NEXT:    movl 20(%ebp), %esi214; X86-NEXT:    shldl $17, %edx, %esi215; X86-NEXT:    shldl $17, %ecx, %edx216; X86-NEXT:    shldl $17, %eax, %ecx217; X86-NEXT:    shll $17, %eax218; X86-NEXT:    movl %ecx, %edi219; X86-NEXT:    orl %esi, %edi220; X86-NEXT:    movl %eax, %ebx221; X86-NEXT:    orl %edx, %ebx222; X86-NEXT:    orl %edi, %ebx223; X86-NEXT:    sete %bl224; X86-NEXT:    pushl %esi225; X86-NEXT:    pushl %edx226; X86-NEXT:    pushl %ecx227; X86-NEXT:    pushl %eax228; X86-NEXT:    calll use@PLT229; X86-NEXT:    addl $16, %esp230; X86-NEXT:    movl %ebx, %eax231; X86-NEXT:    leal -12(%ebp), %esp232; X86-NEXT:    popl %esi233; X86-NEXT:    popl %edi234; X86-NEXT:    popl %ebx235; X86-NEXT:    popl %ebp236; X86-NEXT:    retl237;238; X64-LABEL: opt_setcc_shl_eq_zero_multiple_shl_users:239; X64:       # %bb.0:240; X64-NEXT:    pushq %rbx241; X64-NEXT:    shldq $17, %rdi, %rsi242; X64-NEXT:    shlq $17, %rdi243; X64-NEXT:    movq %rdi, %rax244; X64-NEXT:    orq %rsi, %rax245; X64-NEXT:    sete %bl246; X64-NEXT:    callq use@PLT247; X64-NEXT:    movl %ebx, %eax248; X64-NEXT:    popq %rbx249; X64-NEXT:    retq250   %shl = shl i128 %a, 17251   %cmp = icmp eq i128 %shl, 0252   call void @use(i128 %shl)253   ret i1 %cmp254}255 256; Check that optimization is applied to DAG having appropriate shape257; even if there were no actual shift's expansion.258define i1 @opt_setcc_expanded_shl_correct_shifts(i64 %a, i64 %b) nounwind {259; X86-LABEL: opt_setcc_expanded_shl_correct_shifts:260; X86:       # %bb.0:261; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax262; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx263; X86-NEXT:    orl {{[0-9]+}}(%esp), %eax264; X86-NEXT:    shll $17, %ecx265; X86-NEXT:    orl {{[0-9]+}}(%esp), %eax266; X86-NEXT:    orl %ecx, %eax267; X86-NEXT:    sete %al268; X86-NEXT:    retl269;270; X64-LABEL: opt_setcc_expanded_shl_correct_shifts:271; X64:       # %bb.0:272; X64-NEXT:    shlq $17, %rdi273; X64-NEXT:    orq %rsi, %rdi274; X64-NEXT:    sete %al275; X64-NEXT:    retq276  %shl.a = shl i64 %a, 17277  %srl.b = lshr i64 %b, 47278  %or.0 = or i64 %shl.a, %srl.b279  %shl.b = shl i64 %b, 17280  %or.1 = or i64 %or.0, %shl.b281  %cmp = icmp eq i64 %or.1, 0282  ret i1 %cmp283}284 285; Negative test: optimization should not be applied as286; constants used in shifts do not match.287define i1 @opt_setcc_expanded_shl_wrong_shifts(i64 %a, i64 %b) nounwind {288; X86-LABEL: opt_setcc_expanded_shl_wrong_shifts:289; X86:       # %bb.0:290; X86-NEXT:    pushl %esi291; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax292; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx293; X86-NEXT:    movl {{[0-9]+}}(%esp), %edx294; X86-NEXT:    movl {{[0-9]+}}(%esp), %esi295; X86-NEXT:    shldl $17, %edx, %esi296; X86-NEXT:    shldl $17, %ecx, %edx297; X86-NEXT:    shldl $18, %eax, %ecx298; X86-NEXT:    shll $18, %eax299; X86-NEXT:    orl %edx, %eax300; X86-NEXT:    orl %esi, %ecx301; X86-NEXT:    orl %eax, %ecx302; X86-NEXT:    sete %al303; X86-NEXT:    popl %esi304; X86-NEXT:    retl305;306; X64-LABEL: opt_setcc_expanded_shl_wrong_shifts:307; X64:       # %bb.0:308; X64-NEXT:    shldq $17, %rsi, %rdi309; X64-NEXT:    shlq $18, %rsi310; X64-NEXT:    orq %rdi, %rsi311; X64-NEXT:    sete %al312; X64-NEXT:    retq313  %shl.a = shl i64 %a, 17314  %srl.b = lshr i64 %b, 47315  %or.0 = or i64 %shl.a, %srl.b316  %shl.b = shl i64 %b, 18317  %or.1 = or i64 %or.0, %shl.b318  %cmp = icmp eq i64 %or.1, 0319  ret i1 %cmp320}321 322declare void @use(i128 %a)323