621 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 52; RUN: llc < %s -mtriple=arm64-eabi -aarch64-neon-syntax=apple | FileCheck %s3 4define void @test_vext_s8() nounwind ssp {5; CHECK-LABEL: test_vext_s8:6; CHECK: // %bb.0:7; CHECK-NEXT: sub sp, sp, #328; CHECK-NEXT: ldr d0, [sp, #24]9; CHECK-NEXT: ext.8b v1, v0, v0, #110; CHECK-NEXT: stp d0, d0, [sp, #8]11; CHECK-NEXT: str d1, [sp, #24]12; CHECK-NEXT: add sp, sp, #3213; CHECK-NEXT: ret14 %xS8x8 = alloca <8 x i8>, align 815 %__a = alloca <8 x i8>, align 816 %__b = alloca <8 x i8>, align 817 %tmp = load <8 x i8>, ptr %xS8x8, align 818 store <8 x i8> %tmp, ptr %__a, align 819 %tmp1 = load <8 x i8>, ptr %xS8x8, align 820 store <8 x i8> %tmp1, ptr %__b, align 821 %tmp2 = load <8 x i8>, ptr %__a, align 822 %tmp3 = load <8 x i8>, ptr %__b, align 823 %vext = shufflevector <8 x i8> %tmp2, <8 x i8> %tmp3, <8 x i32> <i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 7, i32 8>24 store <8 x i8> %vext, ptr %xS8x8, align 825 ret void26}27 28define void @test_vext_u8() nounwind ssp {29; CHECK-LABEL: test_vext_u8:30; CHECK: // %bb.0:31; CHECK-NEXT: sub sp, sp, #3232; CHECK-NEXT: ldr d0, [sp, #24]33; CHECK-NEXT: ext.8b v1, v0, v0, #234; CHECK-NEXT: stp d0, d0, [sp, #8]35; CHECK-NEXT: str d1, [sp, #24]36; CHECK-NEXT: add sp, sp, #3237; CHECK-NEXT: ret38 %xU8x8 = alloca <8 x i8>, align 839 %__a = alloca <8 x i8>, align 840 %__b = alloca <8 x i8>, align 841 %tmp = load <8 x i8>, ptr %xU8x8, align 842 store <8 x i8> %tmp, ptr %__a, align 843 %tmp1 = load <8 x i8>, ptr %xU8x8, align 844 store <8 x i8> %tmp1, ptr %__b, align 845 %tmp2 = load <8 x i8>, ptr %__a, align 846 %tmp3 = load <8 x i8>, ptr %__b, align 847 %vext = shufflevector <8 x i8> %tmp2, <8 x i8> %tmp3, <8 x i32> <i32 2, i32 3, i32 4, i32 5, i32 6, i32 7, i32 8, i32 9>48 store <8 x i8> %vext, ptr %xU8x8, align 849 ret void50}51 52define void @test_vext_p8() nounwind ssp {53; CHECK-LABEL: test_vext_p8:54; CHECK: // %bb.0:55; CHECK-NEXT: sub sp, sp, #3256; CHECK-NEXT: ldr d0, [sp, #24]57; CHECK-NEXT: ext.8b v1, v0, v0, #358; CHECK-NEXT: stp d0, d0, [sp, #8]59; CHECK-NEXT: str d1, [sp, #24]60; CHECK-NEXT: add sp, sp, #3261; CHECK-NEXT: ret62 %xP8x8 = alloca <8 x i8>, align 863 %__a = alloca <8 x i8>, align 864 %__b = alloca <8 x i8>, align 865 %tmp = load <8 x i8>, ptr %xP8x8, align 866 store <8 x i8> %tmp, ptr %__a, align 867 %tmp1 = load <8 x i8>, ptr %xP8x8, align 868 store <8 x i8> %tmp1, ptr %__b, align 869 %tmp2 = load <8 x i8>, ptr %__a, align 870 %tmp3 = load <8 x i8>, ptr %__b, align 871 %vext = shufflevector <8 x i8> %tmp2, <8 x i8> %tmp3, <8 x i32> <i32 3, i32 4, i32 5, i32 6, i32 7, i32 8, i32 9, i32 10>72 store <8 x i8> %vext, ptr %xP8x8, align 873 ret void74}75 76define void @test_vext_s16() nounwind ssp {77; CHECK-LABEL: test_vext_s16:78; CHECK: // %bb.0:79; CHECK-NEXT: sub sp, sp, #3280; CHECK-NEXT: ldr d0, [sp, #24]81; CHECK-NEXT: ext.8b v1, v0, v0, #282; CHECK-NEXT: stp d0, d0, [sp, #8]83; CHECK-NEXT: str d1, [sp, #24]84; CHECK-NEXT: add sp, sp, #3285; CHECK-NEXT: ret86 %xS16x4 = alloca <4 x i16>, align 887 %__a = alloca <4 x i16>, align 888 %__b = alloca <4 x i16>, align 889 %tmp = load <4 x i16>, ptr %xS16x4, align 890 store <4 x i16> %tmp, ptr %__a, align 891 %tmp1 = load <4 x i16>, ptr %xS16x4, align 892 store <4 x i16> %tmp1, ptr %__b, align 893 %tmp2 = load <4 x i16>, ptr %__a, align 894 %tmp3 = bitcast <4 x i16> %tmp2 to <8 x i8>95 %tmp4 = load <4 x i16>, ptr %__b, align 896 %tmp5 = bitcast <4 x i16> %tmp4 to <8 x i8>97 %tmp6 = bitcast <8 x i8> %tmp3 to <4 x i16>98 %tmp7 = bitcast <8 x i8> %tmp5 to <4 x i16>99 %vext = shufflevector <4 x i16> %tmp6, <4 x i16> %tmp7, <4 x i32> <i32 1, i32 2, i32 3, i32 4>100 store <4 x i16> %vext, ptr %xS16x4, align 8101 ret void102}103 104define void @test_vext_u16() nounwind ssp {105; CHECK-LABEL: test_vext_u16:106; CHECK: // %bb.0:107; CHECK-NEXT: sub sp, sp, #32108; CHECK-NEXT: ldr d0, [sp, #24]109; CHECK-NEXT: ext.8b v1, v0, v0, #4110; CHECK-NEXT: stp d0, d0, [sp, #8]111; CHECK-NEXT: str d1, [sp, #24]112; CHECK-NEXT: add sp, sp, #32113; CHECK-NEXT: ret114 %xU16x4 = alloca <4 x i16>, align 8115 %__a = alloca <4 x i16>, align 8116 %__b = alloca <4 x i16>, align 8117 %tmp = load <4 x i16>, ptr %xU16x4, align 8118 store <4 x i16> %tmp, ptr %__a, align 8119 %tmp1 = load <4 x i16>, ptr %xU16x4, align 8120 store <4 x i16> %tmp1, ptr %__b, align 8121 %tmp2 = load <4 x i16>, ptr %__a, align 8122 %tmp3 = bitcast <4 x i16> %tmp2 to <8 x i8>123 %tmp4 = load <4 x i16>, ptr %__b, align 8124 %tmp5 = bitcast <4 x i16> %tmp4 to <8 x i8>125 %tmp6 = bitcast <8 x i8> %tmp3 to <4 x i16>126 %tmp7 = bitcast <8 x i8> %tmp5 to <4 x i16>127 %vext = shufflevector <4 x i16> %tmp6, <4 x i16> %tmp7, <4 x i32> <i32 2, i32 3, i32 4, i32 5>128 store <4 x i16> %vext, ptr %xU16x4, align 8129 ret void130}131 132define void @test_vext_p16() nounwind ssp {133; CHECK-LABEL: test_vext_p16:134; CHECK: // %bb.0:135; CHECK-NEXT: sub sp, sp, #32136; CHECK-NEXT: ldr d0, [sp, #24]137; CHECK-NEXT: ext.8b v1, v0, v0, #6138; CHECK-NEXT: stp d0, d0, [sp, #8]139; CHECK-NEXT: str d1, [sp, #24]140; CHECK-NEXT: add sp, sp, #32141; CHECK-NEXT: ret142 %xP16x4 = alloca <4 x i16>, align 8143 %__a = alloca <4 x i16>, align 8144 %__b = alloca <4 x i16>, align 8145 %tmp = load <4 x i16>, ptr %xP16x4, align 8146 store <4 x i16> %tmp, ptr %__a, align 8147 %tmp1 = load <4 x i16>, ptr %xP16x4, align 8148 store <4 x i16> %tmp1, ptr %__b, align 8149 %tmp2 = load <4 x i16>, ptr %__a, align 8150 %tmp3 = bitcast <4 x i16> %tmp2 to <8 x i8>151 %tmp4 = load <4 x i16>, ptr %__b, align 8152 %tmp5 = bitcast <4 x i16> %tmp4 to <8 x i8>153 %tmp6 = bitcast <8 x i8> %tmp3 to <4 x i16>154 %tmp7 = bitcast <8 x i8> %tmp5 to <4 x i16>155 %vext = shufflevector <4 x i16> %tmp6, <4 x i16> %tmp7, <4 x i32> <i32 3, i32 4, i32 5, i32 6>156 store <4 x i16> %vext, ptr %xP16x4, align 8157 ret void158}159 160define void @test_vext_s32() nounwind ssp {161; CHECK-LABEL: test_vext_s32:162; CHECK: // %bb.0:163; CHECK-NEXT: sub sp, sp, #32164; CHECK-NEXT: ldr d0, [sp, #24]165; CHECK-NEXT: rev64.2s v1, v0166; CHECK-NEXT: stp d0, d0, [sp, #8]167; CHECK-NEXT: str d1, [sp, #24]168; CHECK-NEXT: add sp, sp, #32169; CHECK-NEXT: ret170 %xS32x2 = alloca <2 x i32>, align 8171 %__a = alloca <2 x i32>, align 8172 %__b = alloca <2 x i32>, align 8173 %tmp = load <2 x i32>, ptr %xS32x2, align 8174 store <2 x i32> %tmp, ptr %__a, align 8175 %tmp1 = load <2 x i32>, ptr %xS32x2, align 8176 store <2 x i32> %tmp1, ptr %__b, align 8177 %tmp2 = load <2 x i32>, ptr %__a, align 8178 %tmp3 = bitcast <2 x i32> %tmp2 to <8 x i8>179 %tmp4 = load <2 x i32>, ptr %__b, align 8180 %tmp5 = bitcast <2 x i32> %tmp4 to <8 x i8>181 %tmp6 = bitcast <8 x i8> %tmp3 to <2 x i32>182 %tmp7 = bitcast <8 x i8> %tmp5 to <2 x i32>183 %vext = shufflevector <2 x i32> %tmp6, <2 x i32> %tmp7, <2 x i32> <i32 1, i32 2>184 store <2 x i32> %vext, ptr %xS32x2, align 8185 ret void186}187 188define void @test_vext_u32() nounwind ssp {189; CHECK-LABEL: test_vext_u32:190; CHECK: // %bb.0:191; CHECK-NEXT: sub sp, sp, #32192; CHECK-NEXT: ldr d0, [sp, #24]193; CHECK-NEXT: rev64.2s v1, v0194; CHECK-NEXT: stp d0, d0, [sp, #8]195; CHECK-NEXT: str d1, [sp, #24]196; CHECK-NEXT: add sp, sp, #32197; CHECK-NEXT: ret198 %xU32x2 = alloca <2 x i32>, align 8199 %__a = alloca <2 x i32>, align 8200 %__b = alloca <2 x i32>, align 8201 %tmp = load <2 x i32>, ptr %xU32x2, align 8202 store <2 x i32> %tmp, ptr %__a, align 8203 %tmp1 = load <2 x i32>, ptr %xU32x2, align 8204 store <2 x i32> %tmp1, ptr %__b, align 8205 %tmp2 = load <2 x i32>, ptr %__a, align 8206 %tmp3 = bitcast <2 x i32> %tmp2 to <8 x i8>207 %tmp4 = load <2 x i32>, ptr %__b, align 8208 %tmp5 = bitcast <2 x i32> %tmp4 to <8 x i8>209 %tmp6 = bitcast <8 x i8> %tmp3 to <2 x i32>210 %tmp7 = bitcast <8 x i8> %tmp5 to <2 x i32>211 %vext = shufflevector <2 x i32> %tmp6, <2 x i32> %tmp7, <2 x i32> <i32 1, i32 2>212 store <2 x i32> %vext, ptr %xU32x2, align 8213 ret void214}215 216define void @test_vext_f32() nounwind ssp {217; CHECK-LABEL: test_vext_f32:218; CHECK: // %bb.0:219; CHECK-NEXT: sub sp, sp, #32220; CHECK-NEXT: ldr d0, [sp, #24]221; CHECK-NEXT: rev64.2s v1, v0222; CHECK-NEXT: stp d0, d0, [sp, #8]223; CHECK-NEXT: str d1, [sp, #24]224; CHECK-NEXT: add sp, sp, #32225; CHECK-NEXT: ret226 %xF32x2 = alloca <2 x float>, align 8227 %__a = alloca <2 x float>, align 8228 %__b = alloca <2 x float>, align 8229 %tmp = load <2 x float>, ptr %xF32x2, align 8230 store <2 x float> %tmp, ptr %__a, align 8231 %tmp1 = load <2 x float>, ptr %xF32x2, align 8232 store <2 x float> %tmp1, ptr %__b, align 8233 %tmp2 = load <2 x float>, ptr %__a, align 8234 %tmp3 = bitcast <2 x float> %tmp2 to <8 x i8>235 %tmp4 = load <2 x float>, ptr %__b, align 8236 %tmp5 = bitcast <2 x float> %tmp4 to <8 x i8>237 %tmp6 = bitcast <8 x i8> %tmp3 to <2 x float>238 %tmp7 = bitcast <8 x i8> %tmp5 to <2 x float>239 %vext = shufflevector <2 x float> %tmp6, <2 x float> %tmp7, <2 x i32> <i32 1, i32 2>240 store <2 x float> %vext, ptr %xF32x2, align 8241 ret void242}243 244define void @test_vext_s64() nounwind ssp {245; CHECK-LABEL: test_vext_s64:246; CHECK: // %bb.0:247; CHECK-NEXT: sub sp, sp, #32248; CHECK-NEXT: ldr d0, [sp, #24]249; CHECK-NEXT: stp d0, d0, [sp, #8]250; CHECK-NEXT: add sp, sp, #32251; CHECK-NEXT: ret252 ; CHECK_FIXME: {{rev64.2s.*}}253 ; this just turns into a load of the second element254 %xS64x1 = alloca <1 x i64>, align 8255 %__a = alloca <1 x i64>, align 8256 %__b = alloca <1 x i64>, align 8257 %tmp = load <1 x i64>, ptr %xS64x1, align 8258 store <1 x i64> %tmp, ptr %__a, align 8259 %tmp1 = load <1 x i64>, ptr %xS64x1, align 8260 store <1 x i64> %tmp1, ptr %__b, align 8261 %tmp2 = load <1 x i64>, ptr %__a, align 8262 %tmp3 = bitcast <1 x i64> %tmp2 to <8 x i8>263 %tmp4 = load <1 x i64>, ptr %__b, align 8264 %tmp5 = bitcast <1 x i64> %tmp4 to <8 x i8>265 %tmp6 = bitcast <8 x i8> %tmp3 to <1 x i64>266 %tmp7 = bitcast <8 x i8> %tmp5 to <1 x i64>267 %vext = shufflevector <1 x i64> %tmp6, <1 x i64> %tmp7, <1 x i32> <i32 1>268 store <1 x i64> %vext, ptr %xS64x1, align 8269 ret void270}271 272define void @test_vext_u64() nounwind ssp {273; CHECK-LABEL: test_vext_u64:274; CHECK: // %bb.0:275; CHECK-NEXT: sub sp, sp, #32276; CHECK-NEXT: ldr d0, [sp, #24]277; CHECK-NEXT: stp d0, d0, [sp, #8]278; CHECK-NEXT: add sp, sp, #32279; CHECK-NEXT: ret280 ; CHECK_FIXME: {{ext.8.*#1}}281 ; this is turned into a simple load of the 2nd element282 %xU64x1 = alloca <1 x i64>, align 8283 %__a = alloca <1 x i64>, align 8284 %__b = alloca <1 x i64>, align 8285 %tmp = load <1 x i64>, ptr %xU64x1, align 8286 store <1 x i64> %tmp, ptr %__a, align 8287 %tmp1 = load <1 x i64>, ptr %xU64x1, align 8288 store <1 x i64> %tmp1, ptr %__b, align 8289 %tmp2 = load <1 x i64>, ptr %__a, align 8290 %tmp3 = bitcast <1 x i64> %tmp2 to <8 x i8>291 %tmp4 = load <1 x i64>, ptr %__b, align 8292 %tmp5 = bitcast <1 x i64> %tmp4 to <8 x i8>293 %tmp6 = bitcast <8 x i8> %tmp3 to <1 x i64>294 %tmp7 = bitcast <8 x i8> %tmp5 to <1 x i64>295 %vext = shufflevector <1 x i64> %tmp6, <1 x i64> %tmp7, <1 x i32> <i32 1>296 store <1 x i64> %vext, ptr %xU64x1, align 8297 ret void298}299 300define void @test_vextq_s8() nounwind ssp {301; CHECK-LABEL: test_vextq_s8:302; CHECK: // %bb.0:303; CHECK-NEXT: sub sp, sp, #48304; CHECK-NEXT: ldr q0, [sp, #32]305; CHECK-NEXT: ext.16b v1, v0, v0, #4306; CHECK-NEXT: stp q0, q0, [sp]307; CHECK-NEXT: str q1, [sp, #32]308; CHECK-NEXT: add sp, sp, #48309; CHECK-NEXT: ret310 %xS8x16 = alloca <16 x i8>, align 16311 %__a = alloca <16 x i8>, align 16312 %__b = alloca <16 x i8>, align 16313 %tmp = load <16 x i8>, ptr %xS8x16, align 16314 store <16 x i8> %tmp, ptr %__a, align 16315 %tmp1 = load <16 x i8>, ptr %xS8x16, align 16316 store <16 x i8> %tmp1, ptr %__b, align 16317 %tmp2 = load <16 x i8>, ptr %__a, align 16318 %tmp3 = load <16 x i8>, ptr %__b, align 16319 %vext = shufflevector <16 x i8> %tmp2, <16 x i8> %tmp3, <16 x i32> <i32 4, i32 5, i32 6, i32 7, i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15, i32 16, i32 17, i32 18, i32 19>320 store <16 x i8> %vext, ptr %xS8x16, align 16321 ret void322}323 324define void @test_vextq_u8() nounwind ssp {325; CHECK-LABEL: test_vextq_u8:326; CHECK: // %bb.0:327; CHECK-NEXT: sub sp, sp, #48328; CHECK-NEXT: ldr q0, [sp, #32]329; CHECK-NEXT: ext.16b v1, v0, v0, #5330; CHECK-NEXT: stp q0, q0, [sp]331; CHECK-NEXT: str q1, [sp, #32]332; CHECK-NEXT: add sp, sp, #48333; CHECK-NEXT: ret334 %xU8x16 = alloca <16 x i8>, align 16335 %__a = alloca <16 x i8>, align 16336 %__b = alloca <16 x i8>, align 16337 %tmp = load <16 x i8>, ptr %xU8x16, align 16338 store <16 x i8> %tmp, ptr %__a, align 16339 %tmp1 = load <16 x i8>, ptr %xU8x16, align 16340 store <16 x i8> %tmp1, ptr %__b, align 16341 %tmp2 = load <16 x i8>, ptr %__a, align 16342 %tmp3 = load <16 x i8>, ptr %__b, align 16343 %vext = shufflevector <16 x i8> %tmp2, <16 x i8> %tmp3, <16 x i32> <i32 5, i32 6, i32 7, i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15, i32 16, i32 17, i32 18, i32 19, i32 20>344 store <16 x i8> %vext, ptr %xU8x16, align 16345 ret void346}347 348define void @test_vextq_p8() nounwind ssp {349; CHECK-LABEL: test_vextq_p8:350; CHECK: // %bb.0:351; CHECK-NEXT: sub sp, sp, #48352; CHECK-NEXT: ldr q0, [sp, #32]353; CHECK-NEXT: ext.16b v1, v0, v0, #6354; CHECK-NEXT: stp q0, q0, [sp]355; CHECK-NEXT: str q1, [sp, #32]356; CHECK-NEXT: add sp, sp, #48357; CHECK-NEXT: ret358 %xP8x16 = alloca <16 x i8>, align 16359 %__a = alloca <16 x i8>, align 16360 %__b = alloca <16 x i8>, align 16361 %tmp = load <16 x i8>, ptr %xP8x16, align 16362 store <16 x i8> %tmp, ptr %__a, align 16363 %tmp1 = load <16 x i8>, ptr %xP8x16, align 16364 store <16 x i8> %tmp1, ptr %__b, align 16365 %tmp2 = load <16 x i8>, ptr %__a, align 16366 %tmp3 = load <16 x i8>, ptr %__b, align 16367 %vext = shufflevector <16 x i8> %tmp2, <16 x i8> %tmp3, <16 x i32> <i32 6, i32 7, i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15, i32 16, i32 17, i32 18, i32 19, i32 20, i32 21>368 store <16 x i8> %vext, ptr %xP8x16, align 16369 ret void370}371 372define void @test_vextq_s16() nounwind ssp {373; CHECK-LABEL: test_vextq_s16:374; CHECK: // %bb.0:375; CHECK-NEXT: sub sp, sp, #48376; CHECK-NEXT: ldr q0, [sp, #32]377; CHECK-NEXT: ext.16b v1, v0, v0, #14378; CHECK-NEXT: stp q0, q0, [sp]379; CHECK-NEXT: str q1, [sp, #32]380; CHECK-NEXT: add sp, sp, #48381; CHECK-NEXT: ret382 %xS16x8 = alloca <8 x i16>, align 16383 %__a = alloca <8 x i16>, align 16384 %__b = alloca <8 x i16>, align 16385 %tmp = load <8 x i16>, ptr %xS16x8, align 16386 store <8 x i16> %tmp, ptr %__a, align 16387 %tmp1 = load <8 x i16>, ptr %xS16x8, align 16388 store <8 x i16> %tmp1, ptr %__b, align 16389 %tmp2 = load <8 x i16>, ptr %__a, align 16390 %tmp3 = bitcast <8 x i16> %tmp2 to <16 x i8>391 %tmp4 = load <8 x i16>, ptr %__b, align 16392 %tmp5 = bitcast <8 x i16> %tmp4 to <16 x i8>393 %tmp6 = bitcast <16 x i8> %tmp3 to <8 x i16>394 %tmp7 = bitcast <16 x i8> %tmp5 to <8 x i16>395 %vext = shufflevector <8 x i16> %tmp6, <8 x i16> %tmp7, <8 x i32> <i32 7, i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14>396 store <8 x i16> %vext, ptr %xS16x8, align 16397 ret void398}399 400define void @test_vextq_u16() nounwind ssp {401; CHECK-LABEL: test_vextq_u16:402; CHECK: // %bb.0:403; CHECK-NEXT: sub sp, sp, #48404; CHECK-NEXT: ldr q0, [sp, #32]405; CHECK-NEXT: ext.16b v1, v0, v0, #8406; CHECK-NEXT: stp q0, q0, [sp]407; CHECK-NEXT: str q1, [sp, #32]408; CHECK-NEXT: add sp, sp, #48409; CHECK-NEXT: ret410 %xU16x8 = alloca <8 x i16>, align 16411 %__a = alloca <8 x i16>, align 16412 %__b = alloca <8 x i16>, align 16413 %tmp = load <8 x i16>, ptr %xU16x8, align 16414 store <8 x i16> %tmp, ptr %__a, align 16415 %tmp1 = load <8 x i16>, ptr %xU16x8, align 16416 store <8 x i16> %tmp1, ptr %__b, align 16417 %tmp2 = load <8 x i16>, ptr %__a, align 16418 %tmp3 = bitcast <8 x i16> %tmp2 to <16 x i8>419 %tmp4 = load <8 x i16>, ptr %__b, align 16420 %tmp5 = bitcast <8 x i16> %tmp4 to <16 x i8>421 %tmp6 = bitcast <16 x i8> %tmp3 to <8 x i16>422 %tmp7 = bitcast <16 x i8> %tmp5 to <8 x i16>423 %vext = shufflevector <8 x i16> %tmp6, <8 x i16> %tmp7, <8 x i32> <i32 4, i32 5, i32 6, i32 7, i32 8, i32 9, i32 10, i32 11>424 store <8 x i16> %vext, ptr %xU16x8, align 16425 ret void426}427 428define void @test_vextq_p16() nounwind ssp {429; CHECK-LABEL: test_vextq_p16:430; CHECK: // %bb.0:431; CHECK-NEXT: sub sp, sp, #48432; CHECK-NEXT: ldr q0, [sp, #32]433; CHECK-NEXT: ext.16b v1, v0, v0, #10434; CHECK-NEXT: stp q0, q0, [sp]435; CHECK-NEXT: str q1, [sp, #32]436; CHECK-NEXT: add sp, sp, #48437; CHECK-NEXT: ret438 %xP16x8 = alloca <8 x i16>, align 16439 %__a = alloca <8 x i16>, align 16440 %__b = alloca <8 x i16>, align 16441 %tmp = load <8 x i16>, ptr %xP16x8, align 16442 store <8 x i16> %tmp, ptr %__a, align 16443 %tmp1 = load <8 x i16>, ptr %xP16x8, align 16444 store <8 x i16> %tmp1, ptr %__b, align 16445 %tmp2 = load <8 x i16>, ptr %__a, align 16446 %tmp3 = bitcast <8 x i16> %tmp2 to <16 x i8>447 %tmp4 = load <8 x i16>, ptr %__b, align 16448 %tmp5 = bitcast <8 x i16> %tmp4 to <16 x i8>449 %tmp6 = bitcast <16 x i8> %tmp3 to <8 x i16>450 %tmp7 = bitcast <16 x i8> %tmp5 to <8 x i16>451 %vext = shufflevector <8 x i16> %tmp6, <8 x i16> %tmp7, <8 x i32> <i32 5, i32 6, i32 7, i32 8, i32 9, i32 10, i32 11, i32 12>452 store <8 x i16> %vext, ptr %xP16x8, align 16453 ret void454}455 456define void @test_vextq_s32() nounwind ssp {457; CHECK-LABEL: test_vextq_s32:458; CHECK: // %bb.0:459; CHECK-NEXT: sub sp, sp, #48460; CHECK-NEXT: ldr q0, [sp, #32]461; CHECK-NEXT: ext.16b v1, v0, v0, #4462; CHECK-NEXT: stp q0, q0, [sp]463; CHECK-NEXT: str q1, [sp, #32]464; CHECK-NEXT: add sp, sp, #48465; CHECK-NEXT: ret466 %xS32x4 = alloca <4 x i32>, align 16467 %__a = alloca <4 x i32>, align 16468 %__b = alloca <4 x i32>, align 16469 %tmp = load <4 x i32>, ptr %xS32x4, align 16470 store <4 x i32> %tmp, ptr %__a, align 16471 %tmp1 = load <4 x i32>, ptr %xS32x4, align 16472 store <4 x i32> %tmp1, ptr %__b, align 16473 %tmp2 = load <4 x i32>, ptr %__a, align 16474 %tmp3 = bitcast <4 x i32> %tmp2 to <16 x i8>475 %tmp4 = load <4 x i32>, ptr %__b, align 16476 %tmp5 = bitcast <4 x i32> %tmp4 to <16 x i8>477 %tmp6 = bitcast <16 x i8> %tmp3 to <4 x i32>478 %tmp7 = bitcast <16 x i8> %tmp5 to <4 x i32>479 %vext = shufflevector <4 x i32> %tmp6, <4 x i32> %tmp7, <4 x i32> <i32 1, i32 2, i32 3, i32 4>480 store <4 x i32> %vext, ptr %xS32x4, align 16481 ret void482}483 484define void @test_vextq_u32() nounwind ssp {485; CHECK-LABEL: test_vextq_u32:486; CHECK: // %bb.0:487; CHECK-NEXT: sub sp, sp, #48488; CHECK-NEXT: ldr q0, [sp, #32]489; CHECK-NEXT: ext.16b v1, v0, v0, #8490; CHECK-NEXT: stp q0, q0, [sp]491; CHECK-NEXT: str q1, [sp, #32]492; CHECK-NEXT: add sp, sp, #48493; CHECK-NEXT: ret494 %xU32x4 = alloca <4 x i32>, align 16495 %__a = alloca <4 x i32>, align 16496 %__b = alloca <4 x i32>, align 16497 %tmp = load <4 x i32>, ptr %xU32x4, align 16498 store <4 x i32> %tmp, ptr %__a, align 16499 %tmp1 = load <4 x i32>, ptr %xU32x4, align 16500 store <4 x i32> %tmp1, ptr %__b, align 16501 %tmp2 = load <4 x i32>, ptr %__a, align 16502 %tmp3 = bitcast <4 x i32> %tmp2 to <16 x i8>503 %tmp4 = load <4 x i32>, ptr %__b, align 16504 %tmp5 = bitcast <4 x i32> %tmp4 to <16 x i8>505 %tmp6 = bitcast <16 x i8> %tmp3 to <4 x i32>506 %tmp7 = bitcast <16 x i8> %tmp5 to <4 x i32>507 %vext = shufflevector <4 x i32> %tmp6, <4 x i32> %tmp7, <4 x i32> <i32 2, i32 3, i32 4, i32 5>508 store <4 x i32> %vext, ptr %xU32x4, align 16509 ret void510}511 512define void @test_vextq_f32() nounwind ssp {513; CHECK-LABEL: test_vextq_f32:514; CHECK: // %bb.0:515; CHECK-NEXT: sub sp, sp, #48516; CHECK-NEXT: ldr q0, [sp, #32]517; CHECK-NEXT: ext.16b v1, v0, v0, #12518; CHECK-NEXT: stp q0, q0, [sp]519; CHECK-NEXT: str q1, [sp, #32]520; CHECK-NEXT: add sp, sp, #48521; CHECK-NEXT: ret522 %xF32x4 = alloca <4 x float>, align 16523 %__a = alloca <4 x float>, align 16524 %__b = alloca <4 x float>, align 16525 %tmp = load <4 x float>, ptr %xF32x4, align 16526 store <4 x float> %tmp, ptr %__a, align 16527 %tmp1 = load <4 x float>, ptr %xF32x4, align 16528 store <4 x float> %tmp1, ptr %__b, align 16529 %tmp2 = load <4 x float>, ptr %__a, align 16530 %tmp3 = bitcast <4 x float> %tmp2 to <16 x i8>531 %tmp4 = load <4 x float>, ptr %__b, align 16532 %tmp5 = bitcast <4 x float> %tmp4 to <16 x i8>533 %tmp6 = bitcast <16 x i8> %tmp3 to <4 x float>534 %tmp7 = bitcast <16 x i8> %tmp5 to <4 x float>535 %vext = shufflevector <4 x float> %tmp6, <4 x float> %tmp7, <4 x i32> <i32 3, i32 4, i32 5, i32 6>536 store <4 x float> %vext, ptr %xF32x4, align 16537 ret void538}539 540define void @test_vextq_s64() nounwind ssp {541; CHECK-LABEL: test_vextq_s64:542; CHECK: // %bb.0:543; CHECK-NEXT: sub sp, sp, #48544; CHECK-NEXT: ldr q0, [sp, #32]545; CHECK-NEXT: ext.16b v1, v0, v0, #8546; CHECK-NEXT: stp q0, q0, [sp]547; CHECK-NEXT: str q1, [sp, #32]548; CHECK-NEXT: add sp, sp, #48549; CHECK-NEXT: ret550 %xS64x2 = alloca <2 x i64>, align 16551 %__a = alloca <2 x i64>, align 16552 %__b = alloca <2 x i64>, align 16553 %tmp = load <2 x i64>, ptr %xS64x2, align 16554 store <2 x i64> %tmp, ptr %__a, align 16555 %tmp1 = load <2 x i64>, ptr %xS64x2, align 16556 store <2 x i64> %tmp1, ptr %__b, align 16557 %tmp2 = load <2 x i64>, ptr %__a, align 16558 %tmp3 = bitcast <2 x i64> %tmp2 to <16 x i8>559 %tmp4 = load <2 x i64>, ptr %__b, align 16560 %tmp5 = bitcast <2 x i64> %tmp4 to <16 x i8>561 %tmp6 = bitcast <16 x i8> %tmp3 to <2 x i64>562 %tmp7 = bitcast <16 x i8> %tmp5 to <2 x i64>563 %vext = shufflevector <2 x i64> %tmp6, <2 x i64> %tmp7, <2 x i32> <i32 1, i32 2>564 store <2 x i64> %vext, ptr %xS64x2, align 16565 ret void566}567 568define void @test_vextq_u64() nounwind ssp {569; CHECK-LABEL: test_vextq_u64:570; CHECK: // %bb.0:571; CHECK-NEXT: sub sp, sp, #48572; CHECK-NEXT: ldr q0, [sp, #32]573; CHECK-NEXT: ext.16b v1, v0, v0, #8574; CHECK-NEXT: stp q0, q0, [sp]575; CHECK-NEXT: str q1, [sp, #32]576; CHECK-NEXT: add sp, sp, #48577; CHECK-NEXT: ret578 %xU64x2 = alloca <2 x i64>, align 16579 %__a = alloca <2 x i64>, align 16580 %__b = alloca <2 x i64>, align 16581 %tmp = load <2 x i64>, ptr %xU64x2, align 16582 store <2 x i64> %tmp, ptr %__a, align 16583 %tmp1 = load <2 x i64>, ptr %xU64x2, align 16584 store <2 x i64> %tmp1, ptr %__b, align 16585 %tmp2 = load <2 x i64>, ptr %__a, align 16586 %tmp3 = bitcast <2 x i64> %tmp2 to <16 x i8>587 %tmp4 = load <2 x i64>, ptr %__b, align 16588 %tmp5 = bitcast <2 x i64> %tmp4 to <16 x i8>589 %tmp6 = bitcast <16 x i8> %tmp3 to <2 x i64>590 %tmp7 = bitcast <16 x i8> %tmp5 to <2 x i64>591 %vext = shufflevector <2 x i64> %tmp6, <2 x i64> %tmp7, <2 x i32> <i32 1, i32 2>592 store <2 x i64> %vext, ptr %xU64x2, align 16593 ret void594}595 596; shuffles with an undef second operand can use an EXT also so long as the597; indices wrap and stay sequential.598; rdar://12051674599define <16 x i8> @vext1(<16 x i8> %_a) nounwind {600; CHECK-LABEL: vext1:601; CHECK: // %bb.0:602; CHECK-NEXT: ext.16b v0, v0, v0, #8603; CHECK-NEXT: ret604 %vext = shufflevector <16 x i8> %_a, <16 x i8> undef, <16 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15, i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 7>605 ret <16 x i8> %vext606}607 608; <rdar://problem/12212062>609define <2 x i64> @vext2(<2 x i64> %p0, <2 x i64> %p1) nounwind readnone ssp {610; CHECK-LABEL: vext2:611; CHECK: // %bb.0: // %entry612; CHECK-NEXT: add.2d v0, v0, v1613; CHECK-NEXT: ext.16b v0, v0, v0, #8614; CHECK-NEXT: ret615entry:616 %t0 = shufflevector <2 x i64> %p1, <2 x i64> undef, <2 x i32> <i32 1, i32 0>617 %t1 = shufflevector <2 x i64> %p0, <2 x i64> undef, <2 x i32> <i32 1, i32 0>618 %t2 = add <2 x i64> %t1, %t0619 ret <2 x i64> %t2620}621