1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 2 2; RUN: llc < %s -mtriple=x86_64-unknown -mattr=+cf -verify-machineinstrs | FileCheck %s 3; RUN: llc < %s -mtriple=x86_64-unknown -mattr=+cf -x86-cmov-converter=false -verify-machineinstrs | FileCheck %s 4 5define i8 @cfcmov8rr(i8 %0) { 6; CHECK-LABEL: cfcmov8rr: 7; CHECK: # %bb.0: 8; CHECK-NEXT: cmpb $1, %dil 9; CHECK-NEXT: cfcmovel %edi, %eax 10; CHECK-NEXT: # kill: def $al killed $al killed $eax 11; CHECK-NEXT: retq 12 %2 = icmp eq i8 %0, 1 13 %3 = select i1 %2, i8 %0, i8 0 14 ret i8 %3 15} 16 17define i16 @cfcmov16rr(i16 %0) { 18; CHECK-LABEL: cfcmov16rr: 19; CHECK: # %bb.0: 20; CHECK-NEXT: cmpw $1, %di 21; CHECK-NEXT: cfcmovnel %edi, %eax 22; CHECK-NEXT: # kill: def $ax killed $ax killed $eax 23; CHECK-NEXT: retq 24 %2 = icmp ne i16 %0, 1 25 %3 = select i1 %2, i16 %0, i16 0 26 ret i16 %3 27} 28 29define i32 @cfcmov32rr(i32 %0) { 30; CHECK-LABEL: cfcmov32rr: 31; CHECK: # %bb.0: 32; CHECK-NEXT: cmpl $2, %edi 33; CHECK-NEXT: cfcmovael %edi, %eax 34; CHECK-NEXT: retq 35 %2 = icmp ugt i32 %0, 1 36 %3 = select i1 %2, i32 %0, i32 0 37 ret i32 %3 38} 39 40define i64 @cfcmov64rr(i64 %0) { 41; CHECK-LABEL: cfcmov64rr: 42; CHECK: # %bb.0: 43; CHECK-NEXT: testq %rdi, %rdi 44; CHECK-NEXT: cfcmoveq %rdi, %rax 45; CHECK-NEXT: retq 46 %2 = icmp ult i64 %0, 1 47 %3 = select i1 %2, i64 %0, i64 0 48 ret i64 %3 49} 50 51define i8 @cfcmov8rr_inv(i8 %0) { 52; CHECK-LABEL: cfcmov8rr_inv: 53; CHECK: # %bb.0: 54; CHECK-NEXT: cmpb $1, %dil 55; CHECK-NEXT: cfcmovnel %edi, %eax 56; CHECK-NEXT: # kill: def $al killed $al killed $eax 57; CHECK-NEXT: retq 58 %2 = icmp eq i8 %0, 1 59 %3 = select i1 %2, i8 0, i8 %0 60 ret i8 %3 61} 62 63define i16 @cfcmov16rr_inv(i16 %0) { 64; CHECK-LABEL: cfcmov16rr_inv: 65; CHECK: # %bb.0: 66; CHECK-NEXT: cmpw $1, %di 67; CHECK-NEXT: cfcmovel %edi, %eax 68; CHECK-NEXT: # kill: def $ax killed $ax killed $eax 69; CHECK-NEXT: retq 70 %2 = icmp ne i16 %0, 1 71 %3 = select i1 %2, i16 0, i16 %0 72 ret i16 %3 73} 74 75define i32 @cfcmov32rr_inv(i32 %0) { 76; CHECK-LABEL: cfcmov32rr_inv: 77; CHECK: # %bb.0: 78; CHECK-NEXT: cmpl $2, %edi 79; CHECK-NEXT: cfcmovbl %edi, %eax 80; CHECK-NEXT: retq 81 %2 = icmp ugt i32 %0, 1 82 %3 = select i1 %2, i32 0, i32 %0 83 ret i32 %3 84} 85 86define i64 @cfcmov64rr_inv(i64 %0) { 87; CHECK-LABEL: cfcmov64rr_inv: 88; CHECK: # %bb.0: 89; CHECK-NEXT: cmpq $2, %rdi 90; CHECK-NEXT: cfcmovaeq %rdi, %rax 91; CHECK-NEXT: retq 92 %2 = icmp ule i64 %0, 1 93 %3 = select i1 %2, i64 0, i64 %0 94 ret i64 %3 95} 96 97define void @cfcmov16mr(ptr %p, i16 %0) { 98; CHECK-LABEL: cfcmov16mr: 99; CHECK: # %bb.0: 100; CHECK-NEXT: movzwl (%rdi), %eax 101; CHECK-NEXT: cmpw %ax, %si 102; CHECK-NEXT: cfcmovlew %si, (%rdi) 103; CHECK-NEXT: retq 104 %2 = load i16, ptr %p, align 2 105 %3 = icmp sgt i16 %0, %2 106 %4 = select i1 %3, i16 %2, i16 %0 107 store i16 %4, ptr %p, align 2 108 ret void 109} 110 111define void @cfcmov32mr(ptr %p, i32 %0) { 112; CHECK-LABEL: cfcmov32mr: 113; CHECK: # %bb.0: 114; CHECK-NEXT: cmpl (%rdi), %esi 115; CHECK-NEXT: cfcmovgl %esi, (%rdi) 116; CHECK-NEXT: retq 117 %2 = load i32, ptr %p, align 4 118 %3 = call i32 @llvm.smax.i32(i32 %0, i32 %2) 119 store i32 %3, ptr %p, align 4 120 ret void 121} 122 123define void @cfcmov64mr(ptr %p, i64 %0) { 124; CHECK-LABEL: cfcmov64mr: 125; CHECK: # %bb.0: 126; CHECK-NEXT: cmpq (%rdi), %rsi 127; CHECK-NEXT: cfcmovgq %rsi, (%rdi) 128; CHECK-NEXT: retq 129 %2 = load i64, ptr %p, align 8 130 %3 = icmp sgt i64 %0, %2 131 %4 = select i1 %3, i64 %0, i64 %2 132 store i64 %4, ptr %p, align 8 133 ret void 134} 135 136define void @volatileload(ptr %p, i32 %0) { 137; CHECK-LABEL: volatileload: 138; CHECK: # %bb.0: 139; CHECK-NEXT: movl (%rdi), %eax 140; CHECK-NEXT: cmpl %eax, %esi 141; CHECK-NEXT: cmovbl %esi, %eax 142; CHECK-NEXT: movl %eax, (%rdi) 143; CHECK-NEXT: retq 144 %2 = load volatile i32, ptr %p, align 4 145 %3 = call i32 @llvm.umin.i32(i32 %0, i32 %2) 146 store i32 %3, ptr %p, align 4 147 ret void 148} 149 150define void @atomicstore(ptr %p, i64 %0) { 151; CHECK-LABEL: atomicstore: 152; CHECK: # %bb.0: 153; CHECK-NEXT: movq (%rdi), %rax 154; CHECK-NEXT: cmpq %rax, %rsi 155; CHECK-NEXT: cmovaq %rsi, %rax 156; CHECK-NEXT: movq %rax, (%rdi) 157; CHECK-NEXT: retq 158 %2 = load i64, ptr %p, align 8 159 %3 = icmp ugt i64 %0, %2 160 %4 = select i1 %3, i64 %0, i64 %2 161 store atomic i64 %4, ptr %p unordered, align 8 162 ret void 163} 164 165define void @loadstorediffptr(ptr %p, i32 %0) { 166; CHECK-LABEL: loadstorediffptr: 167; CHECK: # %bb.0: 168; CHECK-NEXT: movl (%rdi), %eax 169; CHECK-NEXT: cmpl %eax, %esi 170; CHECK-NEXT: cmovbel %eax, %esi 171; CHECK-NEXT: movl %esi, 4(%rdi) 172; CHECK-NEXT: retq 173 %2 = getelementptr [2 x i32], ptr %p, i32 0, i32 0 174 %3 = load i32, ptr %2, align 4 175 %4 = icmp ule i32 %0, %3 176 %5 = select i1 %4, i32 %3, i32 %0 177 %6 = getelementptr [2 x i32], ptr %p, i32 0, i32 1 178 store i32 %5, ptr %6, align 4 179 ret void 180} 181 182declare i32 @llvm.smax.i32(i32, i32) 183declare i32 @llvm.umin.i32(i32, i32) 184