549 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py2; RUN: llc -mtriple=aarch64-linux-gnu -verify-machineinstrs -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-NO163; RUN: llc -mtriple=aarch64-linux-gnu -mattr=+fullfp16 -verify-machineinstrs -o - %s | FileCheck %s --check-prefixes=CHECK,CHECK-FP164 5define <2 x i32> @test1(<2 x float> %f) {6; CHECK-LABEL: test1:7; CHECK: // %bb.0:8; CHECK-NEXT: fcvtzs v0.2s, v0.2s, #49; CHECK-NEXT: ret10 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>11 %vcvt.i = fptosi <2 x float> %mul.i to <2 x i32>12 ret <2 x i32> %vcvt.i13}14 15define <4 x i32> @test2(<4 x float> %f) {16; CHECK-LABEL: test2:17; CHECK: // %bb.0:18; CHECK-NEXT: fcvtzs v0.4s, v0.4s, #319; CHECK-NEXT: ret20 %mul.i = fmul <4 x float> %f, <float 8.000000e+00, float 8.000000e+00, float 8.000000e+00, float 8.000000e+00>21 %vcvt.i = fptosi <4 x float> %mul.i to <4 x i32>22 ret <4 x i32> %vcvt.i23}24 25define <2 x i64> @test3(<2 x double> %d) {26; CHECK-LABEL: test3:27; CHECK: // %bb.0:28; CHECK-NEXT: fcvtzs v0.2d, v0.2d, #529; CHECK-NEXT: ret30 %mul.i = fmul <2 x double> %d, <double 32.000000e+00, double 32.000000e+00>31 %vcvt.i = fptosi <2 x double> %mul.i to <2 x i64>32 ret <2 x i64> %vcvt.i33}34 35; Truncate double to i3236define <2 x i32> @test4(<2 x double> %d) {37; CHECK-LABEL: test4:38; CHECK: // %bb.0:39; CHECK-NEXT: fcvtzs v0.2d, v0.2d, #440; CHECK-NEXT: xtn v0.2s, v0.2d41; CHECK-NEXT: ret42 %mul.i = fmul <2 x double> %d, <double 16.000000e+00, double 16.000000e+00>43 %vcvt.i = fptosi <2 x double> %mul.i to <2 x i32>44 ret <2 x i32> %vcvt.i45}46 47; Truncate float to i1648define <2 x i16> @test5(<2 x float> %f) {49; CHECK-LABEL: test5:50; CHECK: // %bb.0:51; CHECK-NEXT: fcvtzs v0.2s, v0.2s, #452; CHECK-NEXT: ret53 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>54 %vcvt.i = fptosi <2 x float> %mul.i to <2 x i16>55 ret <2 x i16> %vcvt.i56}57 58; Don't convert float to i6459define <2 x i64> @test6(<2 x float> %f) {60; CHECK-LABEL: test6:61; CHECK: // %bb.0:62; CHECK-NEXT: fmov v1.2s, #16.0000000063; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s64; CHECK-NEXT: fcvtl v0.2d, v0.2s65; CHECK-NEXT: fcvtzs v0.2d, v0.2d66; CHECK-NEXT: ret67 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>68 %vcvt.i = fptosi <2 x float> %mul.i to <2 x i64>69 ret <2 x i64> %vcvt.i70}71 72define <2 x i32> @test7(<2 x float> %f) {73; CHECK-LABEL: test7:74; CHECK: // %bb.0:75; CHECK-NEXT: fcvtzu v0.2s, v0.2s, #476; CHECK-NEXT: ret77 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>78 %vcvt.i = fptoui <2 x float> %mul.i to <2 x i32>79 ret <2 x i32> %vcvt.i80}81 82; Test which should not fold due to non-power of 2.83define <2 x i32> @test8(<2 x float> %f) {84; CHECK-LABEL: test8:85; CHECK: // %bb.0:86; CHECK-NEXT: fmov v1.2s, #17.0000000087; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s88; CHECK-NEXT: fcvtzu v0.2s, v0.2s89; CHECK-NEXT: ret90 %mul.i = fmul <2 x float> %f, <float 17.000000e+00, float 17.000000e+00>91 %vcvt.i = fptoui <2 x float> %mul.i to <2 x i32>92 ret <2 x i32> %vcvt.i93}94 95; Test which should not fold due to non-matching power of 2.96define <2 x i32> @test9(<2 x float> %f) {97; CHECK-LABEL: test9:98; CHECK: // %bb.0:99; CHECK-NEXT: adrp x8, .LCPI8_0100; CHECK-NEXT: ldr d1, [x8, :lo12:.LCPI8_0]101; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s102; CHECK-NEXT: fcvtzu v0.2s, v0.2s103; CHECK-NEXT: ret104 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 8.000000e+00>105 %vcvt.i = fptoui <2 x float> %mul.i to <2 x i32>106 ret <2 x i32> %vcvt.i107}108 109; Combine all undefs.110define <2 x i32> @test10(<2 x float> %f) {111; CHECK-LABEL: test10:112; CHECK: // %bb.0:113; CHECK-NEXT: mvni v0.2s, #63, msl #16114; CHECK-NEXT: fneg v0.2s, v0.2s115; CHECK-NEXT: fcvtzu v0.2s, v0.2s116; CHECK-NEXT: ret117 %mul.i = fmul <2 x float> %f, <float undef, float undef>118 %vcvt.i = fptoui <2 x float> %mul.i to <2 x i32>119 ret <2 x i32> %vcvt.i120}121 122; Combine if mix of undef and pow2.123define <2 x i32> @test11(<2 x float> %f) {124; CHECK-LABEL: test11:125; CHECK: // %bb.0:126; CHECK-NEXT: fcvtzu v0.2s, v0.2s, #3127; CHECK-NEXT: ret128 %mul.i = fmul <2 x float> %f, <float undef, float 8.000000e+00>129 %vcvt.i = fptoui <2 x float> %mul.i to <2 x i32>130 ret <2 x i32> %vcvt.i131}132 133; Don't combine when multiplied by 0.0.134define <2 x i32> @test12(<2 x float> %f) {135; CHECK-LABEL: test12:136; CHECK: // %bb.0:137; CHECK-NEXT: movi d1, #0000000000000000138; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s139; CHECK-NEXT: fcvtzs v0.2s, v0.2s140; CHECK-NEXT: ret141 %mul.i = fmul <2 x float> %f, <float 0.000000e+00, float 0.000000e+00>142 %vcvt.i = fptosi <2 x float> %mul.i to <2 x i32>143 ret <2 x i32> %vcvt.i144}145 146; Test which should not fold due to power of 2 out of range (i.e., 2^33).147define <2 x i32> @test13(<2 x float> %f) {148; CHECK-LABEL: test13:149; CHECK: // %bb.0:150; CHECK-NEXT: movi v1.2s, #80, lsl #24151; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s152; CHECK-NEXT: fcvtzs v0.2s, v0.2s153; CHECK-NEXT: ret154 %mul.i = fmul <2 x float> %f, <float 0x4200000000000000, float 0x4200000000000000>155 %vcvt.i = fptosi <2 x float> %mul.i to <2 x i32>156 ret <2 x i32> %vcvt.i157}158 159; Test case where const is max power of 2 (i.e., 2^32).160define <2 x i32> @test14(<2 x float> %f) {161; CHECK-LABEL: test14:162; CHECK: // %bb.0:163; CHECK-NEXT: fcvtzs v0.2s, v0.2s, #32164; CHECK-NEXT: ret165 %mul.i = fmul <2 x float> %f, <float 0x41F0000000000000, float 0x41F0000000000000>166 %vcvt.i = fptosi <2 x float> %mul.i to <2 x i32>167 ret <2 x i32> %vcvt.i168}169 170define <3 x i32> @test_illegal_fp_to_int(<3 x float> %in) {171; CHECK-LABEL: test_illegal_fp_to_int:172; CHECK: // %bb.0:173; CHECK-NEXT: fcvtzs v0.4s, v0.4s, #2174; CHECK-NEXT: ret175 %scale = fmul <3 x float> %in, <float 4.0, float 4.0, float 4.0>176 %val = fptosi <3 x float> %scale to <3 x i32>177 ret <3 x i32> %val178}179 180define <8 x i16> @test_v8f16(<8 x half> %in) {181; CHECK-NO16-LABEL: test_v8f16:182; CHECK-NO16: // %bb.0:183; CHECK-NO16-NEXT: movi v1.8h, #68, lsl #8184; CHECK-NO16-NEXT: fcvtl v2.4s, v0.4h185; CHECK-NO16-NEXT: fcvtl2 v0.4s, v0.8h186; CHECK-NO16-NEXT: fcvtl v3.4s, v1.4h187; CHECK-NO16-NEXT: fcvtl2 v1.4s, v1.8h188; CHECK-NO16-NEXT: fmul v2.4s, v2.4s, v3.4s189; CHECK-NO16-NEXT: fmul v0.4s, v0.4s, v1.4s190; CHECK-NO16-NEXT: fcvtn v1.4h, v2.4s191; CHECK-NO16-NEXT: fcvtn2 v1.8h, v0.4s192; CHECK-NO16-NEXT: fcvtl2 v0.4s, v1.8h193; CHECK-NO16-NEXT: fcvtl v1.4s, v1.4h194; CHECK-NO16-NEXT: fcvtzs v0.4s, v0.4s195; CHECK-NO16-NEXT: fcvtzs v1.4s, v1.4s196; CHECK-NO16-NEXT: uzp1 v0.8h, v1.8h, v0.8h197; CHECK-NO16-NEXT: ret198;199; CHECK-FP16-LABEL: test_v8f16:200; CHECK-FP16: // %bb.0:201; CHECK-FP16-NEXT: fcvtzs v0.8h, v0.8h, #2202; CHECK-FP16-NEXT: ret203 %scale = fmul <8 x half> %in, <half 4.0, half 4.0, half 4.0, half 4.0, half 4.0, half 4.0, half 4.0, half 4.0>204 %val = fptosi <8 x half> %scale to <8 x i16>205 ret <8 x i16> %val206}207 208define <4 x i16> @test_v4f16(<4 x half> %in) {209; CHECK-NO16-LABEL: test_v4f16:210; CHECK-NO16: // %bb.0:211; CHECK-NO16-NEXT: fmov v1.4s, #4.00000000212; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h213; CHECK-NO16-NEXT: fmul v0.4s, v0.4s, v1.4s214; CHECK-NO16-NEXT: fcvtn v0.4h, v0.4s215; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h216; CHECK-NO16-NEXT: fcvtzu v0.4s, v0.4s217; CHECK-NO16-NEXT: xtn v0.4h, v0.4s218; CHECK-NO16-NEXT: ret219;220; CHECK-FP16-LABEL: test_v4f16:221; CHECK-FP16: // %bb.0:222; CHECK-FP16-NEXT: fcvtzu v0.4h, v0.4h, #2223; CHECK-FP16-NEXT: ret224 %scale = fmul <4 x half> %in, <half 4.0, half 4.0, half 4.0, half 4.0>225 %val = fptoui <4 x half> %scale to <4 x i16>226 ret <4 x i16> %val227}228 229define <4 x i32> @test_v4f16_i32(<4 x half> %in) {230; CHECK-NO16-LABEL: test_v4f16_i32:231; CHECK-NO16: // %bb.0:232; CHECK-NO16-NEXT: fmov v1.4s, #4.00000000233; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h234; CHECK-NO16-NEXT: fmul v0.4s, v0.4s, v1.4s235; CHECK-NO16-NEXT: fcvtn v0.4h, v0.4s236; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h237; CHECK-NO16-NEXT: fcvtzs v0.4s, v0.4s238; CHECK-NO16-NEXT: ret239;240; CHECK-FP16-LABEL: test_v4f16_i32:241; CHECK-FP16: // %bb.0:242; CHECK-FP16-NEXT: movi v1.4h, #68, lsl #8243; CHECK-FP16-NEXT: fmul v0.4h, v0.4h, v1.4h244; CHECK-FP16-NEXT: fcvtl v0.4s, v0.4h245; CHECK-FP16-NEXT: fcvtzs v0.4s, v0.4s246; CHECK-FP16-NEXT: ret247 %scale = fmul <4 x half> %in, <half 4.0, half 4.0, half 4.0, half 4.0>248 %val = fptosi <4 x half> %scale to <4 x i32>249 ret <4 x i32> %val250}251 252 253declare <2 x i32> @llvm.fptosi.sat.v2i32.v2f32(<2 x float>)254declare <2 x i32> @llvm.fptoui.sat.v2i32.v2f32(<2 x float>)255declare <2 x i32> @llvm.fptosi.sat.v2i32.v2f64(<2 x double>)256declare <2 x i64> @llvm.fptosi.sat.v2i64.v2f64(<2 x double>)257declare <4 x i32> @llvm.fptosi.sat.v4i32.v4f32(<4 x float>)258declare <2 x i16> @llvm.fptosi.sat.v2i16.v2f32(<2 x float>)259declare <4 x i16> @llvm.fptosi.sat.v4i16.v4f32(<4 x float>)260declare <2 x i64> @llvm.fptosi.sat.v2i64.v2f32(<2 x float>)261declare <3 x i32> @llvm.fptosi.sat.v3i32.v3f32(<3 x float>)262declare <8 x i16> @llvm.fptosi.sat.v8i16.v8f16(<8 x half>)263declare <4 x i16> @llvm.fptoui.sat.v4i16.v4f16(<4 x half>)264declare <4 x i32> @llvm.fptosi.sat.v4i32.v4f16(<4 x half>)265declare <4 x i24> @llvm.fptoui.sat.v4i24.v4f32(<4 x float>)266 267define <2 x i32> @test1_sat(<2 x float> %f) {268; CHECK-LABEL: test1_sat:269; CHECK: // %bb.0:270; CHECK-NEXT: fcvtzs v0.2s, v0.2s, #4271; CHECK-NEXT: ret272 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>273 %vcvt.i = call <2 x i32> @llvm.fptosi.sat.v2i32.v2f32(<2 x float> %mul.i)274 ret <2 x i32> %vcvt.i275}276 277define <4 x i32> @test2_sat(<4 x float> %f) {278; CHECK-LABEL: test2_sat:279; CHECK: // %bb.0:280; CHECK-NEXT: fcvtzs v0.4s, v0.4s, #3281; CHECK-NEXT: ret282 %mul.i = fmul <4 x float> %f, <float 8.000000e+00, float 8.000000e+00, float 8.000000e+00, float 8.000000e+00>283 %vcvt.i = call <4 x i32> @llvm.fptosi.sat.v4i32.v4f32(<4 x float> %mul.i)284 ret <4 x i32> %vcvt.i285}286 287define <2 x i64> @test3_sat(<2 x double> %d) {288; CHECK-LABEL: test3_sat:289; CHECK: // %bb.0:290; CHECK-NEXT: fcvtzs v0.2d, v0.2d, #5291; CHECK-NEXT: ret292 %mul.i = fmul <2 x double> %d, <double 32.000000e+00, double 32.000000e+00>293 %vcvt.i = call <2 x i64> @llvm.fptosi.sat.v2i64.v2f64(<2 x double> %mul.i)294 ret <2 x i64> %vcvt.i295}296 297; Truncate double to i32298define <2 x i32> @test4_sat(<2 x double> %d) {299; CHECK-LABEL: test4_sat:300; CHECK: // %bb.0:301; CHECK-NEXT: fmov v1.2d, #16.00000000302; CHECK-NEXT: fmul v0.2d, v0.2d, v1.2d303; CHECK-NEXT: mov d1, v0.d[1]304; CHECK-NEXT: fcvtzs w8, d0305; CHECK-NEXT: fcvtzs w9, d1306; CHECK-NEXT: fmov s0, w8307; CHECK-NEXT: mov v0.s[1], w9308; CHECK-NEXT: // kill: def $d0 killed $d0 killed $q0309; CHECK-NEXT: ret310 %mul.i = fmul <2 x double> %d, <double 16.000000e+00, double 16.000000e+00>311 %vcvt.i = call <2 x i32> @llvm.fptosi.sat.v2i32.v2f64(<2 x double> %mul.i)312 ret <2 x i32> %vcvt.i313}314 315; Truncate float to i16316define <2 x i16> @test5_sat(<2 x float> %f) {317; CHECK-LABEL: test5_sat:318; CHECK: // %bb.0:319; CHECK-NEXT: movi v1.2s, #127, msl #8320; CHECK-NEXT: fcvtzs v0.2s, v0.2s, #4321; CHECK-NEXT: smin v0.2s, v0.2s, v1.2s322; CHECK-NEXT: mvni v1.2s, #127, msl #8323; CHECK-NEXT: smax v0.2s, v0.2s, v1.2s324; CHECK-NEXT: ret325 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>326 %vcvt.i = call <2 x i16> @llvm.fptosi.sat.v2i16.v2f32(<2 x float> %mul.i)327 ret <2 x i16> %vcvt.i328}329 330; Truncate float to i16331define <4 x i16> @test5l_sat(<4 x float> %f) {332; CHECK-LABEL: test5l_sat:333; CHECK: // %bb.0:334; CHECK-NEXT: fcvtzs v0.4s, v0.4s, #4335; CHECK-NEXT: sqxtn v0.4h, v0.4s336; CHECK-NEXT: ret337 %mul.i = fmul <4 x float> %f, <float 16.000000e+00, float 16.000000e+00, float 16.000000e+00, float 16.000000e+00>338 %vcvt.i = call <4 x i16> @llvm.fptosi.sat.v4i16.v4f32(<4 x float> %mul.i)339 ret <4 x i16> %vcvt.i340}341 342; Don't convert float to i64343define <2 x i64> @test6_sat(<2 x float> %f) {344; CHECK-LABEL: test6_sat:345; CHECK: // %bb.0:346; CHECK-NEXT: fmov v1.2s, #16.00000000347; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s348; CHECK-NEXT: fcvtl v0.2d, v0.2s349; CHECK-NEXT: fcvtzs v0.2d, v0.2d350; CHECK-NEXT: ret351 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>352 %vcvt.i = call <2 x i64> @llvm.fptosi.sat.v2i64.v2f32(<2 x float> %mul.i)353 ret <2 x i64> %vcvt.i354}355 356define <2 x i32> @test7_sat(<2 x float> %f) {357; CHECK-LABEL: test7_sat:358; CHECK: // %bb.0:359; CHECK-NEXT: fcvtzu v0.2s, v0.2s, #4360; CHECK-NEXT: ret361 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 16.000000e+00>362 %vcvt.i = call <2 x i32> @llvm.fptoui.sat.v2i32.v2f32(<2 x float> %mul.i)363 ret <2 x i32> %vcvt.i364}365 366; Test which should not fold due to non-power of 2.367define <2 x i32> @test8_sat(<2 x float> %f) {368; CHECK-LABEL: test8_sat:369; CHECK: // %bb.0:370; CHECK-NEXT: fmov v1.2s, #17.00000000371; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s372; CHECK-NEXT: fcvtzu v0.2s, v0.2s373; CHECK-NEXT: ret374 %mul.i = fmul <2 x float> %f, <float 17.000000e+00, float 17.000000e+00>375 %vcvt.i = call <2 x i32> @llvm.fptoui.sat.v2i32.v2f32(<2 x float> %mul.i)376 ret <2 x i32> %vcvt.i377}378 379; Test which should not fold due to non-matching power of 2.380define <2 x i32> @test9_sat(<2 x float> %f) {381; CHECK-LABEL: test9_sat:382; CHECK: // %bb.0:383; CHECK-NEXT: adrp x8, .LCPI27_0384; CHECK-NEXT: ldr d1, [x8, :lo12:.LCPI27_0]385; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s386; CHECK-NEXT: fcvtzu v0.2s, v0.2s387; CHECK-NEXT: ret388 %mul.i = fmul <2 x float> %f, <float 16.000000e+00, float 8.000000e+00>389 %vcvt.i = call <2 x i32> @llvm.fptoui.sat.v2i32.v2f32(<2 x float> %mul.i)390 ret <2 x i32> %vcvt.i391}392 393; Combine all undefs.394define <2 x i32> @test10_sat(<2 x float> %f) {395; CHECK-LABEL: test10_sat:396; CHECK: // %bb.0:397; CHECK-NEXT: mvni v0.2s, #63, msl #16398; CHECK-NEXT: fneg v0.2s, v0.2s399; CHECK-NEXT: fcvtzu v0.2s, v0.2s400; CHECK-NEXT: ret401 %mul.i = fmul <2 x float> %f, <float undef, float undef>402 %vcvt.i = call <2 x i32> @llvm.fptoui.sat.v2i32.v2f32(<2 x float> %mul.i)403 ret <2 x i32> %vcvt.i404}405 406; Combine if mix of undef and pow2.407define <2 x i32> @test11_sat(<2 x float> %f) {408; CHECK-LABEL: test11_sat:409; CHECK: // %bb.0:410; CHECK-NEXT: fcvtzu v0.2s, v0.2s, #3411; CHECK-NEXT: ret412 %mul.i = fmul <2 x float> %f, <float undef, float 8.000000e+00>413 %vcvt.i = call <2 x i32> @llvm.fptoui.sat.v2i32.v2f32(<2 x float> %mul.i)414 ret <2 x i32> %vcvt.i415}416 417; Don't combine when multiplied by 0.0.418define <2 x i32> @test12_sat(<2 x float> %f) {419; CHECK-LABEL: test12_sat:420; CHECK: // %bb.0:421; CHECK-NEXT: movi d1, #0000000000000000422; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s423; CHECK-NEXT: fcvtzs v0.2s, v0.2s424; CHECK-NEXT: ret425 %mul.i = fmul <2 x float> %f, <float 0.000000e+00, float 0.000000e+00>426 %vcvt.i = call <2 x i32> @llvm.fptosi.sat.v2i32.v2f32(<2 x float> %mul.i)427 ret <2 x i32> %vcvt.i428}429 430; Test which should not fold due to power of 2 out of range (i.e., 2^33).431define <2 x i32> @test13_sat(<2 x float> %f) {432; CHECK-LABEL: test13_sat:433; CHECK: // %bb.0:434; CHECK-NEXT: movi v1.2s, #80, lsl #24435; CHECK-NEXT: fmul v0.2s, v0.2s, v1.2s436; CHECK-NEXT: fcvtzs v0.2s, v0.2s437; CHECK-NEXT: ret438 %mul.i = fmul <2 x float> %f, <float 0x4200000000000000, float 0x4200000000000000>439 %vcvt.i = call <2 x i32> @llvm.fptosi.sat.v2i32.v2f32(<2 x float> %mul.i)440 ret <2 x i32> %vcvt.i441}442 443; Test case where const is max power of 2 (i.e., 2^32).444define <2 x i32> @test14_sat(<2 x float> %f) {445; CHECK-LABEL: test14_sat:446; CHECK: // %bb.0:447; CHECK-NEXT: fcvtzs v0.2s, v0.2s, #32448; CHECK-NEXT: ret449 %mul.i = fmul <2 x float> %f, <float 0x41F0000000000000, float 0x41F0000000000000>450 %vcvt.i = call <2 x i32> @llvm.fptosi.sat.v2i32.v2f32(<2 x float> %mul.i)451 ret <2 x i32> %vcvt.i452}453 454define <3 x i32> @test_illegal_fp_to_int_sat_sat(<3 x float> %in) {455; CHECK-LABEL: test_illegal_fp_to_int_sat_sat:456; CHECK: // %bb.0:457; CHECK-NEXT: fcvtzs v0.4s, v0.4s, #2458; CHECK-NEXT: ret459 %mul.i = fmul <3 x float> %in, <float 4.0, float 4.0, float 4.0>460 %vcvt.i = call <3 x i32> @llvm.fptosi.sat.v3i32.v3f32(<3 x float> %mul.i)461 ret <3 x i32> %vcvt.i462}463 464define <8 x i16> @test_v8f16_sat(<8 x half> %in) {465; CHECK-NO16-LABEL: test_v8f16_sat:466; CHECK-NO16: // %bb.0:467; CHECK-NO16-NEXT: movi v1.8h, #68, lsl #8468; CHECK-NO16-NEXT: fcvtl v2.4s, v0.4h469; CHECK-NO16-NEXT: fcvtl2 v0.4s, v0.8h470; CHECK-NO16-NEXT: fcvtl v3.4s, v1.4h471; CHECK-NO16-NEXT: fcvtl2 v1.4s, v1.8h472; CHECK-NO16-NEXT: fmul v2.4s, v2.4s, v3.4s473; CHECK-NO16-NEXT: fmul v0.4s, v0.4s, v1.4s474; CHECK-NO16-NEXT: fcvtn v1.4h, v2.4s475; CHECK-NO16-NEXT: fcvtn2 v1.8h, v0.4s476; CHECK-NO16-NEXT: fcvtl v0.4s, v1.4h477; CHECK-NO16-NEXT: fcvtl2 v1.4s, v1.8h478; CHECK-NO16-NEXT: fcvtzs v0.4s, v0.4s479; CHECK-NO16-NEXT: fcvtzs v1.4s, v1.4s480; CHECK-NO16-NEXT: sqxtn v0.4h, v0.4s481; CHECK-NO16-NEXT: sqxtn2 v0.8h, v1.4s482; CHECK-NO16-NEXT: ret483;484; CHECK-FP16-LABEL: test_v8f16_sat:485; CHECK-FP16: // %bb.0:486; CHECK-FP16-NEXT: fcvtzs v0.8h, v0.8h, #2487; CHECK-FP16-NEXT: ret488 %mul.i = fmul <8 x half> %in, <half 4.0, half 4.0, half 4.0, half 4.0, half 4.0, half 4.0, half 4.0, half 4.0>489 %val = call <8 x i16> @llvm.fptosi.sat.v8i16.v8f16(<8 x half> %mul.i)490 ret <8 x i16> %val491}492 493define <4 x i16> @test_v4f16_sat(<4 x half> %in) {494; CHECK-NO16-LABEL: test_v4f16_sat:495; CHECK-NO16: // %bb.0:496; CHECK-NO16-NEXT: fmov v1.4s, #4.00000000497; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h498; CHECK-NO16-NEXT: fmul v0.4s, v0.4s, v1.4s499; CHECK-NO16-NEXT: fcvtn v0.4h, v0.4s500; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h501; CHECK-NO16-NEXT: fcvtzu v0.4s, v0.4s502; CHECK-NO16-NEXT: uqxtn v0.4h, v0.4s503; CHECK-NO16-NEXT: ret504;505; CHECK-FP16-LABEL: test_v4f16_sat:506; CHECK-FP16: // %bb.0:507; CHECK-FP16-NEXT: fcvtzu v0.4h, v0.4h, #2508; CHECK-FP16-NEXT: ret509 %mul.i = fmul <4 x half> %in, <half 4.0, half 4.0, half 4.0, half 4.0>510 %val = call <4 x i16> @llvm.fptoui.sat.v4i16.v4f16(<4 x half> %mul.i)511 ret <4 x i16> %val512}513 514define <4 x i32> @test_v4f16_i32_sat(<4 x half> %in) {515; CHECK-NO16-LABEL: test_v4f16_i32_sat:516; CHECK-NO16: // %bb.0:517; CHECK-NO16-NEXT: fmov v1.4s, #4.00000000518; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h519; CHECK-NO16-NEXT: fmul v0.4s, v0.4s, v1.4s520; CHECK-NO16-NEXT: fcvtn v0.4h, v0.4s521; CHECK-NO16-NEXT: fcvtl v0.4s, v0.4h522; CHECK-NO16-NEXT: fcvtzs v0.4s, v0.4s523; CHECK-NO16-NEXT: ret524;525; CHECK-FP16-LABEL: test_v4f16_i32_sat:526; CHECK-FP16: // %bb.0:527; CHECK-FP16-NEXT: movi v1.4h, #68, lsl #8528; CHECK-FP16-NEXT: fmul v0.4h, v0.4h, v1.4h529; CHECK-FP16-NEXT: fcvtl v0.4s, v0.4h530; CHECK-FP16-NEXT: fcvtzs v0.4s, v0.4s531; CHECK-FP16-NEXT: ret532 %mul.i = fmul <4 x half> %in, <half 4.0, half 4.0, half 4.0, half 4.0>533 %val = call <4 x i32> @llvm.fptosi.sat.v4i32.v4f16(<4 x half> %mul.i)534 ret <4 x i32> %val535}536 537define <4 x i32> @test_extrasat(<4 x float> %f) {538; CHECK-LABEL: test_extrasat:539; CHECK: // %bb.0:540; CHECK-NEXT: movi v1.2d, #0xffffff00ffffff541; CHECK-NEXT: fcvtzu v0.4s, v0.4s, #3542; CHECK-NEXT: umin v0.4s, v0.4s, v1.4s543; CHECK-NEXT: ret544 %mul.i = fmul <4 x float> %f, <float 8.000000e+00, float 8.000000e+00, float 8.000000e+00, float 8.000000e+00>545 %vcvt.i = call <4 x i24> @llvm.fptoui.sat.v4i24.v4f32(<4 x float> %mul.i)546 %t = zext <4 x i24> %vcvt.i to <4 x i32>547 ret <4 x i32> %t548}549