1*9880d681SAndroid Build Coastguard Worker; RUN: llc < %s -mtriple=x86_64-unknown-unknown -mcpu=bdver1 | FileCheck %s 2*9880d681SAndroid Build Coastguard Worker; Verify that for the architectures that are known to have poor latency 3*9880d681SAndroid Build Coastguard Worker; double precision shift instructions we generate alternative sequence 4*9880d681SAndroid Build Coastguard Worker; of instructions with lower latencies instead of shld instruction. 5*9880d681SAndroid Build Coastguard Worker 6*9880d681SAndroid Build Coastguard Worker;uint64_t lshift1(uint64_t a, uint64_t b) 7*9880d681SAndroid Build Coastguard Worker;{ 8*9880d681SAndroid Build Coastguard Worker; return (a << 1) | (b >> 63); 9*9880d681SAndroid Build Coastguard Worker;} 10*9880d681SAndroid Build Coastguard Worker 11*9880d681SAndroid Build Coastguard Worker; CHECK-LABEL: lshift1: 12*9880d681SAndroid Build Coastguard Worker; CHECK: shrq $63, %rsi 13*9880d681SAndroid Build Coastguard Worker; CHECK-NEXT: leaq (%rsi,%rdi,2), %rax 14*9880d681SAndroid Build Coastguard Worker 15*9880d681SAndroid Build Coastguard Workerdefine i64 @lshift1(i64 %a, i64 %b) nounwind readnone uwtable { 16*9880d681SAndroid Build Coastguard Workerentry: 17*9880d681SAndroid Build Coastguard Worker %shl = shl i64 %a, 1 18*9880d681SAndroid Build Coastguard Worker %shr = lshr i64 %b, 63 19*9880d681SAndroid Build Coastguard Worker %or = or i64 %shr, %shl 20*9880d681SAndroid Build Coastguard Worker ret i64 %or 21*9880d681SAndroid Build Coastguard Worker} 22*9880d681SAndroid Build Coastguard Worker 23*9880d681SAndroid Build Coastguard Worker;uint64_t lshift2(uint64_t a, uint64_t b) 24*9880d681SAndroid Build Coastguard Worker;{ 25*9880d681SAndroid Build Coastguard Worker; return (a << 2) | (b >> 62); 26*9880d681SAndroid Build Coastguard Worker;} 27*9880d681SAndroid Build Coastguard Worker 28*9880d681SAndroid Build Coastguard Worker; CHECK-LABEL: lshift2: 29*9880d681SAndroid Build Coastguard Worker; CHECK: shrq $62, %rsi 30*9880d681SAndroid Build Coastguard Worker; CHECK-NEXT: leaq (%rsi,%rdi,4), %rax 31*9880d681SAndroid Build Coastguard Worker 32*9880d681SAndroid Build Coastguard Workerdefine i64 @lshift2(i64 %a, i64 %b) nounwind readnone uwtable { 33*9880d681SAndroid Build Coastguard Workerentry: 34*9880d681SAndroid Build Coastguard Worker %shl = shl i64 %a, 2 35*9880d681SAndroid Build Coastguard Worker %shr = lshr i64 %b, 62 36*9880d681SAndroid Build Coastguard Worker %or = or i64 %shr, %shl 37*9880d681SAndroid Build Coastguard Worker ret i64 %or 38*9880d681SAndroid Build Coastguard Worker} 39*9880d681SAndroid Build Coastguard Worker 40*9880d681SAndroid Build Coastguard Worker;uint64_t lshift7(uint64_t a, uint64_t b) 41*9880d681SAndroid Build Coastguard Worker;{ 42*9880d681SAndroid Build Coastguard Worker; return (a << 7) | (b >> 57); 43*9880d681SAndroid Build Coastguard Worker;} 44*9880d681SAndroid Build Coastguard Worker 45*9880d681SAndroid Build Coastguard Worker; CHECK: lshift7: 46*9880d681SAndroid Build Coastguard Worker; CHECK: shlq $7, {{.*}} 47*9880d681SAndroid Build Coastguard Worker; CHECK-NEXT: shrq $57, {{.*}} 48*9880d681SAndroid Build Coastguard Worker; CHECK-NEXT: leaq ({{.*}},{{.*}}), {{.*}} 49*9880d681SAndroid Build Coastguard Worker 50*9880d681SAndroid Build Coastguard Workerdefine i64 @lshift7(i64 %a, i64 %b) nounwind readnone uwtable { 51*9880d681SAndroid Build Coastguard Workerentry: 52*9880d681SAndroid Build Coastguard Worker %shl = shl i64 %a, 7 53*9880d681SAndroid Build Coastguard Worker %shr = lshr i64 %b, 57 54*9880d681SAndroid Build Coastguard Worker %or = or i64 %shr, %shl 55*9880d681SAndroid Build Coastguard Worker ret i64 %or 56*9880d681SAndroid Build Coastguard Worker} 57*9880d681SAndroid Build Coastguard Worker 58*9880d681SAndroid Build Coastguard Worker;uint64_t lshift63(uint64_t a, uint64_t b) 59*9880d681SAndroid Build Coastguard Worker;{ 60*9880d681SAndroid Build Coastguard Worker; return (a << 63) | (b >> 1); 61*9880d681SAndroid Build Coastguard Worker;} 62*9880d681SAndroid Build Coastguard Worker 63*9880d681SAndroid Build Coastguard Worker; CHECK: lshift63: 64*9880d681SAndroid Build Coastguard Worker; CHECK: shlq $63, {{.*}} 65*9880d681SAndroid Build Coastguard Worker; CHECK-NEXT: shrq {{.*}} 66*9880d681SAndroid Build Coastguard Worker; CHECK-NEXT: leaq ({{.*}},{{.*}}), {{.*}} 67*9880d681SAndroid Build Coastguard Worker 68*9880d681SAndroid Build Coastguard Workerdefine i64 @lshift63(i64 %a, i64 %b) nounwind readnone uwtable { 69*9880d681SAndroid Build Coastguard Workerentry: 70*9880d681SAndroid Build Coastguard Worker %shl = shl i64 %a, 63 71*9880d681SAndroid Build Coastguard Worker %shr = lshr i64 %b, 1 72*9880d681SAndroid Build Coastguard Worker %or = or i64 %shr, %shl 73*9880d681SAndroid Build Coastguard Worker ret i64 %or 74*9880d681SAndroid Build Coastguard Worker} 75