481 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 42; RUN: llc -mattr=+sve < %s | FileCheck %s -check-prefix CHECK-SVE3; RUN: llc -mattr=+sve2p1 < %s | FileCheck %s -check-prefix CHECK-SVE2p1-SME2 -check-prefix CHECK-SVE2p14; RUN: llc -mattr=+sve -mattr=+sme2 -force-streaming < %s | FileCheck %s -check-prefix CHECK-SVE2p1-SME2 -check-prefix CHECK-SME25target triple = "aarch64-linux"6 7; Test combining of getActiveLaneMask with a pair of extract_vector operations.8 9define void @test_2x8bit_mask_with_32bit_index_and_trip_count(i32 %i, i32 %n) #0 {10; CHECK-SVE-LABEL: test_2x8bit_mask_with_32bit_index_and_trip_count:11; CHECK-SVE: // %bb.0:12; CHECK-SVE-NEXT: whilelo p1.b, w0, w113; CHECK-SVE-NEXT: punpklo p0.h, p1.b14; CHECK-SVE-NEXT: punpkhi p1.h, p1.b15; CHECK-SVE-NEXT: b use16;17; CHECK-SVE2p1-SME2-LABEL: test_2x8bit_mask_with_32bit_index_and_trip_count:18; CHECK-SVE2p1-SME2: // %bb.0:19; CHECK-SVE2p1-SME2-NEXT: mov w8, w120; CHECK-SVE2p1-SME2-NEXT: mov w9, w021; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.h, p1.h }, x9, x822; CHECK-SVE2p1-SME2-NEXT: b use23 %r = call <vscale x 16 x i1> @llvm.get.active.lane.mask.nxv16i1.i32(i32 %i, i32 %n)24 %v0 = call <vscale x 8 x i1> @llvm.vector.extract.nxv8i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 0)25 %v1 = call <vscale x 8 x i1> @llvm.vector.extract.nxv8i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 8)26 tail call void @use(<vscale x 8 x i1> %v0, <vscale x 8 x i1> %v1)27 ret void28}29 30define void @test_2x8bit_mask_with_64bit_index_and_trip_count(i64 %i, i64 %n) #0 {31; CHECK-SVE-LABEL: test_2x8bit_mask_with_64bit_index_and_trip_count:32; CHECK-SVE: // %bb.0:33; CHECK-SVE-NEXT: whilelo p1.b, x0, x134; CHECK-SVE-NEXT: punpklo p0.h, p1.b35; CHECK-SVE-NEXT: punpkhi p1.h, p1.b36; CHECK-SVE-NEXT: b use37;38; CHECK-SVE2p1-SME2-LABEL: test_2x8bit_mask_with_64bit_index_and_trip_count:39; CHECK-SVE2p1-SME2: // %bb.0:40; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.h, p1.h }, x0, x141; CHECK-SVE2p1-SME2-NEXT: b use42 %r = call <vscale x 16 x i1> @llvm.get.active.lane.mask.nxv16i1.i64(i64 %i, i64 %n)43 %v0 = call <vscale x 8 x i1> @llvm.vector.extract.nxv8i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 0)44 %v1 = call <vscale x 8 x i1> @llvm.vector.extract.nxv8i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 8)45 tail call void @use(<vscale x 8 x i1> %v0, <vscale x 8 x i1> %v1)46 ret void47}48 49define void @test_edge_case_2x1bit_mask(i64 %i, i64 %n) #0 {50; CHECK-SVE-LABEL: test_edge_case_2x1bit_mask:51; CHECK-SVE: // %bb.0:52; CHECK-SVE-NEXT: whilelo p1.d, x0, x153; CHECK-SVE-NEXT: punpklo p0.h, p1.b54; CHECK-SVE-NEXT: punpkhi p1.h, p1.b55; CHECK-SVE-NEXT: b use56;57; CHECK-SVE2p1-SME2-LABEL: test_edge_case_2x1bit_mask:58; CHECK-SVE2p1-SME2: // %bb.0:59; CHECK-SVE2p1-SME2-NEXT: whilelo p1.d, x0, x160; CHECK-SVE2p1-SME2-NEXT: punpklo p0.h, p1.b61; CHECK-SVE2p1-SME2-NEXT: punpkhi p1.h, p1.b62; CHECK-SVE2p1-SME2-NEXT: b use63 %r = call <vscale x 2 x i1> @llvm.get.active.lane.mask.nxv2i1.i64(i64 %i, i64 %n)64 %v0 = call <vscale x 1 x i1> @llvm.vector.extract.nxv1i1.nxv2i1.i64(<vscale x 2 x i1> %r, i64 0)65 %v1 = call <vscale x 1 x i1> @llvm.vector.extract.nxv1i1.nxv2i1.i64(<vscale x 2 x i1> %r, i64 1)66 tail call void @use(<vscale x 1 x i1> %v0, <vscale x 1 x i1> %v1)67 ret void68}69 70define void @test_boring_case_2x2bit_mask(i64 %i, i64 %n) #0 {71; CHECK-SVE-LABEL: test_boring_case_2x2bit_mask:72; CHECK-SVE: // %bb.0:73; CHECK-SVE-NEXT: whilelo p1.s, x0, x174; CHECK-SVE-NEXT: punpklo p0.h, p1.b75; CHECK-SVE-NEXT: punpkhi p1.h, p1.b76; CHECK-SVE-NEXT: b use77;78; CHECK-SVE2p1-SME2-LABEL: test_boring_case_2x2bit_mask:79; CHECK-SVE2p1-SME2: // %bb.0:80; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.d, p1.d }, x0, x181; CHECK-SVE2p1-SME2-NEXT: b use82 %r = call <vscale x 4 x i1> @llvm.get.active.lane.mask.nxv4i1.i64(i64 %i, i64 %n)83 %v0 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv4i1.i64(<vscale x 4 x i1> %r, i64 0)84 %v1 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv4i1.i64(<vscale x 4 x i1> %r, i64 2)85 tail call void @use(<vscale x 2 x i1> %v0, <vscale x 2 x i1> %v1)86 ret void87}88 89define void @test_legal_4x2bit_mask(i64 %i, i64 %n) #0 {90; CHECK-SVE-LABEL: test_legal_4x2bit_mask:91; CHECK-SVE: // %bb.0:92; CHECK-SVE-NEXT: whilelo p0.h, x0, x193; CHECK-SVE-NEXT: punpkhi p1.h, p0.b94; CHECK-SVE-NEXT: punpklo p4.h, p0.b95; CHECK-SVE-NEXT: punpkhi p3.h, p1.b96; CHECK-SVE-NEXT: punpklo p2.h, p1.b97; CHECK-SVE-NEXT: punpklo p0.h, p4.b98; CHECK-SVE-NEXT: punpkhi p1.h, p4.b99; CHECK-SVE-NEXT: b use100;101; CHECK-SVE2p1-SME2-LABEL: test_legal_4x2bit_mask:102; CHECK-SVE2p1-SME2: // %bb.0:103; CHECK-SVE2p1-SME2-NEXT: cntw x8104; CHECK-SVE2p1-SME2-NEXT: adds x8, x0, x8105; CHECK-SVE2p1-SME2-NEXT: csinv x8, x8, xzr, lo106; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.d, p1.d }, x0, x1107; CHECK-SVE2p1-SME2-NEXT: whilelo { p2.d, p3.d }, x8, x1108; CHECK-SVE2p1-SME2-NEXT: b use109 %r = call <vscale x 8 x i1> @llvm.get.active.lane.mask.nxv8i1.i64(i64 %i, i64 %n)110 %v0 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 6)111 %v1 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 4)112 %v2 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 2)113 %v3 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 0)114 tail call void @use(<vscale x 2 x i1> %v3, <vscale x 2 x i1> %v2, <vscale x 2 x i1> %v1, <vscale x 2 x i1> %v0)115 ret void116}117 118; Negative test where the extract types are correct but we are not extracting all parts of the mask119; Note: We could still create a whilelo_x2 for the first two extracts, but we don't expect this case often yet.120define void @test_partial_extract_correct_types(i64 %i, i64 %n) #0 {121; CHECK-SVE-LABEL: test_partial_extract_correct_types:122; CHECK-SVE: // %bb.0:123; CHECK-SVE-NEXT: whilelo p0.h, x0, x1124; CHECK-SVE-NEXT: punpklo p1.h, p0.b125; CHECK-SVE-NEXT: punpkhi p2.h, p0.b126; CHECK-SVE-NEXT: punpklo p0.h, p1.b127; CHECK-SVE-NEXT: punpkhi p1.h, p1.b128; CHECK-SVE-NEXT: punpkhi p2.h, p2.b129; CHECK-SVE-NEXT: b use130;131; CHECK-SVE2p1-SME2-LABEL: test_partial_extract_correct_types:132; CHECK-SVE2p1-SME2: // %bb.0:133; CHECK-SVE2p1-SME2-NEXT: whilelo p0.h, x0, x1134; CHECK-SVE2p1-SME2-NEXT: punpklo p1.h, p0.b135; CHECK-SVE2p1-SME2-NEXT: punpkhi p2.h, p0.b136; CHECK-SVE2p1-SME2-NEXT: punpklo p0.h, p1.b137; CHECK-SVE2p1-SME2-NEXT: punpkhi p1.h, p1.b138; CHECK-SVE2p1-SME2-NEXT: punpkhi p2.h, p2.b139; CHECK-SVE2p1-SME2-NEXT: b use140 %r = call <vscale x 8 x i1> @llvm.get.active.lane.mask.nxv8i1.i64(i64 %i, i64 %n)141 %v0 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 0)142 %v1 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 2)143 %v2 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 6)144 tail call void @use(<vscale x 2 x i1> %v0, <vscale x 2 x i1> %v1, <vscale x 2 x i1> %v2)145 ret void146}147 148; Negative test for when not extracting exactly two halves of the source vector149define void @test_partial_extract(i64 %i, i64 %n) #0 {150; CHECK-SVE-LABEL: test_partial_extract:151; CHECK-SVE: // %bb.0:152; CHECK-SVE-NEXT: whilelo p0.h, x0, x1153; CHECK-SVE-NEXT: punpklo p1.h, p0.b154; CHECK-SVE-NEXT: punpkhi p2.h, p0.b155; CHECK-SVE-NEXT: punpklo p0.h, p1.b156; CHECK-SVE-NEXT: punpklo p1.h, p2.b157; CHECK-SVE-NEXT: b use158;159; CHECK-SVE2p1-SME2-LABEL: test_partial_extract:160; CHECK-SVE2p1-SME2: // %bb.0:161; CHECK-SVE2p1-SME2-NEXT: whilelo p0.h, x0, x1162; CHECK-SVE2p1-SME2-NEXT: punpklo p1.h, p0.b163; CHECK-SVE2p1-SME2-NEXT: punpkhi p2.h, p0.b164; CHECK-SVE2p1-SME2-NEXT: punpklo p0.h, p1.b165; CHECK-SVE2p1-SME2-NEXT: punpklo p1.h, p2.b166; CHECK-SVE2p1-SME2-NEXT: b use167 %r = call <vscale x 8 x i1> @llvm.get.active.lane.mask.nxv8i1.i64(i64 %i, i64 %n)168 %v0 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 0)169 %v1 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 4)170 tail call void @use(<vscale x 2 x i1> %v0, <vscale x 2 x i1> %v1)171 ret void172}173 174; Negative test for when extracting a fixed-length vector.175define void @test_fixed_extract(i64 %i, i64 %n) #0 {176; CHECK-SVE-LABEL: test_fixed_extract:177; CHECK-SVE: // %bb.0:178; CHECK-SVE-NEXT: whilelo p0.s, x0, x1179; CHECK-SVE-NEXT: cset w8, mi180; CHECK-SVE-NEXT: mov z1.s, p0/z, #1 // =0x1181; CHECK-SVE-NEXT: fmov s0, w8182; CHECK-SVE-NEXT: mov v0.s[1], v1.s[1]183; CHECK-SVE-NEXT: ext z1.b, z1.b, z1.b, #8184; CHECK-SVE-NEXT: // kill: def $d0 killed $d0 killed $q0185; CHECK-SVE-NEXT: // kill: def $d1 killed $d1 killed $z1186; CHECK-SVE-NEXT: b use187;188; CHECK-SVE2p1-LABEL: test_fixed_extract:189; CHECK-SVE2p1: // %bb.0:190; CHECK-SVE2p1-NEXT: whilelo p0.s, x0, x1191; CHECK-SVE2p1-NEXT: cset w8, mi192; CHECK-SVE2p1-NEXT: mov z1.s, p0/z, #1 // =0x1193; CHECK-SVE2p1-NEXT: fmov s0, w8194; CHECK-SVE2p1-NEXT: mov v0.s[1], v1.s[1]195; CHECK-SVE2p1-NEXT: ext z1.b, z1.b, z1.b, #8196; CHECK-SVE2p1-NEXT: // kill: def $d0 killed $d0 killed $q0197; CHECK-SVE2p1-NEXT: // kill: def $d1 killed $d1 killed $z1198; CHECK-SVE2p1-NEXT: b use199;200; CHECK-SME2-LABEL: test_fixed_extract:201; CHECK-SME2: // %bb.0:202; CHECK-SME2-NEXT: whilelo p0.s, x0, x1203; CHECK-SME2-NEXT: cset w8, mi204; CHECK-SME2-NEXT: mov z1.s, p0/z, #1 // =0x1205; CHECK-SME2-NEXT: fmov s2, w8206; CHECK-SME2-NEXT: mov z0.s, z1.s[1]207; CHECK-SME2-NEXT: ext z1.b, z1.b, z1.b, #8208; CHECK-SME2-NEXT: // kill: def $d1 killed $d1 killed $z1209; CHECK-SME2-NEXT: zip1 z0.s, z2.s, z0.s210; CHECK-SME2-NEXT: // kill: def $d0 killed $d0 killed $z0211; CHECK-SME2-NEXT: b use212 %r = call <vscale x 4 x i1> @llvm.get.active.lane.mask.nxv4i1.i64(i64 %i, i64 %n)213 %v0 = call <2 x i1> @llvm.vector.extract.v2i1.nxv4i1.i64(<vscale x 4 x i1> %r, i64 0)214 %v1 = call <2 x i1> @llvm.vector.extract.v2i1.nxv4i1.i64(<vscale x 4 x i1> %r, i64 2)215 tail call void @use(<2 x i1> %v0, <2 x i1> %v1)216 ret void217}218 219; Negative test where the number of extracts is right, but they cannot be combined because220; there is not an extract for each part221define void @test_4x2bit_duplicate_mask(i64 %i, i64 %n) #0 {222; CHECK-SVE-LABEL: test_4x2bit_duplicate_mask:223; CHECK-SVE: // %bb.0:224; CHECK-SVE-NEXT: whilelo p0.h, x0, x1225; CHECK-SVE-NEXT: punpklo p1.h, p0.b226; CHECK-SVE-NEXT: punpkhi p3.h, p0.b227; CHECK-SVE-NEXT: punpkhi p0.h, p1.b228; CHECK-SVE-NEXT: punpklo p2.h, p3.b229; CHECK-SVE-NEXT: punpkhi p3.h, p3.b230; CHECK-SVE-NEXT: mov p1.b, p0.b231; CHECK-SVE-NEXT: b use232;233; CHECK-SVE2p1-SME2-LABEL: test_4x2bit_duplicate_mask:234; CHECK-SVE2p1-SME2: // %bb.0:235; CHECK-SVE2p1-SME2-NEXT: whilelo p0.h, x0, x1236; CHECK-SVE2p1-SME2-NEXT: punpklo p1.h, p0.b237; CHECK-SVE2p1-SME2-NEXT: punpkhi p3.h, p0.b238; CHECK-SVE2p1-SME2-NEXT: punpkhi p0.h, p1.b239; CHECK-SVE2p1-SME2-NEXT: punpklo p2.h, p3.b240; CHECK-SVE2p1-SME2-NEXT: punpkhi p3.h, p3.b241; CHECK-SVE2p1-SME2-NEXT: mov p1.b, p0.b242; CHECK-SVE2p1-SME2-NEXT: b use243 %r = call <vscale x 8 x i1> @llvm.get.active.lane.mask.nxv8i1.i64(i64 %i, i64 %n)244 %v0 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 2)245 %v1 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 2)246 %v2 = call <vscale x 2 x i1> @llvm.vector.extract.nxv4i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 4)247 %v3 = call <vscale x 2 x i1> @llvm.vector.extract.nxv4i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 6)248 tail call void @use(<vscale x 2 x i1> %v0, <vscale x 2 x i1> %v1, <vscale x 2 x i1> %v2, <vscale x 2 x i1> %v3)249 ret void250}251 252; Illegal Types253 254define void @test_2x16bit_mask_with_32bit_index_and_trip_count(i32 %i, i32 %n) #0 {255; CHECK-SVE-LABEL: test_2x16bit_mask_with_32bit_index_and_trip_count:256; CHECK-SVE: // %bb.0:257; CHECK-SVE-NEXT: rdvl x8, #1258; CHECK-SVE-NEXT: adds w8, w0, w8259; CHECK-SVE-NEXT: csinv w8, w8, wzr, lo260; CHECK-SVE-NEXT: whilelo p0.b, w0, w1261; CHECK-SVE-NEXT: whilelo p1.b, w8, w1262; CHECK-SVE-NEXT: b use263;264; CHECK-SVE2p1-SME2-LABEL: test_2x16bit_mask_with_32bit_index_and_trip_count:265; CHECK-SVE2p1-SME2: // %bb.0:266; CHECK-SVE2p1-SME2-NEXT: mov w8, w1267; CHECK-SVE2p1-SME2-NEXT: mov w9, w0268; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.b, p1.b }, x9, x8269; CHECK-SVE2p1-SME2-NEXT: b use270 %r = call <vscale x 32 x i1> @llvm.get.active.lane.mask.nxv32i1.i32(i32 %i, i32 %n)271 %v0 = call <vscale x 16 x i1> @llvm.vector.extract.nxv16i1.nxv32i1.i64(<vscale x 32 x i1> %r, i64 0)272 %v1 = call <vscale x 16 x i1> @llvm.vector.extract.nxv16i1.nxv32i1.i64(<vscale x 32 x i1> %r, i64 16)273 tail call void @use(<vscale x 16 x i1> %v0, <vscale x 16 x i1> %v1)274 ret void275}276 277define void @test_2x32bit_mask_with_32bit_index_and_trip_count(i32 %i, i32 %n) #0 {278; CHECK-SVE-LABEL: test_2x32bit_mask_with_32bit_index_and_trip_count:279; CHECK-SVE: // %bb.0:280; CHECK-SVE-NEXT: rdvl x8, #2281; CHECK-SVE-NEXT: rdvl x9, #1282; CHECK-SVE-NEXT: adds w8, w0, w8283; CHECK-SVE-NEXT: csinv w8, w8, wzr, lo284; CHECK-SVE-NEXT: adds w10, w8, w9285; CHECK-SVE-NEXT: csinv w10, w10, wzr, lo286; CHECK-SVE-NEXT: whilelo p3.b, w10, w1287; CHECK-SVE-NEXT: adds w9, w0, w9288; CHECK-SVE-NEXT: csinv w9, w9, wzr, lo289; CHECK-SVE-NEXT: whilelo p0.b, w0, w1290; CHECK-SVE-NEXT: whilelo p1.b, w9, w1291; CHECK-SVE-NEXT: whilelo p2.b, w8, w1292; CHECK-SVE-NEXT: b use293;294; CHECK-SVE2p1-SME2-LABEL: test_2x32bit_mask_with_32bit_index_and_trip_count:295; CHECK-SVE2p1-SME2: // %bb.0:296; CHECK-SVE2p1-SME2-NEXT: rdvl x8, #2297; CHECK-SVE2p1-SME2-NEXT: mov w9, w1298; CHECK-SVE2p1-SME2-NEXT: mov w10, w0299; CHECK-SVE2p1-SME2-NEXT: adds w8, w0, w8300; CHECK-SVE2p1-SME2-NEXT: csinv w8, w8, wzr, lo301; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.b, p1.b }, x10, x9302; CHECK-SVE2p1-SME2-NEXT: whilelo { p2.b, p3.b }, x8, x9303; CHECK-SVE2p1-SME2-NEXT: b use304 %r = call <vscale x 64 x i1> @llvm.get.active.lane.mask.nxv64i1.i32(i32 %i, i32 %n)305 %v0 = call <vscale x 16 x i1> @llvm.vector.extract.nxv16i1.nxv64i1.i64(<vscale x 64 x i1> %r, i64 0)306 %v1 = call <vscale x 16 x i1> @llvm.vector.extract.nxv16i1.nxv64i1.i64(<vscale x 64 x i1> %r, i64 16)307 %v2 = call <vscale x 16 x i1> @llvm.vector.extract.nxv16i1.nxv64i1.i64(<vscale x 64 x i1> %r, i64 32)308 %v3 = call <vscale x 16 x i1> @llvm.vector.extract.nxv16i1.nxv64i1.i64(<vscale x 64 x i1> %r, i64 48)309 tail call void @use(<vscale x 16 x i1> %v0, <vscale x 16 x i1> %v1, <vscale x 16 x i1> %v2, <vscale x 16 x i1> %v3)310 ret void311}312 313; Extra use of the get_active_lane_mask from an extractelement, which is replaced with ptest_first.314 315define void @test_2x8bit_mask_with_extracts_and_ptest(i64 %i, i64 %n) {316; CHECK-SVE-LABEL: test_2x8bit_mask_with_extracts_and_ptest:317; CHECK-SVE: // %bb.0: // %entry318; CHECK-SVE-NEXT: whilelo p1.b, x0, x1319; CHECK-SVE-NEXT: b.pl .LBB11_2320; CHECK-SVE-NEXT: // %bb.1: // %if.then321; CHECK-SVE-NEXT: punpklo p0.h, p1.b322; CHECK-SVE-NEXT: punpkhi p1.h, p1.b323; CHECK-SVE-NEXT: b use324; CHECK-SVE-NEXT: .LBB11_2: // %if.end325; CHECK-SVE-NEXT: ret326;327; CHECK-SVE2p1-SME2-LABEL: test_2x8bit_mask_with_extracts_and_ptest:328; CHECK-SVE2p1-SME2: // %bb.0: // %entry329; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.h, p1.h }, x0, x1330; CHECK-SVE2p1-SME2-NEXT: b.pl .LBB11_2331; CHECK-SVE2p1-SME2-NEXT: // %bb.1: // %if.then332; CHECK-SVE2p1-SME2-NEXT: b use333; CHECK-SVE2p1-SME2-NEXT: .LBB11_2: // %if.end334; CHECK-SVE2p1-SME2-NEXT: ret335entry:336 %r = call <vscale x 16 x i1> @llvm.get.active.lane.mask.nxv16i1.i32(i64 %i, i64 %n)337 %v0 = call <vscale x 8 x i1> @llvm.vector.extract.nxv8i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 0)338 %v1 = call <vscale x 8 x i1> @llvm.vector.extract.nxv8i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 8)339 %elt0 = extractelement <vscale x 16 x i1> %r, i32 0340 br i1 %elt0, label %if.then, label %if.end341 342if.then:343 tail call void @use(<vscale x 8 x i1> %v0, <vscale x 8 x i1> %v1)344 br label %if.end345 346if.end:347 ret void348}349 350; Extra use of the get_active_lane_mask from an extractelement, which is351; replaced with ptest_first and reinterpret_casts because the extract is not nxv16i1.352 353define void @test_2x8bit_mask_with_extracts_and_reinterpret_casts(i64 %i, i64 %n) {354; CHECK-SVE-LABEL: test_2x8bit_mask_with_extracts_and_reinterpret_casts:355; CHECK-SVE: // %bb.0: // %entry356; CHECK-SVE-NEXT: whilelo p1.h, x0, x1357; CHECK-SVE-NEXT: b.pl .LBB12_2358; CHECK-SVE-NEXT: // %bb.1: // %if.then359; CHECK-SVE-NEXT: punpklo p0.h, p1.b360; CHECK-SVE-NEXT: punpkhi p1.h, p1.b361; CHECK-SVE-NEXT: b use362; CHECK-SVE-NEXT: .LBB12_2: // %if.end363; CHECK-SVE-NEXT: ret364;365; CHECK-SVE2p1-SME2-LABEL: test_2x8bit_mask_with_extracts_and_reinterpret_casts:366; CHECK-SVE2p1-SME2: // %bb.0: // %entry367; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.s, p1.s }, x0, x1368; CHECK-SVE2p1-SME2-NEXT: b.pl .LBB12_2369; CHECK-SVE2p1-SME2-NEXT: // %bb.1: // %if.then370; CHECK-SVE2p1-SME2-NEXT: b use371; CHECK-SVE2p1-SME2-NEXT: .LBB12_2: // %if.end372; CHECK-SVE2p1-SME2-NEXT: ret373entry:374 %r = call <vscale x 8 x i1> @llvm.get.active.lane.mask.nxv8i1.i64(i64 %i, i64 %n)375 %v0 = tail call <vscale x 4 x i1> @llvm.vector.extract.nxv4i1.nxv8i1(<vscale x 8 x i1> %r, i64 0)376 %v1 = tail call <vscale x 4 x i1> @llvm.vector.extract.nxv4i1.nxv8i1(<vscale x 8 x i1> %r, i64 4)377 %elt0 = extractelement <vscale x 8 x i1> %r, i64 0378 br i1 %elt0, label %if.then, label %if.end379 380if.then:381 tail call void @use(<vscale x 4 x i1> %v0, <vscale x 4 x i1> %v1)382 br label %if.end383 384if.end:385 ret void386}387 388define void @test_4x4bit_mask_with_extracts_and_ptest(i64 %i, i64 %n) {389; CHECK-SVE-LABEL: test_4x4bit_mask_with_extracts_and_ptest:390; CHECK-SVE: // %bb.0: // %entry391; CHECK-SVE-NEXT: whilelo p0.b, x0, x1392; CHECK-SVE-NEXT: b.pl .LBB13_2393; CHECK-SVE-NEXT: // %bb.1: // %if.then394; CHECK-SVE-NEXT: punpklo p1.h, p0.b395; CHECK-SVE-NEXT: punpkhi p3.h, p0.b396; CHECK-SVE-NEXT: punpklo p0.h, p1.b397; CHECK-SVE-NEXT: punpkhi p1.h, p1.b398; CHECK-SVE-NEXT: punpklo p2.h, p3.b399; CHECK-SVE-NEXT: punpkhi p3.h, p3.b400; CHECK-SVE-NEXT: b use401; CHECK-SVE-NEXT: .LBB13_2: // %if.end402; CHECK-SVE-NEXT: ret403;404; CHECK-SVE2p1-SME2-LABEL: test_4x4bit_mask_with_extracts_and_ptest:405; CHECK-SVE2p1-SME2: // %bb.0: // %entry406; CHECK-SVE2p1-SME2-NEXT: cnth x8407; CHECK-SVE2p1-SME2-NEXT: adds x8, x0, x8408; CHECK-SVE2p1-SME2-NEXT: csinv x8, x8, xzr, lo409; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.s, p1.s }, x0, x1410; CHECK-SVE2p1-SME2-NEXT: b.pl .LBB13_2411; CHECK-SVE2p1-SME2-NEXT: // %bb.1: // %if.then412; CHECK-SVE2p1-SME2-NEXT: whilelo { p2.s, p3.s }, x8, x1413; CHECK-SVE2p1-SME2-NEXT: b use414; CHECK-SVE2p1-SME2-NEXT: .LBB13_2: // %if.end415; CHECK-SVE2p1-SME2-NEXT: ret416entry:417 %r = call <vscale x 16 x i1> @llvm.get.active.lane.mask.nxv16i1.i32(i64 %i, i64 %n)418 %v0 = call <vscale x 4 x i1> @llvm.vector.extract.nxv4i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 0)419 %v1 = call <vscale x 4 x i1> @llvm.vector.extract.nxv4i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 4)420 %v2 = call <vscale x 4 x i1> @llvm.vector.extract.nxv4i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 8)421 %v3 = call <vscale x 4 x i1> @llvm.vector.extract.nxv4i1.nxv16i1.i64(<vscale x 16 x i1> %r, i64 12)422 %elt0 = extractelement <vscale x 16 x i1> %r, i32 0423 br i1 %elt0, label %if.then, label %if.end424 425if.then:426 tail call void @use(<vscale x 4 x i1> %v0, <vscale x 4 x i1> %v1, <vscale x 4 x i1> %v2, <vscale x 4 x i1> %v3)427 br label %if.end428 429if.end:430 ret void431}432 433define void @test_4x2bit_mask_with_extracts_and_reinterpret_casts(i64 %i, i64 %n) {434; CHECK-SVE-LABEL: test_4x2bit_mask_with_extracts_and_reinterpret_casts:435; CHECK-SVE: // %bb.0: // %entry436; CHECK-SVE-NEXT: whilelo p0.h, x0, x1437; CHECK-SVE-NEXT: b.pl .LBB14_2438; CHECK-SVE-NEXT: // %bb.1: // %if.then439; CHECK-SVE-NEXT: punpklo p1.h, p0.b440; CHECK-SVE-NEXT: punpkhi p3.h, p0.b441; CHECK-SVE-NEXT: punpklo p0.h, p1.b442; CHECK-SVE-NEXT: punpkhi p1.h, p1.b443; CHECK-SVE-NEXT: punpklo p2.h, p3.b444; CHECK-SVE-NEXT: punpkhi p3.h, p3.b445; CHECK-SVE-NEXT: b use446; CHECK-SVE-NEXT: .LBB14_2: // %if.end447; CHECK-SVE-NEXT: ret448;449; CHECK-SVE2p1-SME2-LABEL: test_4x2bit_mask_with_extracts_and_reinterpret_casts:450; CHECK-SVE2p1-SME2: // %bb.0: // %entry451; CHECK-SVE2p1-SME2-NEXT: cntw x8452; CHECK-SVE2p1-SME2-NEXT: adds x8, x0, x8453; CHECK-SVE2p1-SME2-NEXT: csinv x8, x8, xzr, lo454; CHECK-SVE2p1-SME2-NEXT: whilelo { p0.d, p1.d }, x0, x1455; CHECK-SVE2p1-SME2-NEXT: b.pl .LBB14_2456; CHECK-SVE2p1-SME2-NEXT: // %bb.1: // %if.then457; CHECK-SVE2p1-SME2-NEXT: whilelo { p2.d, p3.d }, x8, x1458; CHECK-SVE2p1-SME2-NEXT: b use459; CHECK-SVE2p1-SME2-NEXT: .LBB14_2: // %if.end460; CHECK-SVE2p1-SME2-NEXT: ret461entry:462 %r = call <vscale x 8 x i1> @llvm.get.active.lane.mask.nxv8i1.i32(i64 %i, i64 %n)463 %v0 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 0)464 %v1 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 2)465 %v2 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 4)466 %v3 = call <vscale x 2 x i1> @llvm.vector.extract.nxv2i1.nxv8i1.i64(<vscale x 8 x i1> %r, i64 6)467 %elt0 = extractelement <vscale x 8 x i1> %r, i32 0468 br i1 %elt0, label %if.then, label %if.end469 470if.then:471 tail call void @use(<vscale x 2 x i1> %v0, <vscale x 2 x i1> %v1, <vscale x 2 x i1> %v2, <vscale x 2 x i1> %v3)472 br label %if.end473 474if.end:475 ret void476}477 478declare void @use(...)479 480attributes #0 = { nounwind }481