]> granicus.if.org Git - llvm/commitdiff
[AArch64][SVE2] Asm: support SVE2 String Processing Group
authorCullen Rhodes <cullen.rhodes@arm.com>
Fri, 24 May 2019 10:32:01 +0000 (10:32 +0000)
committerCullen Rhodes <cullen.rhodes@arm.com>
Fri, 24 May 2019 10:32:01 +0000 (10:32 +0000)
Summary:
Patch adds support for the SVE2 character match instructions MATCH and NMATCH.

The specification can be found here:
https://developer.arm.com/docs/ddi0602/latest

Reviewed By: SjoerdMeijer

Differential Revision: https://reviews.llvm.org/D62206

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@361627 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Target/AArch64/AArch64SVEInstrInfo.td
lib/Target/AArch64/SVEInstrFormats.td
test/MC/AArch64/SVE2/match-diagnostics.s [new file with mode: 0644]
test/MC/AArch64/SVE2/match.s [new file with mode: 0644]
test/MC/AArch64/SVE2/nmatch-diagnostics.s [new file with mode: 0644]
test/MC/AArch64/SVE2/nmatch.s [new file with mode: 0644]

index 3e17e687bdc0b19ac43e31e27d01737fa462ec72..da26b409a45704500e9d54e2a744aea7c7b7f02d 100644 (file)
@@ -1264,6 +1264,10 @@ let Predicates = [HasSVE2] in {
   defm SQXTUNB_ZZ : sve2_int_sat_extract_narrow<0b100, "sqxtunb">;
   defm SQXTUNT_ZZ : sve2_int_sat_extract_narrow<0b101, "sqxtunt">;
 
+  // SVE2 character match
+  defm MATCH_PPzZZ  : sve2_char_match<0b0, "match">;
+  defm NMATCH_PPzZZ : sve2_char_match<0b1, "nmatch">;
+
   // Predicated shifts
   defm SQSHL_ZPmI  : sve_int_bin_pred_shift_imm_left< 0b0110, "sqshl">;
   defm UQSHL_ZPmI  : sve_int_bin_pred_shift_imm_left< 0b0111, "uqshl">;
index c4c890a63ecd0a0e9a58ddcabc28bd7bd5b31cd2..a05533b18dae10887108017633c6f397db9e3962 100644 (file)
@@ -5132,3 +5132,34 @@ multiclass sve_int_break_z<bits<3> opc, string asm> {
   def NAME : sve_int_break<opc, asm, "/z", (ins PPRAny:$Pg, PPR8:$Pn)>;
 }
 
+//===----------------------------------------------------------------------===//
+// SVE2 String Processing Group
+//===----------------------------------------------------------------------===//
+
+class sve2_char_match<bit sz, bit opc, string asm,
+                      PPRRegOp pprty, ZPRRegOp zprty>
+: I<(outs pprty:$Pd), (ins PPR3bAny:$Pg, zprty:$Zn, zprty:$Zm),
+  asm, "\t$Pd, $Pg/z, $Zn, $Zm",
+  "",
+  []>, Sched<[]> {
+  bits<4> Pd;
+  bits<3> Pg;
+  bits<5> Zm;
+  bits<5> Zn;
+  let Inst{31-23} = 0b010001010;
+  let Inst{22}    = sz;
+  let Inst{21}    = 0b1;
+  let Inst{20-16} = Zm;
+  let Inst{15-13} = 0b100;
+  let Inst{12-10} = Pg;
+  let Inst{9-5}   = Zn;
+  let Inst{4}     = opc;
+  let Inst{3-0}   = Pd;
+
+  let Defs = [NZCV];
+}
+
+multiclass sve2_char_match<bit opc, string asm> {
+  def _B : sve2_char_match<0b0, opc, asm, PPR8, ZPR8>;
+  def _H : sve2_char_match<0b1, opc, asm, PPR16, ZPR16>;
+}
diff --git a/test/MC/AArch64/SVE2/match-diagnostics.s b/test/MC/AArch64/SVE2/match-diagnostics.s
new file mode 100644 (file)
index 0000000..349747f
--- /dev/null
@@ -0,0 +1,61 @@
+// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sve2  2>&1 < %s| FileCheck %s
+
+// --------------------------------------------------------------------------//
+// Restricted predicate out of range.
+
+match p0.b, p8/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: restricted predicate has range [0, 7].
+// CHECK-NEXT: match p0.b, p8/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+
+// --------------------------------------------------------------------------//
+// Invalid predicate operation
+
+match p0.b, p0/m, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid operand for instruction
+// CHECK-NEXT: match p0.b, p0/m, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+
+// --------------------------------------------------------------------------//
+// Invalid destination predicate register
+
+match p0.s, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid predicate register.
+// CHECK-NEXT: match p0.s, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+match p0.d, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid predicate register.
+// CHECK-NEXT: match p0.d, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+// --------------------------------------------------------------------------//
+// Invalid element width
+
+match p0.b, p0/z, z0.s, z0.s
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid element width
+// CHECK-NEXT: match p0.b, p0/z, z0.s, z0.s
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+match p0.b, p0/z, z0.d, z0.d
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid element width
+// CHECK-NEXT: match p0.b, p0/z, z0.d, z0.d
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+
+// --------------------------------------------------------------------------//
+// Negative tests for instructions that are incompatible with movprfx
+
+movprfx z0.b, p0/z, z7.b
+match p0.b, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: instruction is unpredictable when following a movprfx, suggest replacing movprfx with mov
+// CHECK-NEXT: match p0.b, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+movprfx z0, z7
+match p0.b, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: instruction is unpredictable when following a movprfx, suggest replacing movprfx with mov
+// CHECK-NEXT: match p0.b, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
diff --git a/test/MC/AArch64/SVE2/match.s b/test/MC/AArch64/SVE2/match.s
new file mode 100644 (file)
index 0000000..07008f0
--- /dev/null
@@ -0,0 +1,32 @@
+// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sve2 < %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=+sve2 < %s \
+// RUN:        | llvm-objdump -d -mattr=+sve2 - | FileCheck %s --check-prefix=CHECK-INST
+// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sve2 < %s \
+// RUN:        | llvm-objdump -d - | FileCheck %s --check-prefix=CHECK-UNKNOWN
+
+match p0.b, p0/z, z0.b, z0.b
+// CHECK-INST: match p0.b, p0/z, z0.b, z0.b
+// CHECK-ENCODING: [0x00,0x80,0x20,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: 00 80 20 45 <unknown>
+
+match p0.h, p0/z, z0.h, z0.h
+// CHECK-INST: match p0.h, p0/z, z0.h, z0.h
+// CHECK-ENCODING: [0x00,0x80,0x60,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: 00 80 60 45 <unknown>
+
+match p15.b, p7/z, z30.b, z31.b
+// CHECK-INST: match p15.b, p7/z, z30.b, z31.b
+// CHECK-ENCODING: [0xcf,0x9f,0x3f,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: cf 9f 3f 45 <unknown>
+
+match p15.h, p7/z, z30.h, z31.h
+// CHECK-INST: match p15.h, p7/z, z30.h, z31.h
+// CHECK-ENCODING: [0xcf,0x9f,0x7f,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: cf 9f 7f 45 <unknown>
diff --git a/test/MC/AArch64/SVE2/nmatch-diagnostics.s b/test/MC/AArch64/SVE2/nmatch-diagnostics.s
new file mode 100644 (file)
index 0000000..e53b9e6
--- /dev/null
@@ -0,0 +1,61 @@
+// RUN: not llvm-mc -triple=aarch64 -show-encoding -mattr=+sve2  2>&1 < %s| FileCheck %s
+
+// --------------------------------------------------------------------------//
+// Restricted predicate out of range.
+
+nmatch p0.b, p8/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: restricted predicate has range [0, 7].
+// CHECK-NEXT: nmatch p0.b, p8/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+
+// --------------------------------------------------------------------------//
+// Invalid predicate operation
+
+nmatch p0.b, p0/m, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid operand for instruction
+// CHECK-NEXT: nmatch p0.b, p0/m, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+
+// --------------------------------------------------------------------------//
+// Invalid destination predicate register
+
+nmatch p0.s, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid predicate register.
+// CHECK-NEXT: nmatch p0.s, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+nmatch p0.d, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid predicate register.
+// CHECK-NEXT: nmatch p0.d, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+// --------------------------------------------------------------------------//
+// Invalid element width
+
+nmatch p0.b, p0/z, z0.s, z0.s
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid element width
+// CHECK-NEXT: nmatch p0.b, p0/z, z0.s, z0.s
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+nmatch p0.b, p0/z, z0.d, z0.d
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: invalid element width
+// CHECK-NEXT: nmatch p0.b, p0/z, z0.d, z0.d
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+
+// --------------------------------------------------------------------------//
+// Negative tests for instructions that are incompatible with movprfx
+
+movprfx z0.b, p0/z, z7.b
+nmatch p0.b, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: instruction is unpredictable when following a movprfx, suggest replacing movprfx with mov
+// CHECK-NEXT: nmatch p0.b, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
+
+movprfx z0, z7
+nmatch p0.b, p0/z, z0.b, z0.b
+// CHECK: [[@LINE-1]]:{{[0-9]+}}: error: instruction is unpredictable when following a movprfx, suggest replacing movprfx with mov
+// CHECK-NEXT: nmatch p0.b, p0/z, z0.b, z0.b
+// CHECK-NOT: [[@LINE-1]]:{{[0-9]+}}:
diff --git a/test/MC/AArch64/SVE2/nmatch.s b/test/MC/AArch64/SVE2/nmatch.s
new file mode 100644 (file)
index 0000000..6121f55
--- /dev/null
@@ -0,0 +1,32 @@
+// RUN: llvm-mc -triple=aarch64 -show-encoding -mattr=+sve2 < %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=+sve2 < %s \
+// RUN:        | llvm-objdump -d -mattr=+sve2 - | FileCheck %s --check-prefix=CHECK-INST
+// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+sve2 < %s \
+// RUN:        | llvm-objdump -d - | FileCheck %s --check-prefix=CHECK-UNKNOWN
+
+nmatch p0.b, p0/z, z0.b, z0.b
+// CHECK-INST: nmatch p0.b, p0/z, z0.b, z0.b
+// CHECK-ENCODING: [0x10,0x80,0x20,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: 10 80 20 45 <unknown>
+
+nmatch p0.h, p0/z, z0.h, z0.h
+// CHECK-INST: nmatch p0.h, p0/z, z0.h, z0.h
+// CHECK-ENCODING: [0x10,0x80,0x60,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: 10 80 60 45 <unknown>
+
+nmatch p15.b, p7/z, z30.b, z31.b
+// CHECK-INST: nmatch p15.b, p7/z, z30.b, z31.b
+// CHECK-ENCODING: [0xdf,0x9f,0x3f,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: df 9f 3f 45 <unknown>
+
+nmatch p15.h, p7/z, z30.h, z31.h
+// CHECK-INST: nmatch p15.h, p7/z, z30.h, z31.h
+// CHECK-ENCODING: [0xdf,0x9f,0x7f,0x45]
+// CHECK-ERROR: instruction requires: sve2
+// CHECK-UNKNOWN: df 9f 7f 45 <unknown>