[AArch64][NFC] NFC for const vector as Instruction operand (#116790)
[llvm-project.git] / llvm / test / Transforms / InstCombine / fneg-as-int.ll
blobf8d88b4f238f27df9fbb32c370d29f26cbd893d1
1 ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 2
2 ; RUN: opt -S -passes=instcombine %s | FileCheck %s
4 define float @fneg_as_int_f32_castback_noimplicitfloat(float %val) noimplicitfloat {
5 ; CHECK-LABEL: define float @fneg_as_int_f32_castback_noimplicitfloat
6 ; CHECK-SAME: (float [[VAL:%.*]]) #[[ATTR0:[0-9]+]] {
7 ; CHECK-NEXT:    [[BITCAST:%.*]] = bitcast float [[VAL]] to i32
8 ; CHECK-NEXT:    [[XOR:%.*]] = xor i32 [[BITCAST]], -2147483648
9 ; CHECK-NEXT:    [[FNEG:%.*]] = bitcast i32 [[XOR]] to float
10 ; CHECK-NEXT:    ret float [[FNEG]]
12   %bitcast = bitcast float %val to i32
13   %xor = xor i32 %bitcast, -2147483648
14   %fneg = bitcast i32 %xor to float
15   ret float %fneg
18 define <2 x i32> @fneg_as_int_v2f32_noimplicitfloat(<2 x float> %x) noimplicitfloat {
19 ; CHECK-LABEL: define <2 x i32> @fneg_as_int_v2f32_noimplicitfloat
20 ; CHECK-SAME: (<2 x float> [[X:%.*]]) #[[ATTR0]] {
21 ; CHECK-NEXT:    [[BC:%.*]] = bitcast <2 x float> [[X]] to <2 x i32>
22 ; CHECK-NEXT:    [[XOR:%.*]] = xor <2 x i32> [[BC]], splat (i32 -2147483648)
23 ; CHECK-NEXT:    ret <2 x i32> [[XOR]]
25   %bc = bitcast <2 x float> %x to <2 x i32>
26   %xor = xor <2 x i32> %bc, <i32 -2147483648, i32 -2147483648>
27   ret <2 x i32> %xor
30 define float @fneg_as_int_f32_castback(float %val) {
31 ; CHECK-LABEL: define float @fneg_as_int_f32_castback
32 ; CHECK-SAME: (float [[VAL:%.*]]) {
33 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg float [[VAL]]
34 ; CHECK-NEXT:    ret float [[TMP1]]
36   %bitcast = bitcast float %val to i32
37   %xor = xor i32 %bitcast, -2147483648
38   %fneg = bitcast i32 %xor to float
39   ret float %fneg
42 define float @not_fneg_as_int_f32_castback_wrongconst(float %val) {
43 ; CHECK-LABEL: define float @not_fneg_as_int_f32_castback_wrongconst
44 ; CHECK-SAME: (float [[VAL:%.*]]) {
45 ; CHECK-NEXT:    [[BITCAST:%.*]] = bitcast float [[VAL]] to i32
46 ; CHECK-NEXT:    [[XOR:%.*]] = xor i32 [[BITCAST]], -2147483647
47 ; CHECK-NEXT:    [[FNEG:%.*]] = bitcast i32 [[XOR]] to float
48 ; CHECK-NEXT:    ret float [[FNEG]]
50   %bitcast = bitcast float %val to i32
51   %xor = xor i32 %bitcast, -2147483647
52   %fneg = bitcast i32 %xor to float
53   ret float %fneg
56 define float @fneg_as_int_f32_castback_multi_use(float %val, ptr %ptr) {
57 ; CHECK-LABEL: define float @fneg_as_int_f32_castback_multi_use
58 ; CHECK-SAME: (float [[VAL:%.*]], ptr [[PTR:%.*]]) {
59 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg float [[VAL]]
60 ; CHECK-NEXT:    store float [[TMP1]], ptr [[PTR]], align 4
61 ; CHECK-NEXT:    ret float [[TMP1]]
63   %bitcast = bitcast float %val to i32
64   %xor = xor i32 %bitcast, -2147483648
65   store i32 %xor, ptr %ptr
66   %fneg = bitcast i32 %xor to float
67   ret float %fneg
70 define i64 @fneg_as_int_f64(double %x) {
71 ; CHECK-LABEL: define i64 @fneg_as_int_f64
72 ; CHECK-SAME: (double [[X:%.*]]) {
73 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg double [[X]]
74 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast double [[TMP1]] to i64
75 ; CHECK-NEXT:    ret i64 [[XOR]]
77   %bc = bitcast double %x to i64
78   %xor = xor i64 %bc, -9223372036854775808
79   ret i64 %xor
82 define <2 x i64> @fneg_as_int_v2f64(<2 x double> %x) {
83 ; CHECK-LABEL: define <2 x i64> @fneg_as_int_v2f64
84 ; CHECK-SAME: (<2 x double> [[X:%.*]]) {
85 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg <2 x double> [[X]]
86 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast <2 x double> [[TMP1]] to <2 x i64>
87 ; CHECK-NEXT:    ret <2 x i64> [[XOR]]
89   %bc = bitcast <2 x double> %x to <2 x i64>
90   %xor = xor <2 x i64> %bc, <i64 -9223372036854775808, i64 -9223372036854775808>
91   ret <2 x i64> %xor
94 define i64 @fneg_as_int_f64_swap(double %x) {
95 ; CHECK-LABEL: define i64 @fneg_as_int_f64_swap
96 ; CHECK-SAME: (double [[X:%.*]]) {
97 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg double [[X]]
98 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast double [[TMP1]] to i64
99 ; CHECK-NEXT:    ret i64 [[XOR]]
101   %bc = bitcast double %x to i64
102   %xor = xor i64 -9223372036854775808, %bc
103   ret i64 %xor
106 define i32 @fneg_as_int_f32(float %x) {
107 ; CHECK-LABEL: define i32 @fneg_as_int_f32
108 ; CHECK-SAME: (float [[X:%.*]]) {
109 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg float [[X]]
110 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast float [[TMP1]] to i32
111 ; CHECK-NEXT:    ret i32 [[XOR]]
113   %bc = bitcast float %x to i32
114   %xor = xor i32 %bc, -2147483648
115   ret i32 %xor
118 define <2 x i32> @fneg_as_int_v2f32(<2 x float> %x) {
119 ; CHECK-LABEL: define <2 x i32> @fneg_as_int_v2f32
120 ; CHECK-SAME: (<2 x float> [[X:%.*]]) {
121 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg <2 x float> [[X]]
122 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast <2 x float> [[TMP1]] to <2 x i32>
123 ; CHECK-NEXT:    ret <2 x i32> [[XOR]]
125   %bc = bitcast <2 x float> %x to <2 x i32>
126   %xor = xor <2 x i32> %bc, <i32 -2147483648, i32 -2147483648>
127   ret <2 x i32> %xor
130 define <2 x i32> @not_fneg_as_int_v2f32_nonsplat(<2 x float> %x) {
131 ; CHECK-LABEL: define <2 x i32> @not_fneg_as_int_v2f32_nonsplat
132 ; CHECK-SAME: (<2 x float> [[X:%.*]]) {
133 ; CHECK-NEXT:    [[BC:%.*]] = bitcast <2 x float> [[X]] to <2 x i32>
134 ; CHECK-NEXT:    [[XOR:%.*]] = xor <2 x i32> [[BC]], <i32 -2147483648, i32 -2147483647>
135 ; CHECK-NEXT:    ret <2 x i32> [[XOR]]
137   %bc = bitcast <2 x float> %x to <2 x i32>
138   %xor = xor <2 x i32> %bc, <i32 -2147483648, i32 -2147483647>
139   ret <2 x i32> %xor
142 define <3 x i32> @fneg_as_int_v3f32_poison(<3 x float> %x) {
143 ; CHECK-LABEL: define <3 x i32> @fneg_as_int_v3f32_poison
144 ; CHECK-SAME: (<3 x float> [[X:%.*]]) {
145 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg <3 x float> [[X]]
146 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast <3 x float> [[TMP1]] to <3 x i32>
147 ; CHECK-NEXT:    ret <3 x i32> [[XOR]]
149   %bc = bitcast <3 x float> %x to <3 x i32>
150   %xor = xor <3 x i32> %bc, <i32 -2147483648, i32 poison, i32 -2147483648>
151   ret <3 x i32> %xor
154 ; Make sure that only a bitcast is transformed.
155 define i64 @fneg_as_int_f64_not_bitcast(double %x) {
156 ; CHECK-LABEL: define i64 @fneg_as_int_f64_not_bitcast
157 ; CHECK-SAME: (double [[X:%.*]]) {
158 ; CHECK-NEXT:    [[BC:%.*]] = fptoui double [[X]] to i64
159 ; CHECK-NEXT:    [[XOR:%.*]] = xor i64 [[BC]], -9223372036854775808
160 ; CHECK-NEXT:    ret i64 [[XOR]]
162   %bc = fptoui double %x to i64
163   %xor = xor i64 %bc, -9223372036854775808
164   ret i64 %xor
167 define float @not_fneg_as_int_f32_bitcast_from_v2f16(<2 x half> %val) {
168 ; CHECK-LABEL: define float @not_fneg_as_int_f32_bitcast_from_v2f16
169 ; CHECK-SAME: (<2 x half> [[VAL:%.*]]) {
170 ; CHECK-NEXT:    [[BITCAST:%.*]] = bitcast <2 x half> [[VAL]] to i32
171 ; CHECK-NEXT:    [[XOR:%.*]] = xor i32 [[BITCAST]], -2147483648
172 ; CHECK-NEXT:    [[FNEG:%.*]] = bitcast i32 [[XOR]] to float
173 ; CHECK-NEXT:    ret float [[FNEG]]
175   %bitcast = bitcast <2 x half> %val to i32
176   %xor = xor i32 %bitcast, -2147483648
177   %fneg = bitcast i32 %xor to float
178   ret float %fneg
181 define float @not_fneg_as_int_f32_bitcast_from_v2i16(<2 x i16> %val) {
182 ; CHECK-LABEL: define float @not_fneg_as_int_f32_bitcast_from_v2i16
183 ; CHECK-SAME: (<2 x i16> [[VAL:%.*]]) {
184 ; CHECK-NEXT:    [[BITCAST:%.*]] = bitcast <2 x i16> [[VAL]] to i32
185 ; CHECK-NEXT:    [[XOR:%.*]] = xor i32 [[BITCAST]], -2147483648
186 ; CHECK-NEXT:    [[FNEG:%.*]] = bitcast i32 [[XOR]] to float
187 ; CHECK-NEXT:    ret float [[FNEG]]
189   %bitcast = bitcast <2 x i16> %val to i32
190   %xor = xor i32 %bitcast, -2147483648
191   %fneg = bitcast i32 %xor to float
192   ret float %fneg
195 define i128 @fneg_as_int_fp128_f64_mask(fp128 %x) {
196 ; CHECK-LABEL: define i128 @fneg_as_int_fp128_f64_mask
197 ; CHECK-SAME: (fp128 [[X:%.*]]) {
198 ; CHECK-NEXT:    [[BC:%.*]] = bitcast fp128 [[X]] to i128
199 ; CHECK-NEXT:    [[XOR:%.*]] = xor i128 [[BC]], -9223372036854775808
200 ; CHECK-NEXT:    ret i128 [[XOR]]
202   %bc = bitcast fp128 %x to i128
203   %xor = xor i128 %bc, -9223372036854775808
204   ret i128 %xor
207 define i128 @fneg_as_int_fp128_f128_mask(fp128 %x) {
208 ; CHECK-LABEL: define i128 @fneg_as_int_fp128_f128_mask
209 ; CHECK-SAME: (fp128 [[X:%.*]]) {
210 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg fp128 [[X]]
211 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast fp128 [[TMP1]] to i128
212 ; CHECK-NEXT:    ret i128 [[XOR]]
214   %bc = bitcast fp128 %x to i128
215   %xor = xor i128 %bc, -170141183460469231731687303715884105728
216   ret i128 %xor
219 define i16 @fneg_as_int_f16(half %x) {
220 ; CHECK-LABEL: define i16 @fneg_as_int_f16
221 ; CHECK-SAME: (half [[X:%.*]]) {
222 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg half [[X]]
223 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast half [[TMP1]] to i16
224 ; CHECK-NEXT:    ret i16 [[XOR]]
226   %bc = bitcast half %x to i16
227   %xor = xor i16 %bc, -32768
228   ret i16 %xor
231 define <2 x i16> @fneg_as_int_v2f16(<2 x half> %x) {
232 ; CHECK-LABEL: define <2 x i16> @fneg_as_int_v2f16
233 ; CHECK-SAME: (<2 x half> [[X:%.*]]) {
234 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg <2 x half> [[X]]
235 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast <2 x half> [[TMP1]] to <2 x i16>
236 ; CHECK-NEXT:    ret <2 x i16> [[XOR]]
238   %bc = bitcast <2 x half> %x to <2 x i16>
239   %xor = xor <2 x i16> %bc, <i16 -32768, i16 -32768>
240   ret <2 x i16> %xor
243 define i16 @fneg_as_int_bf16(bfloat %x) {
244 ; CHECK-LABEL: define i16 @fneg_as_int_bf16
245 ; CHECK-SAME: (bfloat [[X:%.*]]) {
246 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg bfloat [[X]]
247 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast bfloat [[TMP1]] to i16
248 ; CHECK-NEXT:    ret i16 [[XOR]]
250   %bc = bitcast bfloat %x to i16
251   %xor = xor i16 %bc, -32768
252   ret i16 %xor
255 define <2 x i16> @fneg_as_int_v2bf16(<2 x bfloat> %x) {
256 ; CHECK-LABEL: define <2 x i16> @fneg_as_int_v2bf16
257 ; CHECK-SAME: (<2 x bfloat> [[X:%.*]]) {
258 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg <2 x bfloat> [[X]]
259 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast <2 x bfloat> [[TMP1]] to <2 x i16>
260 ; CHECK-NEXT:    ret <2 x i16> [[XOR]]
262   %bc = bitcast <2 x bfloat> %x to <2 x i16>
263   %xor = xor <2 x i16> %bc, <i16 -32768, i16 -32768>
264   ret <2 x i16> %xor
267 define i80 @fneg_as_int_x86_fp80_f64_mask(x86_fp80 %x) {
268 ; CHECK-LABEL: define i80 @fneg_as_int_x86_fp80_f64_mask
269 ; CHECK-SAME: (x86_fp80 [[X:%.*]]) {
270 ; CHECK-NEXT:    [[TMP1:%.*]] = fneg x86_fp80 [[X]]
271 ; CHECK-NEXT:    [[XOR:%.*]] = bitcast x86_fp80 [[TMP1]] to i80
272 ; CHECK-NEXT:    ret i80 [[XOR]]
274   %bc = bitcast x86_fp80 %x to i80
275   %xor = xor i80 %bc, -604462909807314587353088
276   ret i80 %xor
279 define i128 @fneg_as_int_ppc_fp128_f64_mask(ppc_fp128 %x) {
280 ; CHECK-LABEL: define i128 @fneg_as_int_ppc_fp128_f64_mask
281 ; CHECK-SAME: (ppc_fp128 [[X:%.*]]) {
282 ; CHECK-NEXT:    [[BC:%.*]] = bitcast ppc_fp128 [[X]] to i128
283 ; CHECK-NEXT:    [[XOR:%.*]] = xor i128 [[BC]], -9223372036854775808
284 ; CHECK-NEXT:    ret i128 [[XOR]]
286   %bc = bitcast ppc_fp128 %x to i128
287   %xor = xor i128 %bc, -9223372036854775808
288   ret i128 %xor
291 define i128 @fneg_as_int_ppc_fp128_f128_mask(ppc_fp128 %x) {
292 ; CHECK-LABEL: define i128 @fneg_as_int_ppc_fp128_f128_mask
293 ; CHECK-SAME: (ppc_fp128 [[X:%.*]]) {
294 ; CHECK-NEXT:    [[BC:%.*]] = bitcast ppc_fp128 [[X]] to i128
295 ; CHECK-NEXT:    [[XOR:%.*]] = xor i128 [[BC]], -170141183460469231731687303715884105728
296 ; CHECK-NEXT:    ret i128 [[XOR]]
298   %bc = bitcast ppc_fp128 %x to i128
299   %xor = xor i128 %bc, -170141183460469231731687303715884105728
300   ret i128 %xor