278 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 42; RUN: llc -mtriple=aarch64 %s -o - | FileCheck %s --check-prefixes=CHECK,CHECK-SD3; RUN: llc -mtriple=aarch64 -global-isel %s -o - | FileCheck %s --check-prefixes=CHECK,CHECK-GI4 5; ====== Scalar Tests =====6 7; ====== Scalar bswap.i16 Tests =====8define i16 @bswap_i16_to_i16_anyext(i16 %a){9; CHECK-SD-LABEL: bswap_i16_to_i16_anyext:10; CHECK-SD: // %bb.0:11; CHECK-SD-NEXT: rev16 w0, w012; CHECK-SD-NEXT: ret13;14; CHECK-GI-LABEL: bswap_i16_to_i16_anyext:15; CHECK-GI: // %bb.0:16; CHECK-GI-NEXT: rev w8, w017; CHECK-GI-NEXT: lsr w0, w8, #1618; CHECK-GI-NEXT: ret19 %3 = call i16 @llvm.bswap.i16(i16 %a)20 ret i16 %321}22declare i16 @llvm.bswap.i16(i16)23 24; The zext here is optimised to an any_extend during isel.25define i64 @bswap_i16_to_i64_anyext(i16 %a) {26; CHECK-SD-LABEL: bswap_i16_to_i64_anyext:27; CHECK-SD: // %bb.0:28; CHECK-SD-NEXT: // kill: def $w0 killed $w0 def $x029; CHECK-SD-NEXT: rev16 x8, x030; CHECK-SD-NEXT: lsl x0, x8, #4831; CHECK-SD-NEXT: ret32;33; CHECK-GI-LABEL: bswap_i16_to_i64_anyext:34; CHECK-GI: // %bb.0:35; CHECK-GI-NEXT: rev w8, w036; CHECK-GI-NEXT: lsr w8, w8, #1637; CHECK-GI-NEXT: and x8, x8, #0xffff38; CHECK-GI-NEXT: lsl x0, x8, #4839; CHECK-GI-NEXT: ret40 %3 = call i16 @llvm.bswap.i16(i16 %a)41 %4 = zext i16 %3 to i6442 %5 = shl i64 %4, 4843 ret i64 %544}45 46; The zext here is optimised to an any_extend during isel..47define i128 @bswap_i16_to_i128_anyext(i16 %a) {48; CHECK-SD-LABEL: bswap_i16_to_i128_anyext:49; CHECK-SD: // %bb.0:50; CHECK-SD-NEXT: mov w8, w051; CHECK-SD-NEXT: mov x0, xzr52; CHECK-SD-NEXT: rev w8, w853; CHECK-SD-NEXT: lsr w8, w8, #1654; CHECK-SD-NEXT: lsl x1, x8, #4855; CHECK-SD-NEXT: ret56;57; CHECK-GI-LABEL: bswap_i16_to_i128_anyext:58; CHECK-GI: // %bb.0:59; CHECK-GI-NEXT: mov w8, w060; CHECK-GI-NEXT: mov x0, xzr61; CHECK-GI-NEXT: rev w8, w862; CHECK-GI-NEXT: lsr w8, w8, #1663; CHECK-GI-NEXT: and x8, x8, #0xffff64; CHECK-GI-NEXT: lsl x1, x8, #4865; CHECK-GI-NEXT: ret66 %3 = call i16 @llvm.bswap.i16(i16 %a)67 %4 = zext i16 %3 to i12868 %5 = shl i128 %4, 11269 ret i128 %570}71 72define i32 @bswap_i16_to_i32_zext(i16 %a){73; CHECK-LABEL: bswap_i16_to_i32_zext:74; CHECK: // %bb.0:75; CHECK-NEXT: rev w8, w076; CHECK-NEXT: lsr w0, w8, #1677; CHECK-NEXT: ret78 %3 = call i16 @llvm.bswap.i16(i16 %a)79 %4 = zext i16 %3 to i3280 ret i32 %481}82 83; ====== Other scalar bswap tests =====84define i32 @bswap_i32(i32 %a){85; CHECK-LABEL: bswap_i32:86; CHECK: // %bb.0:87; CHECK-NEXT: rev w0, w088; CHECK-NEXT: ret89 %3 = call i32 @llvm.bswap.i32(i32 %a)90 ret i32 %391}92declare i32 @llvm.bswap.i32(i32)93 94define i64 @bswap_i64(i64 %a){95; CHECK-LABEL: bswap_i64:96; CHECK: // %bb.0:97; CHECK-NEXT: rev x0, x098; CHECK-NEXT: ret99 %3 = call i64 @llvm.bswap.i64(i64 %a)100 ret i64 %3101}102declare i64 @llvm.bswap.i64(i64)103 104define i128 @bswap_i128(i128 %a){105; CHECK-LABEL: bswap_i128:106; CHECK: // %bb.0:107; CHECK-NEXT: rev x8, x1108; CHECK-NEXT: rev x1, x0109; CHECK-NEXT: mov x0, x8110; CHECK-NEXT: ret111 %3 = call i128 @llvm.bswap.i128(i128 %a)112 ret i128 %3113}114declare i128 @llvm.bswap.i128(i128)115 116; ===== Legal Vector Type Tests =====117 118define <4 x i16> @bswap_v4i16(<4 x i16> %a){119; CHECK-LABEL: bswap_v4i16:120; CHECK: // %bb.0:121; CHECK-NEXT: rev16 v0.8b, v0.8b122; CHECK-NEXT: ret123 %3 = call <4 x i16> @llvm.bswap.v4i16(<4 x i16> %a)124 ret <4 x i16> %3125}126declare <4 x i16> @llvm.bswap.v4i16(<4 x i16>)127 128define <8 x i16> @bswap_v8i16(<8 x i16> %a){129; CHECK-LABEL: bswap_v8i16:130; CHECK: // %bb.0:131; CHECK-NEXT: rev16 v0.16b, v0.16b132; CHECK-NEXT: ret133 %3 = call <8 x i16> @llvm.bswap.v8i16(<8 x i16> %a)134 ret <8 x i16> %3135}136declare <8 x i16> @llvm.bswap.v8i16(<8 x i16>)137 138define <2 x i32> @bswap_v2i32(<2 x i32> %a){139; CHECK-LABEL: bswap_v2i32:140; CHECK: // %bb.0:141; CHECK-NEXT: rev32 v0.8b, v0.8b142; CHECK-NEXT: ret143 %3 = call <2 x i32> @llvm.bswap.v2i32(<2 x i32> %a)144 ret <2 x i32> %3145}146declare <2 x i32> @llvm.bswap.v2i32(<2 x i32>)147 148define <4 x i32> @bswap_v4i32(<4 x i32> %a){149; CHECK-LABEL: bswap_v4i32:150; CHECK: // %bb.0:151; CHECK-NEXT: rev32 v0.16b, v0.16b152; CHECK-NEXT: ret153 %3 = call <4 x i32> @llvm.bswap.v4i32(<4 x i32> %a)154 ret <4 x i32> %3155}156declare <4 x i32> @llvm.bswap.v4i32(<4 x i32>)157 158define <2 x i64> @bswap_v2i64(<2 x i64> %a){159; CHECK-LABEL: bswap_v2i64:160; CHECK: // %bb.0:161; CHECK-NEXT: rev64 v0.16b, v0.16b162; CHECK-NEXT: ret163 %3 = call <2 x i64> @llvm.bswap.v2i64(<2 x i64> %a)164 ret <2 x i64> %3165}166declare <2 x i64> @llvm.bswap.v2i64(<2 x i64>)167 168; ===== Smaller/Larger Width Vectors with Legal Element Sizes =====169 170define <2 x i16> @bswap_v2i16(<2 x i16> %a){171; CHECK-SD-LABEL: bswap_v2i16:172; CHECK-SD: // %bb.0: // %entry173; CHECK-SD-NEXT: rev32 v0.8b, v0.8b174; CHECK-SD-NEXT: ushr v0.2s, v0.2s, #16175; CHECK-SD-NEXT: ret176;177; CHECK-GI-LABEL: bswap_v2i16:178; CHECK-GI: // %bb.0: // %entry179; CHECK-GI-NEXT: uzp1 v0.4h, v0.4h, v0.4h180; CHECK-GI-NEXT: rev16 v0.8b, v0.8b181; CHECK-GI-NEXT: ushll v0.4s, v0.4h, #0182; CHECK-GI-NEXT: // kill: def $d0 killed $d0 killed $q0183; CHECK-GI-NEXT: ret184entry:185 %res = call <2 x i16> @llvm.bswap.v2i16(<2 x i16> %a)186 ret <2 x i16> %res187}188declare <2 x i16> @llvm.bswap.v2i16(<2 x i16>)189 190define <16 x i16> @bswap_v16i16(<16 x i16> %a){191; CHECK-LABEL: bswap_v16i16:192; CHECK: // %bb.0: // %entry193; CHECK-NEXT: rev16 v0.16b, v0.16b194; CHECK-NEXT: rev16 v1.16b, v1.16b195; CHECK-NEXT: ret196entry:197 %res = call <16 x i16> @llvm.bswap.v16i16(<16 x i16> %a)198 ret <16 x i16> %res199}200declare <16 x i16> @llvm.bswap.v16i16(<16 x i16>)201 202define <1 x i32> @bswap_v1i32(<1 x i32> %a){203; CHECK-SD-LABEL: bswap_v1i32:204; CHECK-SD: // %bb.0: // %entry205; CHECK-SD-NEXT: rev32 v0.8b, v0.8b206; CHECK-SD-NEXT: ret207;208; CHECK-GI-LABEL: bswap_v1i32:209; CHECK-GI: // %bb.0: // %entry210; CHECK-GI-NEXT: fmov w8, s0211; CHECK-GI-NEXT: rev w8, w8212; CHECK-GI-NEXT: fmov s0, w8213; CHECK-GI-NEXT: ret214entry:215 %res = call <1 x i32> @llvm.bswap.v1i32(<1 x i32> %a)216 ret <1 x i32> %res217}218declare <1 x i32> @llvm.bswap.v1i32(<1 x i32>)219 220define <8 x i32> @bswap_v8i32(<8 x i32> %a){221; CHECK-LABEL: bswap_v8i32:222; CHECK: // %bb.0: // %entry223; CHECK-NEXT: rev32 v0.16b, v0.16b224; CHECK-NEXT: rev32 v1.16b, v1.16b225; CHECK-NEXT: ret226entry:227 %res = call <8 x i32> @llvm.bswap.v8i32(<8 x i32> %a)228 ret <8 x i32> %res229}230declare <8 x i32> @llvm.bswap.v8i32(<8 x i32>)231 232define <4 x i64> @bswap_v4i64(<4 x i64> %a){233; CHECK-LABEL: bswap_v4i64:234; CHECK: // %bb.0: // %entry235; CHECK-NEXT: rev64 v0.16b, v0.16b236; CHECK-NEXT: rev64 v1.16b, v1.16b237; CHECK-NEXT: ret238entry:239 %res = call <4 x i64> @llvm.bswap.v4i64(<4 x i64> %a)240 ret <4 x i64> %res241}242declare <4 x i64> @llvm.bswap.v4i64(<4 x i64>)243 244; ===== Vectors with Non-Pow 2 Widths =====245 246define <3 x i16> @bswap_v3i16(<3 x i16> %a){247; CHECK-LABEL: bswap_v3i16:248; CHECK: // %bb.0: // %entry249; CHECK-NEXT: rev16 v0.8b, v0.8b250; CHECK-NEXT: ret251entry:252 %res = call <3 x i16> @llvm.bswap.v3i16(<3 x i16> %a)253 ret <3 x i16> %res254}255declare <3 x i16> @llvm.bswap.v3i16(<3 x i16>)256 257define <7 x i16> @bswap_v7i16(<7 x i16> %a){258; CHECK-LABEL: bswap_v7i16:259; CHECK: // %bb.0: // %entry260; CHECK-NEXT: rev16 v0.16b, v0.16b261; CHECK-NEXT: ret262entry:263 %res = call <7 x i16> @llvm.bswap.v7i16(<7 x i16> %a)264 ret <7 x i16> %res265}266declare <7 x i16> @llvm.bswap.v7i16(<7 x i16>)267 268define <3 x i32> @bswap_v3i32(<3 x i32> %a){269; CHECK-LABEL: bswap_v3i32:270; CHECK: // %bb.0: // %entry271; CHECK-NEXT: rev32 v0.16b, v0.16b272; CHECK-NEXT: ret273entry:274 %res = call <3 x i32> @llvm.bswap.v3i32(<3 x i32> %a)275 ret <3 x i32> %res276}277declare <3 x i32> @llvm.bswap.v3i32(<3 x i32>)278