From: Sander de Smalen Date: Tue, 17 Jul 2018 08:39:48 +0000 (+0000) Subject: [AArch64][SVE] Asm: Support for EXT instruction. X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=46f56568b28273754fd30274dbca7389636f17d4;p=llvm [AArch64][SVE] Asm: Support for EXT instruction. This patch adds an instruction that allows extracting a vector from a pair of vectors, given an immediate index that describes the element position to extract from. The instruction has the following assembly: ext z0.b, z0.b, z1.b, #imm where #imm is an immediate between 0 and 255. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@337251 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/Target/AArch64/AArch64SVEInstrInfo.td b/lib/Target/AArch64/AArch64SVEInstrInfo.td index 831c65e6d59..c3885c6d7e9 100644 --- a/lib/Target/AArch64/AArch64SVEInstrInfo.td +++ b/lib/Target/AArch64/AArch64SVEInstrInfo.td @@ -115,6 +115,7 @@ let Predicates = [HasSVE] in { defm COMPACT_ZPZ : sve_int_perm_compact<"compact">; defm INSR_ZR : sve_int_perm_insrs<"insr">; defm INSR_ZV : sve_int_perm_insrv<"insr">; + def EXT_ZZI : sve_int_perm_extract_i<"ext">; defm SUNPKLO_ZZ : sve_int_perm_unpk<0b00, "sunpklo">; defm SUNPKHI_ZZ : sve_int_perm_unpk<0b01, "sunpkhi">; diff --git a/lib/Target/AArch64/SVEInstrFormats.td b/lib/Target/AArch64/SVEInstrFormats.td index fb5c875ee18..0d5b8b13b8e 100644 --- a/lib/Target/AArch64/SVEInstrFormats.td +++ b/lib/Target/AArch64/SVEInstrFormats.td @@ -728,6 +728,26 @@ multiclass sve_int_perm_insrv { def _D : sve_int_perm_insrv<0b11, asm, ZPR64, FPR64>; } +//===----------------------------------------------------------------------===// +// SVE Permute - Extract Group +//===----------------------------------------------------------------------===// + +class sve_int_perm_extract_i +: I<(outs ZPR8:$Zdn), (ins ZPR8:$_Zdn, ZPR8:$Zm, imm0_255:$imm8), + asm, "\t$Zdn, $_Zdn, $Zm, $imm8", + "", []>, Sched<[]> { + bits<5> Zdn; + bits<5> Zm; + bits<8> imm8; + let Inst{31-21} = 0b00000101001; + let Inst{20-16} = imm8{7-3}; + let Inst{15-13} = 0b000; + let Inst{12-10} = imm8{2-0}; + let Inst{9-5} = Zm; + let Inst{4-0} = Zdn; + + let Constraints = "$Zdn = $_Zdn"; +} //===----------------------------------------------------------------------===// // SVE Vector Select Group diff --git a/test/MC/AArch64/SVE/ext-diagnostics.s b/test/MC/AArch64/SVE/ext-diagnostics.s new file mode 100644 index 00000000000..8f9bee79b85 --- /dev/null +++ b/test/MC/AArch64/SVE/ext-diagnostics.s @@ -0,0 +1,33 @@ +// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sve 2>&1 < %s| FileCheck %s + + +// ------------------------------------------------------------------------- // +// Tied operands must match + +ext z0.b, z1.b, z2.b, #0 +// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: operand must match destination register +// CHECK-NEXT: ext z0.b, z1.b, z2.b, #0 +// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}: + + +// ------------------------------------------------------------------------- // +// Invalid element widths. + +ext z0.h, z0.h, z1.h, #0 +// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid element width +// CHECK-NEXT: ext z0.h, z0.h, z1.h, #0 +// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}: + + +// ------------------------------------------------------------------------- // +// Invalid immediate range. + +ext z0.b, z0.b, z1.b, #-1 +// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: immediate must be an integer in range [0, 255]. +// CHECK-NEXT: ext z0.b, z0.b, z1.b, #-1 +// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}: + +ext z0.b, z0.b, z1.b, #256 +// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: immediate must be an integer in range [0, 255]. +// CHECK-NEXT: ext z0.b, z0.b, z1.b, #256 +// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}: diff --git a/test/MC/AArch64/SVE/ext.s b/test/MC/AArch64/SVE/ext.s new file mode 100644 index 00000000000..2afc5f09771 --- /dev/null +++ b/test/MC/AArch64/SVE/ext.s @@ -0,0 +1,20 @@ +// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sve < %s \ +// RUN: | FileCheck %s --check-prefixes=CHECK-ENCODING,CHECK-INST +// RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \ +// RUN: | FileCheck %s --check-prefix=CHECK-ERROR +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sve < %s \ +// RUN: | llvm-objdump -d -mattr=+sve - | FileCheck %s --check-prefix=CHECK-INST +// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sve < %s \ +// RUN: | llvm-objdump -d - | FileCheck %s --check-prefix=CHECK-UNKNOWN + +ext z31.b, z31.b, z0.b, #0 +// CHECK-INST: ext z31.b, z31.b, z0.b, #0 +// CHECK-ENCODING: [0x1f,0x00,0x20,0x05] +// CHECK-ERROR: instruction requires: sve +// CHECK-UNKNOWN: 1f 00 20 05 + +ext z31.b, z31.b, z0.b, #255 +// CHECK-INST: ext z31.b, z31.b, z0.b, #255 +// CHECK-ENCODING: [0x1f,0x1c,0x3f,0x05] +// CHECK-ERROR: instruction requires: sve +// CHECK-UNKNOWN: 1f 1c 3f 05