674 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py2; RUN: llc -mtriple=aarch64-unknown-linux-gnu < %s | FileCheck %s --check-prefixes CHECK,CHECK-LE3; RUN: llc -mtriple=aarch64_be-unknown-linux-gnu < %s | FileCheck %s --check-prefix CHECK-BE4; RUN: llc -mtriple=aarch64-unknown-linux-gnu -global-isel < %s | FileCheck %s --check-prefixes CHECK,CHECK-GI5 6declare <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16>, <4 x i16>)7declare <4 x i32> @llvm.aarch64.neon.umull.v4i32(<4 x i16>, <4 x i16>)8declare <8 x i8> @llvm.aarch64.neon.sabd.v8i8(<8 x i8>, <8 x i8>)9declare <8 x i8> @llvm.aarch64.neon.uabd.v8i8(<8 x i8>, <8 x i8>)10declare <4 x i32> @llvm.aarch64.neon.sqdmull.v4i32(<4 x i16>, <4 x i16>)11declare <4 x i32> @llvm.aarch64.neon.sqadd.v4i32(<4 x i32>, <4 x i32>)12declare <8 x i16> @llvm.aarch64.neon.pmull.v8i16(<8 x i8>, <8 x i8>)13declare <2 x i64> @llvm.aarch64.neon.umull.v2i64(<2 x i32> %s1, <2 x i32> %s2)14 15define <4 x i32> @test_smull_high_s16_base(<8 x i16> %a, <8 x i16> %b) #0 {16; CHECK-LABEL: test_smull_high_s16_base:17; CHECK: // %bb.0: // %entry18; CHECK-NEXT: smull2 v0.4s, v0.8h, v1.8h19; CHECK-NEXT: ret20;21; CHECK-BE-LABEL: test_smull_high_s16_base:22; CHECK-BE: // %bb.0: // %entry23; CHECK-BE-NEXT: rev64 v1.8h, v1.8h24; CHECK-BE-NEXT: rev64 v0.8h, v0.8h25; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #826; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #827; CHECK-BE-NEXT: smull2 v0.4s, v0.8h, v1.8h28; CHECK-BE-NEXT: rev64 v0.4s, v0.4s29; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #830; CHECK-BE-NEXT: ret31entry:32 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>33 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>34 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)35 ret <4 x i32> %r36}37 38define <4 x i32> @test_smull_high_s16_bitcasta1(<2 x i64> %aa, <8 x i16> %b) #0 {39; CHECK-LABEL: test_smull_high_s16_bitcasta1:40; CHECK: // %bb.0: // %entry41; CHECK-NEXT: smull2 v0.4s, v0.8h, v1.8h42; CHECK-NEXT: ret43;44; CHECK-BE-LABEL: test_smull_high_s16_bitcasta1:45; CHECK-BE: // %bb.0: // %entry46; CHECK-BE-NEXT: rev64 v1.8h, v1.8h47; CHECK-BE-NEXT: rev64 v0.8h, v0.8h48; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #849; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #850; CHECK-BE-NEXT: smull2 v0.4s, v0.8h, v1.8h51; CHECK-BE-NEXT: rev64 v0.4s, v0.4s52; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #853; CHECK-BE-NEXT: ret54entry:55 %a = bitcast <2 x i64> %aa to <8 x i16>56 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>57 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>58 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)59 ret <4 x i32> %r60}61 62define <4 x i32> @test_smull_high_s16_bitcastb1(<8 x i16> %a, <16 x i8> %bb) #0 {63; CHECK-LABEL: test_smull_high_s16_bitcastb1:64; CHECK: // %bb.0: // %entry65; CHECK-NEXT: smull2 v0.4s, v0.8h, v1.8h66; CHECK-NEXT: ret67;68; CHECK-BE-LABEL: test_smull_high_s16_bitcastb1:69; CHECK-BE: // %bb.0: // %entry70; CHECK-BE-NEXT: rev64 v0.8h, v0.8h71; CHECK-BE-NEXT: rev64 v1.8h, v1.8h72; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #873; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #874; CHECK-BE-NEXT: smull2 v0.4s, v0.8h, v1.8h75; CHECK-BE-NEXT: rev64 v0.4s, v0.4s76; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #877; CHECK-BE-NEXT: ret78entry:79 %b = bitcast <16 x i8> %bb to <8 x i16>80 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>81 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>82 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)83 ret <4 x i32> %r84}85 86define <4 x i32> @test_smull_high_s16_bitcasta2(<2 x i64> %a, <8 x i16> %b) #0 {87; CHECK-LABEL: test_smull_high_s16_bitcasta2:88; CHECK: // %bb.0: // %entry89; CHECK-NEXT: smull2 v0.4s, v0.8h, v1.8h90; CHECK-NEXT: ret91;92; CHECK-BE-LABEL: test_smull_high_s16_bitcasta2:93; CHECK-BE: // %bb.0: // %entry94; CHECK-BE-NEXT: rev64 v1.8h, v1.8h95; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #896; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #897; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #898; CHECK-BE-NEXT: rev64 v0.4h, v0.4h99; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8100; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h101; CHECK-BE-NEXT: rev64 v0.4s, v0.4s102; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8103; CHECK-BE-NEXT: ret104entry:105 %s1a = shufflevector <2 x i64> %a, <2 x i64> undef, <1 x i32> <i32 1>106 %s1 = bitcast <1 x i64> %s1a to <4 x i16>107 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>108 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)109 ret <4 x i32> %r110}111 112define <4 x i32> @test_smull_high_s16_bitcastb2(<8 x i16> %a, <16 x i8> %b) #0 {113; CHECK-LABEL: test_smull_high_s16_bitcastb2:114; CHECK: // %bb.0: // %entry115; CHECK-NEXT: smull2 v0.4s, v0.8h, v1.8h116; CHECK-NEXT: ret117;118; CHECK-BE-LABEL: test_smull_high_s16_bitcastb2:119; CHECK-BE: // %bb.0: // %entry120; CHECK-BE-NEXT: rev64 v1.16b, v1.16b121; CHECK-BE-NEXT: rev64 v0.8h, v0.8h122; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8123; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8124; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8125; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8126; CHECK-BE-NEXT: rev16 v1.8b, v1.8b127; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h128; CHECK-BE-NEXT: rev64 v0.4s, v0.4s129; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8130; CHECK-BE-NEXT: ret131entry:132 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>133 %s2a = shufflevector <16 x i8> %b, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>134 %s2 = bitcast <8 x i8> %s2a to <4 x i16>135 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)136 ret <4 x i32> %r137}138 139 140define <4 x i32> @test_smull_high_s16_bitcasta1_wrongindex(<2 x i64> %aa, <8 x i16> %b) #0 {141; CHECK-LE-LABEL: test_smull_high_s16_bitcasta1_wrongindex:142; CHECK-LE: // %bb.0: // %entry143; CHECK-LE-NEXT: ext v2.16b, v0.16b, v0.16b, #8144; CHECK-LE-NEXT: ext v1.16b, v1.16b, v1.16b, #8145; CHECK-LE-NEXT: ext v0.8b, v0.8b, v2.8b, #4146; CHECK-LE-NEXT: smull v0.4s, v0.4h, v1.4h147; CHECK-LE-NEXT: ret148;149; CHECK-BE-LABEL: test_smull_high_s16_bitcasta1_wrongindex:150; CHECK-BE: // %bb.0: // %entry151; CHECK-BE-NEXT: rev64 v1.8h, v1.8h152; CHECK-BE-NEXT: rev64 v0.8h, v0.8h153; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8154; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8155; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #4156; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8157; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h158; CHECK-BE-NEXT: rev64 v0.4s, v0.4s159; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8160; CHECK-BE-NEXT: ret161;162; CHECK-GI-LABEL: test_smull_high_s16_bitcasta1_wrongindex:163; CHECK-GI: // %bb.0: // %entry164; CHECK-GI-NEXT: ext v0.16b, v0.16b, v0.16b, #4165; CHECK-GI-NEXT: mov d1, v1.d[1]166; CHECK-GI-NEXT: smull v0.4s, v0.4h, v1.4h167; CHECK-GI-NEXT: ret168entry:169 %a = bitcast <2 x i64> %aa to <8 x i16>170 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 2, i32 3, i32 4, i32 5>171 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>172 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)173 ret <4 x i32> %r174}175 176define <4 x i32> @test_smull_high_s16_bitcastb1_wrongindex(<8 x i16> %a, <16 x i8> %bb) #0 {177; CHECK-LE-LABEL: test_smull_high_s16_bitcastb1_wrongindex:178; CHECK-LE: // %bb.0: // %entry179; CHECK-LE-NEXT: ext v2.16b, v1.16b, v1.16b, #8180; CHECK-LE-NEXT: ext v0.16b, v0.16b, v0.16b, #8181; CHECK-LE-NEXT: ext v1.8b, v1.8b, v2.8b, #6182; CHECK-LE-NEXT: smull v0.4s, v0.4h, v1.4h183; CHECK-LE-NEXT: ret184;185; CHECK-BE-LABEL: test_smull_high_s16_bitcastb1_wrongindex:186; CHECK-BE: // %bb.0: // %entry187; CHECK-BE-NEXT: rev64 v0.8h, v0.8h188; CHECK-BE-NEXT: rev64 v1.8h, v1.8h189; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8190; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8191; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8192; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #6193; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h194; CHECK-BE-NEXT: rev64 v0.4s, v0.4s195; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8196; CHECK-BE-NEXT: ret197;198; CHECK-GI-LABEL: test_smull_high_s16_bitcastb1_wrongindex:199; CHECK-GI: // %bb.0: // %entry200; CHECK-GI-NEXT: mov d0, v0.d[1]201; CHECK-GI-NEXT: ext v1.16b, v1.16b, v0.16b, #6202; CHECK-GI-NEXT: smull v0.4s, v0.4h, v1.4h203; CHECK-GI-NEXT: ret204entry:205 %b = bitcast <16 x i8> %bb to <8 x i16>206 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>207 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 3, i32 4, i32 5, i32 6>208 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)209 ret <4 x i32> %r210}211 212define <4 x i32> @test_smull_high_s16_bitcasta2_wrongindex(<4 x i32> %a, <8 x i16> %b) #0 {213; CHECK-LE-LABEL: test_smull_high_s16_bitcasta2_wrongindex:214; CHECK-LE: // %bb.0: // %entry215; CHECK-LE-NEXT: ext v0.16b, v0.16b, v0.16b, #4216; CHECK-LE-NEXT: ext v1.16b, v1.16b, v1.16b, #8217; CHECK-LE-NEXT: smull v0.4s, v0.4h, v1.4h218; CHECK-LE-NEXT: ret219;220; CHECK-BE-LABEL: test_smull_high_s16_bitcasta2_wrongindex:221; CHECK-BE: // %bb.0: // %entry222; CHECK-BE-NEXT: rev64 v0.4s, v0.4s223; CHECK-BE-NEXT: rev64 v1.8h, v1.8h224; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8225; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8226; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #4227; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8228; CHECK-BE-NEXT: rev32 v0.4h, v0.4h229; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h230; CHECK-BE-NEXT: rev64 v0.4s, v0.4s231; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8232; CHECK-BE-NEXT: ret233;234; CHECK-GI-LABEL: test_smull_high_s16_bitcasta2_wrongindex:235; CHECK-GI: // %bb.0: // %entry236; CHECK-GI-NEXT: ext v0.16b, v0.16b, v0.16b, #4237; CHECK-GI-NEXT: mov d1, v1.d[1]238; CHECK-GI-NEXT: smull v0.4s, v0.4h, v1.4h239; CHECK-GI-NEXT: ret240entry:241 %s1a = shufflevector <4 x i32> %a, <4 x i32> undef, <2 x i32> <i32 1, i32 2>242 %s1 = bitcast <2 x i32> %s1a to <4 x i16>243 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>244 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)245 ret <4 x i32> %r246}247 248define <4 x i32> @test_smull_high_s16_bitcastb2_wrongindex(<8 x i16> %a, <16 x i8> %b) #0 {249; CHECK-LE-LABEL: test_smull_high_s16_bitcastb2_wrongindex:250; CHECK-LE: // %bb.0: // %entry251; CHECK-LE-NEXT: ext v0.16b, v0.16b, v0.16b, #8252; CHECK-LE-NEXT: ext v1.16b, v1.16b, v1.16b, #4253; CHECK-LE-NEXT: smull v0.4s, v0.4h, v1.4h254; CHECK-LE-NEXT: ret255;256; CHECK-BE-LABEL: test_smull_high_s16_bitcastb2_wrongindex:257; CHECK-BE: // %bb.0: // %entry258; CHECK-BE-NEXT: rev64 v1.16b, v1.16b259; CHECK-BE-NEXT: rev64 v0.8h, v0.8h260; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8261; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8262; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #4263; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8264; CHECK-BE-NEXT: rev16 v1.8b, v1.8b265; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h266; CHECK-BE-NEXT: rev64 v0.4s, v0.4s267; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8268; CHECK-BE-NEXT: ret269;270; CHECK-GI-LABEL: test_smull_high_s16_bitcastb2_wrongindex:271; CHECK-GI: // %bb.0: // %entry272; CHECK-GI-NEXT: mov d0, v0.d[1]273; CHECK-GI-NEXT: ext v1.16b, v1.16b, v0.16b, #4274; CHECK-GI-NEXT: smull v0.4s, v0.4h, v1.4h275; CHECK-GI-NEXT: ret276entry:277 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>278 %s2a = shufflevector <16 x i8> %b, <16 x i8> undef, <8 x i32> <i32 4, i32 5, i32 6, i32 7, i32 8, i32 9, i32 10, i32 11>279 %s2 = bitcast <8 x i8> %s2a to <4 x i16>280 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)281 ret <4 x i32> %r282}283 284 285define <4 x i32> @test_smull_high_s16_splata1(<2 x i64> %aa, <8 x i16> %b) #0 {286; CHECK-LE-LABEL: test_smull_high_s16_splata1:287; CHECK-LE: // %bb.0: // %entry288; CHECK-LE-NEXT: smull2 v0.4s, v1.8h, v0.h[3]289; CHECK-LE-NEXT: ret290;291; CHECK-BE-LABEL: test_smull_high_s16_splata1:292; CHECK-BE: // %bb.0: // %entry293; CHECK-BE-NEXT: rev64 v1.8h, v1.8h294; CHECK-BE-NEXT: rev64 v0.8h, v0.8h295; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8296; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8297; CHECK-BE-NEXT: smull2 v0.4s, v1.8h, v0.h[3]298; CHECK-BE-NEXT: rev64 v0.4s, v0.4s299; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8300; CHECK-BE-NEXT: ret301;302; CHECK-GI-LABEL: test_smull_high_s16_splata1:303; CHECK-GI: // %bb.0: // %entry304; CHECK-GI-NEXT: mov d1, v1.d[1]305; CHECK-GI-NEXT: smull v0.4s, v1.4h, v0.h[3]306; CHECK-GI-NEXT: ret307entry:308 %a = bitcast <2 x i64> %aa to <8 x i16>309 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 3, i32 3, i32 3, i32 3>310 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>311 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)312 ret <4 x i32> %r313}314 315define <4 x i32> @test_smull_high_s16_splatb1(<8 x i16> %a, <16 x i8> %bb) #0 {316; CHECK-LE-LABEL: test_smull_high_s16_splatb1:317; CHECK-LE: // %bb.0: // %entry318; CHECK-LE-NEXT: smull2 v0.4s, v0.8h, v1.h[3]319; CHECK-LE-NEXT: ret320;321; CHECK-BE-LABEL: test_smull_high_s16_splatb1:322; CHECK-BE: // %bb.0: // %entry323; CHECK-BE-NEXT: rev64 v0.8h, v0.8h324; CHECK-BE-NEXT: rev64 v1.8h, v1.8h325; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8326; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8327; CHECK-BE-NEXT: smull2 v0.4s, v0.8h, v1.h[3]328; CHECK-BE-NEXT: rev64 v0.4s, v0.4s329; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8330; CHECK-BE-NEXT: ret331;332; CHECK-GI-LABEL: test_smull_high_s16_splatb1:333; CHECK-GI: // %bb.0: // %entry334; CHECK-GI-NEXT: mov d0, v0.d[1]335; CHECK-GI-NEXT: smull v0.4s, v0.4h, v1.h[3]336; CHECK-GI-NEXT: ret337entry:338 %b = bitcast <16 x i8> %bb to <8 x i16>339 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>340 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 3, i32 3, i32 3, i32 3>341 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)342 ret <4 x i32> %r343}344 345define <4 x i32> @test_smull_high_s16_splata2(<4 x i32> %a, <8 x i16> %b) #0 {346; CHECK-LE-LABEL: test_smull_high_s16_splata2:347; CHECK-LE: // %bb.0: // %entry348; CHECK-LE-NEXT: dup v0.2s, v0.s[3]349; CHECK-LE-NEXT: ext v1.16b, v1.16b, v1.16b, #8350; CHECK-LE-NEXT: smull v0.4s, v0.4h, v1.4h351; CHECK-LE-NEXT: ret352;353; CHECK-BE-LABEL: test_smull_high_s16_splata2:354; CHECK-BE: // %bb.0: // %entry355; CHECK-BE-NEXT: rev64 v0.4s, v0.4s356; CHECK-BE-NEXT: rev64 v1.8h, v1.8h357; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8358; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8359; CHECK-BE-NEXT: dup v0.2s, v0.s[3]360; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8361; CHECK-BE-NEXT: rev32 v0.4h, v0.4h362; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h363; CHECK-BE-NEXT: rev64 v0.4s, v0.4s364; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8365; CHECK-BE-NEXT: ret366;367; CHECK-GI-LABEL: test_smull_high_s16_splata2:368; CHECK-GI: // %bb.0: // %entry369; CHECK-GI-NEXT: dup v0.2s, v0.s[3]370; CHECK-GI-NEXT: mov d1, v1.d[1]371; CHECK-GI-NEXT: smull v0.4s, v0.4h, v1.4h372; CHECK-GI-NEXT: ret373entry:374 %s1a = shufflevector <4 x i32> %a, <4 x i32> undef, <2 x i32> <i32 3, i32 3>375 %s1 = bitcast <2 x i32> %s1a to <4 x i16>376 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>377 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)378 ret <4 x i32> %r379}380 381define <4 x i32> @test_smull_high_s16_splatb2(<8 x i16> %a, <16 x i8> %b) #0 {382; CHECK-LE-LABEL: test_smull_high_s16_splatb2:383; CHECK-LE: // %bb.0: // %entry384; CHECK-LE-NEXT: ext v0.16b, v0.16b, v0.16b, #8385; CHECK-LE-NEXT: dup v1.8b, v1.b[3]386; CHECK-LE-NEXT: smull v0.4s, v0.4h, v1.4h387; CHECK-LE-NEXT: ret388;389; CHECK-BE-LABEL: test_smull_high_s16_splatb2:390; CHECK-BE: // %bb.0: // %entry391; CHECK-BE-NEXT: rev64 v1.16b, v1.16b392; CHECK-BE-NEXT: rev64 v0.8h, v0.8h393; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8394; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8395; CHECK-BE-NEXT: dup v1.8b, v1.b[3]396; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8397; CHECK-BE-NEXT: rev16 v1.8b, v1.8b398; CHECK-BE-NEXT: smull v0.4s, v0.4h, v1.4h399; CHECK-BE-NEXT: rev64 v0.4s, v0.4s400; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8401; CHECK-BE-NEXT: ret402;403; CHECK-GI-LABEL: test_smull_high_s16_splatb2:404; CHECK-GI: // %bb.0: // %entry405; CHECK-GI-NEXT: mov d0, v0.d[1]406; CHECK-GI-NEXT: dup v1.8b, v1.b[3]407; CHECK-GI-NEXT: smull v0.4s, v0.4h, v1.4h408; CHECK-GI-NEXT: ret409entry:410 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>411 %s2a = shufflevector <16 x i8> %b, <16 x i8> undef, <8 x i32> <i32 3, i32 3, i32 3, i32 3, i32 3, i32 3, i32 3, i32 3>412 %s2 = bitcast <8 x i8> %s2a to <4 x i16>413 %r = call <4 x i32> @llvm.aarch64.neon.smull.v4i32(<4 x i16> %s1, <4 x i16> %s2)414 ret <4 x i32> %r415}416 417 418 419define <4 x i32> @test_umull_high_s16_bitcasta1(<2 x i64> %aa, <8 x i16> %b) #0 {420; CHECK-LABEL: test_umull_high_s16_bitcasta1:421; CHECK: // %bb.0: // %entry422; CHECK-NEXT: umull2 v0.4s, v0.8h, v1.8h423; CHECK-NEXT: ret424;425; CHECK-BE-LABEL: test_umull_high_s16_bitcasta1:426; CHECK-BE: // %bb.0: // %entry427; CHECK-BE-NEXT: rev64 v1.8h, v1.8h428; CHECK-BE-NEXT: rev64 v0.8h, v0.8h429; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8430; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8431; CHECK-BE-NEXT: umull2 v0.4s, v0.8h, v1.8h432; CHECK-BE-NEXT: rev64 v0.4s, v0.4s433; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8434; CHECK-BE-NEXT: ret435entry:436 %a = bitcast <2 x i64> %aa to <8 x i16>437 %s1 = shufflevector <8 x i16> %a, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>438 %s2 = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>439 %r = call <4 x i32> @llvm.aarch64.neon.umull.v4i32(<4 x i16> %s1, <4 x i16> %s2)440 ret <4 x i32> %r441}442 443define <8 x i16> @test_vabdl_high_u82(<16 x i8> %a, <8 x i16> %bb) {444; CHECK-LABEL: test_vabdl_high_u82:445; CHECK: // %bb.0: // %entry446; CHECK-NEXT: uabdl2 v0.8h, v0.16b, v1.16b447; CHECK-NEXT: ret448;449; CHECK-BE-LABEL: test_vabdl_high_u82:450; CHECK-BE: // %bb.0: // %entry451; CHECK-BE-NEXT: rev64 v0.16b, v0.16b452; CHECK-BE-NEXT: rev64 v1.16b, v1.16b453; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8454; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8455; CHECK-BE-NEXT: uabdl2 v0.8h, v0.16b, v1.16b456; CHECK-BE-NEXT: rev64 v0.8h, v0.8h457; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8458; CHECK-BE-NEXT: ret459entry:460 %b = bitcast <8 x i16> %bb to <16 x i8>461 %shuffle.i.i = shufflevector <16 x i8> %a, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>462 %shuffle.i3.i = shufflevector <16 x i8> %b, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>463 %vabd.i.i.i = tail call <8 x i8> @llvm.aarch64.neon.uabd.v8i8(<8 x i8> %shuffle.i.i, <8 x i8> %shuffle.i3.i)464 %vmovl.i.i.i = zext <8 x i8> %vabd.i.i.i to <8 x i16>465 ret <8 x i16> %vmovl.i.i.i466}467 468define <8 x i16> @test_vabdl_high_s82(<16 x i8> %a, <8 x i16> %bb) {469; CHECK-LABEL: test_vabdl_high_s82:470; CHECK: // %bb.0: // %entry471; CHECK-NEXT: sabdl2 v0.8h, v0.16b, v1.16b472; CHECK-NEXT: ret473;474; CHECK-BE-LABEL: test_vabdl_high_s82:475; CHECK-BE: // %bb.0: // %entry476; CHECK-BE-NEXT: rev64 v0.16b, v0.16b477; CHECK-BE-NEXT: rev64 v1.16b, v1.16b478; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8479; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8480; CHECK-BE-NEXT: sabdl2 v0.8h, v0.16b, v1.16b481; CHECK-BE-NEXT: rev64 v0.8h, v0.8h482; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8483; CHECK-BE-NEXT: ret484entry:485 %b = bitcast <8 x i16> %bb to <16 x i8>486 %shuffle.i.i = shufflevector <16 x i8> %a, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>487 %shuffle.i3.i = shufflevector <16 x i8> %b, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>488 %vabd.i.i.i = tail call <8 x i8> @llvm.aarch64.neon.sabd.v8i8(<8 x i8> %shuffle.i.i, <8 x i8> %shuffle.i3.i)489 %vmovl.i.i.i = zext <8 x i8> %vabd.i.i.i to <8 x i16>490 ret <8 x i16> %vmovl.i.i.i491}492 493define <4 x i32> @test_vqdmlal_high_s16_bitcast(<4 x i32> %a, <8 x i16> %b, <16 x i8> %cc) {494; CHECK-LABEL: test_vqdmlal_high_s16_bitcast:495; CHECK: // %bb.0: // %entry496; CHECK-NEXT: sqdmlal2 v0.4s, v1.8h, v2.8h497; CHECK-NEXT: ret498;499; CHECK-BE-LABEL: test_vqdmlal_high_s16_bitcast:500; CHECK-BE: // %bb.0: // %entry501; CHECK-BE-NEXT: rev64 v1.8h, v1.8h502; CHECK-BE-NEXT: rev64 v0.4s, v0.4s503; CHECK-BE-NEXT: rev64 v2.8h, v2.8h504; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8505; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8506; CHECK-BE-NEXT: ext v2.16b, v2.16b, v2.16b, #8507; CHECK-BE-NEXT: sqdmlal2 v0.4s, v1.8h, v2.8h508; CHECK-BE-NEXT: rev64 v0.4s, v0.4s509; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8510; CHECK-BE-NEXT: ret511entry:512 %c = bitcast <16 x i8> %cc to <8 x i16>513 %shuffle.i.i = shufflevector <8 x i16> %b, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>514 %shuffle.i3.i = shufflevector <8 x i16> %c, <8 x i16> undef, <4 x i32> <i32 4, i32 5, i32 6, i32 7>515 %vqdmlal2.i.i = tail call <4 x i32> @llvm.aarch64.neon.sqdmull.v4i32(<4 x i16> %shuffle.i.i, <4 x i16> %shuffle.i3.i)516 %vqdmlal4.i.i = tail call <4 x i32> @llvm.aarch64.neon.sqadd.v4i32(<4 x i32> %a, <4 x i32> %vqdmlal2.i.i)517 ret <4 x i32> %vqdmlal4.i.i518}519 520define <8 x i16> @test_pmull_high_p8_128(i128 %aa, i128 %bb) {521; CHECK-LE-LABEL: test_pmull_high_p8_128:522; CHECK-LE: // %bb.0: // %entry523; CHECK-LE-NEXT: fmov d0, x3524; CHECK-LE-NEXT: fmov d1, x1525; CHECK-LE-NEXT: pmull v0.8h, v1.8b, v0.8b526; CHECK-LE-NEXT: ret527;528; CHECK-BE-LABEL: test_pmull_high_p8_128:529; CHECK-BE: // %bb.0: // %entry530; CHECK-BE-NEXT: fmov d0, x3531; CHECK-BE-NEXT: fmov d1, x1532; CHECK-BE-NEXT: rev64 v0.8b, v0.8b533; CHECK-BE-NEXT: rev64 v1.8b, v1.8b534; CHECK-BE-NEXT: pmull v0.8h, v1.8b, v0.8b535; CHECK-BE-NEXT: rev64 v0.8h, v0.8h536; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8537; CHECK-BE-NEXT: ret538;539; CHECK-GI-LABEL: test_pmull_high_p8_128:540; CHECK-GI: // %bb.0: // %entry541; CHECK-GI-NEXT: mov v0.d[0], x0542; CHECK-GI-NEXT: mov v1.d[0], x2543; CHECK-GI-NEXT: mov v0.d[1], x1544; CHECK-GI-NEXT: mov v1.d[1], x3545; CHECK-GI-NEXT: pmull2 v0.8h, v0.16b, v1.16b546; CHECK-GI-NEXT: ret547entry:548 %a = bitcast i128 %aa to <16 x i8>549 %b = bitcast i128 %bb to <16 x i8>550 %shuffle.i.i = shufflevector <16 x i8> %a, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>551 %shuffle.i3.i = shufflevector <16 x i8> %b, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>552 %vmull.i.i = tail call <8 x i16> @llvm.aarch64.neon.pmull.v8i16(<8 x i8> %shuffle.i.i, <8 x i8> %shuffle.i3.i)553 ret <8 x i16> %vmull.i.i554}555 556define <8 x i16> @test_pmull_high_p8_64(<2 x i64> %aa, <2 x i64> %bb) {557; CHECK-LABEL: test_pmull_high_p8_64:558; CHECK: // %bb.0: // %entry559; CHECK-NEXT: pmull2 v0.8h, v0.16b, v1.16b560; CHECK-NEXT: ret561;562; CHECK-BE-LABEL: test_pmull_high_p8_64:563; CHECK-BE: // %bb.0: // %entry564; CHECK-BE-NEXT: rev64 v0.16b, v0.16b565; CHECK-BE-NEXT: rev64 v1.16b, v1.16b566; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8567; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8568; CHECK-BE-NEXT: pmull2 v0.8h, v0.16b, v1.16b569; CHECK-BE-NEXT: rev64 v0.8h, v0.8h570; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8571; CHECK-BE-NEXT: ret572entry:573 %a = bitcast <2 x i64> %aa to <16 x i8>574 %b = bitcast <2 x i64> %bb to <16 x i8>575 %shuffle.i.i = shufflevector <16 x i8> %a, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>576 %shuffle.i3.i = shufflevector <16 x i8> %b, <16 x i8> undef, <8 x i32> <i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15>577 %vmull.i.i = tail call <8 x i16> @llvm.aarch64.neon.pmull.v8i16(<8 x i8> %shuffle.i.i, <8 x i8> %shuffle.i3.i)578 ret <8 x i16> %vmull.i.i579}580 581define <8 x i16> @foov8i16(<16 x i8> %a1, <2 x i64> %b1) {582; CHECK-LE-LABEL: foov8i16:583; CHECK-LE: // %bb.0:584; CHECK-LE-NEXT: shrn v0.4h, v0.4s, #5585; CHECK-LE-NEXT: shrn2 v0.8h, v1.4s, #5586; CHECK-LE-NEXT: ret587;588; CHECK-BE-LABEL: foov8i16:589; CHECK-BE: // %bb.0:590; CHECK-BE-NEXT: rev64 v0.4s, v0.4s591; CHECK-BE-NEXT: rev64 v1.4s, v1.4s592; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8593; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8594; CHECK-BE-NEXT: shrn v0.4h, v0.4s, #5595; CHECK-BE-NEXT: shrn2 v0.8h, v1.4s, #5596; CHECK-BE-NEXT: rev64 v0.8h, v0.8h597; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8598; CHECK-BE-NEXT: ret599;600; CHECK-GI-LABEL: foov8i16:601; CHECK-GI: // %bb.0:602; CHECK-GI-NEXT: shrn v1.4h, v1.4s, #5603; CHECK-GI-NEXT: shrn v0.4h, v0.4s, #5604; CHECK-GI-NEXT: fmov x8, d1605; CHECK-GI-NEXT: mov v0.d[1], x8606; CHECK-GI-NEXT: ret607 %a0 = bitcast <16 x i8> %a1 to <4 x i32>608 %b0 = bitcast <2 x i64> %b1 to <4 x i32>609 %vshrn_low_shift = lshr <4 x i32> %a0, <i32 5, i32 5, i32 5, i32 5>610 %vshrn_low = trunc <4 x i32> %vshrn_low_shift to <4 x i16>611 %vshrn_high_shift = lshr <4 x i32> %b0, <i32 5, i32 5, i32 5, i32 5>612 %vshrn_high = trunc <4 x i32> %vshrn_high_shift to <4 x i16>613 %1 = bitcast <4 x i16> %vshrn_low to <1 x i64>614 %2 = bitcast <4 x i16> %vshrn_high to <1 x i64>615 %shuffle.i = shufflevector <1 x i64> %1, <1 x i64> %2, <2 x i32> <i32 0, i32 1>616 %3 = bitcast <2 x i64> %shuffle.i to <8 x i16>617 ret <8 x i16> %3618}619 620define <2 x i64> @hadd32_zext_asr(<16 x i8> %src1a) {621; CHECK-LE-LABEL: hadd32_zext_asr:622; CHECK-LE: // %bb.0:623; CHECK-LE-NEXT: ushll2 v0.2d, v0.4s, #1624; CHECK-LE-NEXT: ret625;626; CHECK-BE-LABEL: hadd32_zext_asr:627; CHECK-BE: // %bb.0:628; CHECK-BE-NEXT: rev64 v0.4s, v0.4s629; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8630; CHECK-BE-NEXT: ushll2 v0.2d, v0.4s, #1631; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8632; CHECK-BE-NEXT: ret633;634; CHECK-GI-LABEL: hadd32_zext_asr:635; CHECK-GI: // %bb.0:636; CHECK-GI-NEXT: mov d0, v0.d[1]637; CHECK-GI-NEXT: ushll v0.2d, v0.2s, #1638; CHECK-GI-NEXT: ret639 %src1 = bitcast <16 x i8> %src1a to <4 x i32>640 %s1 = shufflevector <4 x i32> %src1, <4 x i32> undef, <2 x i32> <i32 2, i32 3>641 %zextsrc1 = zext <2 x i32> %s1 to <2 x i64>642 %resulti32 = shl <2 x i64> %zextsrc1, <i64 1, i64 1>643 ret <2 x i64> %resulti32644}645 646define <2 x i64> @test_umull_high_s16_splata1(<2 x i64> %aa, <4 x i32> %b) #0 {647; CHECK-LE-LABEL: test_umull_high_s16_splata1:648; CHECK-LE: // %bb.0: // %entry649; CHECK-LE-NEXT: umull2 v0.2d, v1.4s, v0.s[1]650; CHECK-LE-NEXT: ret651;652; CHECK-BE-LABEL: test_umull_high_s16_splata1:653; CHECK-BE: // %bb.0: // %entry654; CHECK-BE-NEXT: rev64 v1.4s, v1.4s655; CHECK-BE-NEXT: rev64 v0.4s, v0.4s656; CHECK-BE-NEXT: ext v1.16b, v1.16b, v1.16b, #8657; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8658; CHECK-BE-NEXT: umull2 v0.2d, v1.4s, v0.s[1]659; CHECK-BE-NEXT: ext v0.16b, v0.16b, v0.16b, #8660; CHECK-BE-NEXT: ret661;662; CHECK-GI-LABEL: test_umull_high_s16_splata1:663; CHECK-GI: // %bb.0: // %entry664; CHECK-GI-NEXT: mov d1, v1.d[1]665; CHECK-GI-NEXT: umull v0.2d, v1.2s, v0.s[1]666; CHECK-GI-NEXT: ret667entry:668 %a = bitcast <2 x i64> %aa to <4 x i32>669 %s1 = shufflevector <4 x i32> %a, <4 x i32> undef, <2 x i32> <i32 1, i32 1>670 %s2 = shufflevector <4 x i32> %b, <4 x i32> undef, <2 x i32> <i32 2, i32 3>671 %r = call <2 x i64> @llvm.aarch64.neon.umull.v2i64(<2 x i32> %s1, <2 x i32> %s2)672 ret <2 x i64> %r673}674