1 ; RUN: opt < %s -instsimplify -S | FileCheck %s 2 3 ; Cycle through commuted variants where one operand of fcmp ord/uno is 4 ; known not-a-NAN and the other is repeated in the logically-connected fcmp. 5 6 define i1 @ord1(float %x, float %y) { 7 ; CHECK-LABEL: @ord1( 8 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp ord float %x, %y 9 ; CHECK-NEXT: ret i1 [[CMP2]] 10 ; 11 %cmp1 = fcmp ord float 0.0, %x 12 %cmp2 = fcmp ord float %x, %y 13 %r = and i1 %cmp1, %cmp2 14 ret i1 %r 15 } 16 17 define i1 @ord2(double %x, double %y) { 18 ; CHECK-LABEL: @ord2( 19 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp ord double %y, %x 20 ; CHECK-NEXT: ret i1 [[CMP2]] 21 ; 22 %cmp1 = fcmp ord double 42.0, %x 23 %cmp2 = fcmp ord double %y, %x 24 %r = and i1 %cmp1, %cmp2 25 ret i1 %r 26 } 27 28 define <2 x i1> @ord3(<2 x float> %x, <2 x float> %y) { 29 ; CHECK-LABEL: @ord3( 30 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp ord <2 x float> %x, %y 31 ; CHECK-NEXT: ret <2 x i1> [[CMP2]] 32 ; 33 %cmp1 = fcmp ord <2 x float> %x, zeroinitializer 34 %cmp2 = fcmp ord <2 x float> %x, %y 35 %r = and <2 x i1> %cmp1, %cmp2 36 ret <2 x i1> %r 37 } 38 39 define <2 x i1> @ord4(<2 x double> %x, <2 x double> %y) { 40 ; CHECK-LABEL: @ord4( 41 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp ord <2 x double> %y, %x 42 ; CHECK-NEXT: ret <2 x i1> [[CMP2]] 43 ; 44 %cmp1 = fcmp ord <2 x double> %x, <double 42.0, double 42.0> 45 %cmp2 = fcmp ord <2 x double> %y, %x 46 %r = and <2 x i1> %cmp1, %cmp2 47 ret <2 x i1> %r 48 } 49 50 define i1 @ord5(float %x, float %y) { 51 ; CHECK-LABEL: @ord5( 52 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp ord float %x, %y 53 ; CHECK-NEXT: ret i1 [[CMP1]] 54 ; 55 %nnan = fdiv nnan float %x, %y 56 %cmp1 = fcmp ord float %x, %y 57 %cmp2 = fcmp ord float %nnan, %x 58 %r = and i1 %cmp1, %cmp2 59 ret i1 %r 60 } 61 62 define i1 @ord6(double %x, double %y) { 63 ; CHECK-LABEL: @ord6( 64 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp ord double %y, %x 65 ; CHECK-NEXT: ret i1 [[CMP1]] 66 ; 67 %cmp1 = fcmp ord double %y, %x 68 %cmp2 = fcmp ord double 42.0, %x 69 %r = and i1 %cmp1, %cmp2 70 ret i1 %r 71 } 72 73 define <2 x i1> @ord7(<2 x float> %x, <2 x float> %y) { 74 ; CHECK-LABEL: @ord7( 75 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp ord <2 x float> %x, %y 76 ; CHECK-NEXT: ret <2 x i1> [[CMP1]] 77 ; 78 %cmp1 = fcmp ord <2 x float> %x, %y 79 %cmp2 = fcmp ord <2 x float> %x, zeroinitializer 80 %r = and <2 x i1> %cmp1, %cmp2 81 ret <2 x i1> %r 82 } 83 84 define <2 x i1> @ord8(<2 x double> %x, <2 x double> %y) { 85 ; CHECK-LABEL: @ord8( 86 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp ord <2 x double> %y, %x 87 ; CHECK-NEXT: ret <2 x i1> [[CMP1]] 88 ; 89 %cmp1 = fcmp ord <2 x double> %y, %x 90 %cmp2 = fcmp ord <2 x double> %x, <double 0.0, double 42.0> 91 %r = and <2 x i1> %cmp1, %cmp2 92 ret <2 x i1> %r 93 } 94 95 define i1 @uno1(float %x, float %y) { 96 ; CHECK-LABEL: @uno1( 97 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp uno float %x, %y 98 ; CHECK-NEXT: ret i1 [[CMP2]] 99 ; 100 %cmp1 = fcmp uno float 0.0, %x 101 %cmp2 = fcmp uno float %x, %y 102 %r = or i1 %cmp1, %cmp2 103 ret i1 %r 104 } 105 106 define i1 @uno2(double %x, double %y) { 107 ; CHECK-LABEL: @uno2( 108 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp uno double %y, %x 109 ; CHECK-NEXT: ret i1 [[CMP2]] 110 ; 111 %cmp1 = fcmp uno double 42.0, %x 112 %cmp2 = fcmp uno double %y, %x 113 %r = or i1 %cmp1, %cmp2 114 ret i1 %r 115 } 116 117 define <2 x i1> @uno3(<2 x float> %x, <2 x float> %y) { 118 ; CHECK-LABEL: @uno3( 119 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp uno <2 x float> %x, %y 120 ; CHECK-NEXT: ret <2 x i1> [[CMP2]] 121 ; 122 %cmp1 = fcmp uno <2 x float> %x, zeroinitializer 123 %cmp2 = fcmp uno <2 x float> %x, %y 124 %r = or <2 x i1> %cmp1, %cmp2 125 ret <2 x i1> %r 126 } 127 128 define <2 x i1> @uno4(<2 x double> %x, <2 x double> %y) { 129 ; CHECK-LABEL: @uno4( 130 ; CHECK-NEXT: [[CMP2:%.*]] = fcmp uno <2 x double> %y, %x 131 ; CHECK-NEXT: ret <2 x i1> [[CMP2]] 132 ; 133 %cmp1 = fcmp uno <2 x double> %x, <double 42.0, double 42.0> 134 %cmp2 = fcmp uno <2 x double> %y, %x 135 %r = or <2 x i1> %cmp1, %cmp2 136 ret <2 x i1> %r 137 } 138 139 define i1 @uno5(float %x, float %y) { 140 ; CHECK-LABEL: @uno5( 141 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp uno float %x, %y 142 ; CHECK-NEXT: ret i1 [[CMP1]] 143 ; 144 %cmp1 = fcmp uno float %x, %y 145 %cmp2 = fcmp uno float 0.0, %x 146 %r = or i1 %cmp1, %cmp2 147 ret i1 %r 148 } 149 150 define i1 @uno6(double %x, double %y) { 151 ; CHECK-LABEL: @uno6( 152 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp uno double %y, %x 153 ; CHECK-NEXT: ret i1 [[CMP1]] 154 ; 155 %cmp1 = fcmp uno double %y, %x 156 %cmp2 = fcmp uno double 42.0, %x 157 %r = or i1 %cmp1, %cmp2 158 ret i1 %r 159 } 160 161 define <2 x i1> @uno7(<2 x float> %x, <2 x float> %y) { 162 ; CHECK-LABEL: @uno7( 163 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp uno <2 x float> %x, %y 164 ; CHECK-NEXT: ret <2 x i1> [[CMP1]] 165 ; 166 %nnan = fdiv nnan <2 x float> %x, %y 167 %cmp1 = fcmp uno <2 x float> %x, %y 168 %cmp2 = fcmp uno <2 x float> %x, %nnan 169 %r = or <2 x i1> %cmp1, %cmp2 170 ret <2 x i1> %r 171 } 172 173 define <2 x i1> @uno8(<2 x double> %x, <2 x double> %y) { 174 ; CHECK-LABEL: @uno8( 175 ; CHECK-NEXT: [[CMP1:%.*]] = fcmp uno <2 x double> %y, %x 176 ; CHECK-NEXT: ret <2 x i1> [[CMP1]] 177 ; 178 %cmp1 = fcmp uno <2 x double> %y, %x 179 %cmp2 = fcmp uno <2 x double> %x, <double 0x7ff0000000000000, double 42.0> 180 %r = or <2 x i1> %cmp1, %cmp2 181 ret <2 x i1> %r 182 } 183 184