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 6define 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 17define 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 28define <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 39define <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 50define 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 62define 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 73define <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 84define <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 95define 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 106define 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 117define <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 128define <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 139define 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 150define 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 161define <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 173define <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