1 ; Test 64-bit unsigned comparison in which the second operand is a variable. 2 ; 3 ; RUN: llc < %s -mtriple=s390x-linux-gnu | FileCheck %s 4 5 ; Check CLGR. 6 define double @f1(double %a, double %b, i64 %i1, i64 %i2) { 7 ; CHECK-LABEL: f1: 8 ; CHECK: clgrjl %r2, %r3 9 ; CHECK: ldr %f0, %f2 10 ; CHECK: br %r14 11 %cond = icmp ult i64 %i1, %i2 12 %res = select i1 %cond, double %a, double %b 13 ret double %res 14 } 15 16 ; Check CLG with no displacement. 17 define double @f2(double %a, double %b, i64 %i1, i64 *%ptr) { 18 ; CHECK-LABEL: f2: 19 ; CHECK: clg %r2, 0(%r3) 20 ; CHECK-NEXT: jl 21 ; CHECK: ldr %f0, %f2 22 ; CHECK: br %r14 23 %i2 = load i64 , i64 *%ptr 24 %cond = icmp ult i64 %i1, %i2 25 %res = select i1 %cond, double %a, double %b 26 ret double %res 27 } 28 29 ; Check the high end of the aligned CLG range. 30 define double @f3(double %a, double %b, i64 %i1, i64 *%base) { 31 ; CHECK-LABEL: f3: 32 ; CHECK: clg %r2, 524280(%r3) 33 ; CHECK-NEXT: jl 34 ; CHECK: ldr %f0, %f2 35 ; CHECK: br %r14 36 %ptr = getelementptr i64, i64 *%base, i64 65535 37 %i2 = load i64 , i64 *%ptr 38 %cond = icmp ult i64 %i1, %i2 39 %res = select i1 %cond, double %a, double %b 40 ret double %res 41 } 42 43 ; Check the next doubleword up, which needs separate address logic. 44 ; Other sequences besides this one would be OK. 45 define double @f4(double %a, double %b, i64 %i1, i64 *%base) { 46 ; CHECK-LABEL: f4: 47 ; CHECK: agfi %r3, 524288 48 ; CHECK: clg %r2, 0(%r3) 49 ; CHECK-NEXT: jl 50 ; CHECK: ldr %f0, %f2 51 ; CHECK: br %r14 52 %ptr = getelementptr i64, i64 *%base, i64 65536 53 %i2 = load i64 , i64 *%ptr 54 %cond = icmp ult i64 %i1, %i2 55 %res = select i1 %cond, double %a, double %b 56 ret double %res 57 } 58 59 ; Check the high end of the negative aligned CLG range. 60 define double @f5(double %a, double %b, i64 %i1, i64 *%base) { 61 ; CHECK-LABEL: f5: 62 ; CHECK: clg %r2, -8(%r3) 63 ; CHECK-NEXT: jl 64 ; CHECK: ldr %f0, %f2 65 ; CHECK: br %r14 66 %ptr = getelementptr i64, i64 *%base, i64 -1 67 %i2 = load i64 , i64 *%ptr 68 %cond = icmp ult i64 %i1, %i2 69 %res = select i1 %cond, double %a, double %b 70 ret double %res 71 } 72 73 ; Check the low end of the CLG range. 74 define double @f6(double %a, double %b, i64 %i1, i64 *%base) { 75 ; CHECK-LABEL: f6: 76 ; CHECK: clg %r2, -524288(%r3) 77 ; CHECK-NEXT: jl 78 ; CHECK: ldr %f0, %f2 79 ; CHECK: br %r14 80 %ptr = getelementptr i64, i64 *%base, i64 -65536 81 %i2 = load i64 , i64 *%ptr 82 %cond = icmp ult i64 %i1, %i2 83 %res = select i1 %cond, double %a, double %b 84 ret double %res 85 } 86 87 ; Check the next doubleword down, which needs separate address logic. 88 ; Other sequences besides this one would be OK. 89 define double @f7(double %a, double %b, i64 %i1, i64 *%base) { 90 ; CHECK-LABEL: f7: 91 ; CHECK: agfi %r3, -524296 92 ; CHECK: clg %r2, 0(%r3) 93 ; CHECK-NEXT: jl 94 ; CHECK: ldr %f0, %f2 95 ; CHECK: br %r14 96 %ptr = getelementptr i64, i64 *%base, i64 -65537 97 %i2 = load i64 , i64 *%ptr 98 %cond = icmp ult i64 %i1, %i2 99 %res = select i1 %cond, double %a, double %b 100 ret double %res 101 } 102 103 ; Check that CLG allows an index. 104 define double @f8(double %a, double %b, i64 %i1, i64 %base, i64 %index) { 105 ; CHECK-LABEL: f8: 106 ; CHECK: clg %r2, 524280({{%r4,%r3|%r3,%r4}}) 107 ; CHECK-NEXT: jl 108 ; CHECK: ldr %f0, %f2 109 ; CHECK: br %r14 110 %add1 = add i64 %base, %index 111 %add2 = add i64 %add1, 524280 112 %ptr = inttoptr i64 %add2 to i64 * 113 %i2 = load i64 , i64 *%ptr 114 %cond = icmp ult i64 %i1, %i2 115 %res = select i1 %cond, double %a, double %b 116 ret double %res 117 } 118 119 ; Check the comparison can be reversed if that allows CLG to be used. 120 define double @f9(double %a, double %b, i64 %i2, i64 *%ptr) { 121 ; CHECK-LABEL: f9: 122 ; CHECK: clg %r2, 0(%r3) 123 ; CHECK-NEXT: jh {{\.L.*}} 124 ; CHECK: ldr %f0, %f2 125 ; CHECK: br %r14 126 %i1 = load i64 , i64 *%ptr 127 %cond = icmp ult i64 %i1, %i2 128 %res = select i1 %cond, double %a, double %b 129 ret double %res 130 } 131