[v1,3/6] aarch64: Add support for sme2.1 movaz instructions.

Message ID 20240708153645.1134208-4-srinath.parvathaneni@arm.com
State New
Headers
Series Binutils] aarch64: Add support for sme2p1 instructions. |

Checks

Context Check Description
linaro-tcwg-bot/tcwg_binutils_build--master-arm success Build passed
linaro-tcwg-bot/tcwg_binutils_build--master-aarch64 success Build passed
linaro-tcwg-bot/tcwg_binutils_check--master-aarch64 fail Test failed
linaro-tcwg-bot/tcwg_binutils_check--master-arm success Test passed

Commit Message

Srinath Parvathaneni July 8, 2024, 3:36 p.m. UTC
  This patch adds support for following sme2.1 movaz instructions and
the spec is available here [1].

1. MOVAZ (array to vector, two registers).
2. MOVAZ (array to vector, four registers).
3. MOVAZ (tile to vector, single).

[1]: https://developer.arm.com/documentation/ddi0602/2024-03/SME-Instructions?lang=en
---
 gas/config/tc-aarch64.c                  |  1 +
 gas/testsuite/gas/aarch64/sme2p1-3-bad.d |  4 ++
 gas/testsuite/gas/aarch64/sme2p1-3-bad.l | 30 ++++++++++
 gas/testsuite/gas/aarch64/sme2p1-3-bad.s | 20 +++++++
 gas/testsuite/gas/aarch64/sme2p1-3.d     | 26 ++++++++
 gas/testsuite/gas/aarch64/sme2p1-3.s     | 19 ++++++
 gas/testsuite/gas/aarch64/sme2p1-4-bad.d |  4 ++
 gas/testsuite/gas/aarch64/sme2p1-4-bad.l | 76 ++++++++++++++++++++++++
 gas/testsuite/gas/aarch64/sme2p1-4-bad.s | 48 +++++++++++++++
 gas/testsuite/gas/aarch64/sme2p1-4.d     | 53 +++++++++++++++++
 gas/testsuite/gas/aarch64/sme2p1-4.s     | 48 +++++++++++++++
 include/opcode/aarch64.h                 |  1 +
 opcodes/aarch64-asm.c                    | 43 ++++++++++++++
 opcodes/aarch64-asm.h                    |  1 +
 opcodes/aarch64-dis.c                    | 49 +++++++++++++++
 opcodes/aarch64-dis.h                    |  1 +
 opcodes/aarch64-opc.c                    | 13 +++-
 opcodes/aarch64-opc.h                    |  4 ++
 opcodes/aarch64-tbl.h                    | 19 ++++++
 19 files changed, 459 insertions(+), 1 deletion(-)
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.d
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.l
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.s
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3.d
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3.s
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-4-bad.d
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-4-bad.l
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-4-bad.s
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-4.d
 create mode 100644 gas/testsuite/gas/aarch64/sme2p1-4.s
  

Comments

Jan Beulich July 15, 2024, 6:14 a.m. UTC | #1
On 08.07.2024 17:36, Srinath Parvathaneni wrote:
> 
> This patch adds support for following sme2.1 movaz instructions and
> the spec is available here [1].
> 
> 1. MOVAZ (array to vector, two registers).
> 2. MOVAZ (array to vector, four registers).
> 3. MOVAZ (tile to vector, single).
> 
> [1]: https://developer.arm.com/documentation/ddi0602/2024-03/SME-Instructions?lang=en
> ---
>  gas/config/tc-aarch64.c                  |  1 +
>  gas/testsuite/gas/aarch64/sme2p1-3-bad.d |  4 ++
>  gas/testsuite/gas/aarch64/sme2p1-3-bad.l | 30 ++++++++++
>  gas/testsuite/gas/aarch64/sme2p1-3-bad.s | 20 +++++++
>  gas/testsuite/gas/aarch64/sme2p1-3.d     | 26 ++++++++
>  gas/testsuite/gas/aarch64/sme2p1-3.s     | 19 ++++++
>  gas/testsuite/gas/aarch64/sme2p1-4-bad.d |  4 ++
>  gas/testsuite/gas/aarch64/sme2p1-4-bad.l | 76 ++++++++++++++++++++++++
>  gas/testsuite/gas/aarch64/sme2p1-4-bad.s | 48 +++++++++++++++
>  gas/testsuite/gas/aarch64/sme2p1-4.d     | 53 +++++++++++++++++
>  gas/testsuite/gas/aarch64/sme2p1-4.s     | 48 +++++++++++++++
>  include/opcode/aarch64.h                 |  1 +
>  opcodes/aarch64-asm.c                    | 43 ++++++++++++++
>  opcodes/aarch64-asm.h                    |  1 +
>  opcodes/aarch64-dis.c                    | 49 +++++++++++++++
>  opcodes/aarch64-dis.h                    |  1 +
>  opcodes/aarch64-opc.c                    | 13 +++-
>  opcodes/aarch64-opc.h                    |  4 ++
>  opcodes/aarch64-tbl.h                    | 19 ++++++
>  19 files changed, 459 insertions(+), 1 deletion(-)
>  create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.d
>  create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.l
>  create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.s
>  create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3.d

In here expectations are for the optional ", VGx..." to be present. Elsewhere
in disassembly I think optional parts are omitted, at least by default. Except
that I notice that this same construct looks to uniformly be there when SME2
(or newer) insns have it. Perhaps I'm unaware of an earlier discussion on this
...

Jan
  
Srinath Parvathaneni July 15, 2024, 9:21 a.m. UTC | #2
Hi,

On 7/15/24 07:14, Jan Beulich wrote:
> On 08.07.2024 17:36, Srinath Parvathaneni wrote:
>>
>> This patch adds support for following sme2.1 movaz instructions and
>> the spec is available here [1].
>>
>> 1. MOVAZ (array to vector, two registers).
>> 2. MOVAZ (array to vector, four registers).
>> 3. MOVAZ (tile to vector, single).
>>
>> [1]: https://developer.arm.com/documentation/ddi0602/2024-03/SME-Instructions?lang=en
>> ---
>>   gas/config/tc-aarch64.c                  |  1 +
>>   gas/testsuite/gas/aarch64/sme2p1-3-bad.d |  4 ++
>>   gas/testsuite/gas/aarch64/sme2p1-3-bad.l | 30 ++++++++++
>>   gas/testsuite/gas/aarch64/sme2p1-3-bad.s | 20 +++++++
>>   gas/testsuite/gas/aarch64/sme2p1-3.d     | 26 ++++++++
>>   gas/testsuite/gas/aarch64/sme2p1-3.s     | 19 ++++++
>>   gas/testsuite/gas/aarch64/sme2p1-4-bad.d |  4 ++
>>   gas/testsuite/gas/aarch64/sme2p1-4-bad.l | 76 ++++++++++++++++++++++++
>>   gas/testsuite/gas/aarch64/sme2p1-4-bad.s | 48 +++++++++++++++
>>   gas/testsuite/gas/aarch64/sme2p1-4.d     | 53 +++++++++++++++++
>>   gas/testsuite/gas/aarch64/sme2p1-4.s     | 48 +++++++++++++++
>>   include/opcode/aarch64.h                 |  1 +
>>   opcodes/aarch64-asm.c                    | 43 ++++++++++++++
>>   opcodes/aarch64-asm.h                    |  1 +
>>   opcodes/aarch64-dis.c                    | 49 +++++++++++++++
>>   opcodes/aarch64-dis.h                    |  1 +
>>   opcodes/aarch64-opc.c                    | 13 +++-
>>   opcodes/aarch64-opc.h                    |  4 ++
>>   opcodes/aarch64-tbl.h                    | 19 ++++++
>>   19 files changed, 459 insertions(+), 1 deletion(-)
>>   create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.d
>>   create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.l
>>   create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3-bad.s
>>   create mode 100644 gas/testsuite/gas/aarch64/sme2p1-3.d
> 
> In here expectations are for the optional ", VGx..." to be present. Elsewhere
> in disassembly I think optional parts are omitted, at least by default. Except
> that I notice that this same construct looks to uniformly be there when SME2
> (or newer) insns have it. Perhaps I'm unaware of an earlier discussion on this
> ...
> 
> Jan
The spec states "The vector group symbol is preferred for disassembly, 
but optional in assembler source code.", so we have added the 
disassembly with "VGx...".

But with other optional argument cases, as you mentioned if optional 
argument is present (and set to default) or ignored in the assembly, we 
have dropped the optional argument from the disassembly.

Regards,
Srinath
  

Patch

diff --git a/gas/config/tc-aarch64.c b/gas/config/tc-aarch64.c
index 2cd47f3d099..d4906ef3ddb 100644
--- a/gas/config/tc-aarch64.c
+++ b/gas/config/tc-aarch64.c
@@ -8181,6 +8181,7 @@  parse_operands (char *str, const aarch64_opcode *opcode)
 	case AARCH64_OPND_SME_ZA_array_vrsh_2:
 	case AARCH64_OPND_SME_ZA_array_vrss_2:
 	case AARCH64_OPND_SME_ZA_array_vrsd_2:
+	case AARCH64_OPND_SME_ZA_ARRAY4:
 	  if (!parse_dual_indexed_reg (&str, REG_TYPE_ZATHV,
 				       &info->indexed_za, &qualifier, 0))
 	    goto failure;
diff --git a/gas/testsuite/gas/aarch64/sme2p1-3-bad.d b/gas/testsuite/gas/aarch64/sme2p1-3-bad.d
new file mode 100644
index 00000000000..730d3bff752
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-3-bad.d
@@ -0,0 +1,4 @@ 
+#name: Negative test of SME2.1 movaz array to vector instructions.
+#as: -march=armv9.4-a+sme2p1
+#source: sme2p1-3-bad.s
+#error_output: sme2p1-3-bad.l
diff --git a/gas/testsuite/gas/aarch64/sme2p1-3-bad.l b/gas/testsuite/gas/aarch64/sme2p1-3-bad.l
new file mode 100644
index 00000000000..8b7019f6163
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-3-bad.l
@@ -0,0 +1,30 @@ 
+.*: Assembler messages:
+.*: Error: operand mismatch -- `movaz {z0.s-z1.s},za.d\[w8,0,vgx2\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz {z0.d-z1.d}, za.d\[w8, 0, vgx2\]
+.*: Error: operand mismatch -- `movaz {z30.h-z31.h},za.d\[w8,0,vgx2\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz {z30.d-z31.d}, za.d\[w8, 0, vgx2\]
+.*: Error: operand mismatch -- `movaz {z0.b-z1.b},za.b\[w11,0,vgx2\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz {z0.d-z1.d}, za.d\[w11, 0, vgx2\]
+.*: Error: expected a selection register in the range w8-w11 at operand 2 -- `movaz {z0.d-z1.d},za.d\[w13,7,vgx2\]'
+.*: Error: immediate offset out of range 0 to 7 at operand 2 -- `movaz {z30.d-z31.d},za.d\[w11,15,vgx2\]'
+.*: Error: invalid vector group size at operand 2 -- `movaz {z14.d-z15.d},za.d\[w9,4,vgx3\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz {z6.d-z7.d},za.d\[w10\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz {z2.d-z4.d},za.d\[w10 6\]'
+.*: Error: operand mismatch -- `movaz {z0.s-z3.s},za.d\[w8,0,vgx4\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz {z0.d-z3.d}, za.d\[w8, 0, vgx4\]
+.*: Error: operand mismatch -- `movaz {z28.h-z31.h},za.d\[w8,0,vgx4\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz {z28.d-z31.d}, za.d\[w8, 0, vgx4\]
+.*: Error: operand mismatch -- `movaz {z0.b-z3.b},za.b\[w11,0,vgx4\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz {z0.d-z3.d}, za.d\[w11, 0, vgx4\]
+.*: Error: expected a selection register in the range w8-w11 at operand 2 -- `movaz {z0.d-z3.d},za.d\[w14,7,vgx4\]'
+.*: Error: invalid vector group size at operand 2 -- `movaz {z28.d-z31.d},za.d\[w11,11,vgx3\]'
+.*: Error: start register out of range at operand 1 -- `movaz {z14.d-z17.d},za.d\[w9,4,vgx4\]'
+.*: Error: too many registers in vector register list at operand 1 -- `movaz {z4.d-z8.d},za.d\[w10,3,vgx4\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz {z0.d,z3.d},za.d\[w10\]'
+.*: Error: the register list must have a stride of 1 at operand 1 -- `movaz {z1.d,z4.d},za.d\[w10,20\]'
diff --git a/gas/testsuite/gas/aarch64/sme2p1-3-bad.s b/gas/testsuite/gas/aarch64/sme2p1-3-bad.s
new file mode 100644
index 00000000000..cec5987e535
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-3-bad.s
@@ -0,0 +1,20 @@ 
+/* MOVAZ (array to vector, two registers).  */
+movaz {z0.s - z1.s} , za.d[w8, 0, vgx2]
+movaz {z30.h - z31.h} , za.d[w8, 0, vgx2]
+movaz {z0.b - z1.b} , za.b[w11, 0, vgx2]
+movaz {z0.d - z1.d} , za.d[w13, 7, vgx2]
+movaz {z30.d - z31.d} , za.d[w11, 15, vgx2]
+movaz {z14.d - z15.d} , za.d[w9, 4, vgx3]
+movaz {z6.d - z7.d} , za.d[w10]
+movaz {z2.d - z4.d} , za.d[w10 6]
+
+/* MOVAZ (array to vector, four registers).  */
+movaz {z0.s - z3.s} , za.d[w8, 0, vgx4]
+movaz {z28.h - z31.h} , za.d[w8, 0, vgx4]
+movaz {z0.b - z3.b} , za.b[w11, 0, vgx4]
+movaz {z0.d - z3.d} , za.d[w14, 7, vgx4]
+movaz {z28.d - z31.d} , za.d[w11, 11, vgx3]
+movaz {z14.d - z17.d} , za.d[w9, 4, vgx4]
+movaz {z4.d - z8.d} , za.d[w10, 3, vgx4]
+movaz {z0.d, z3.d} , za.d[w10]
+movaz {z1.d, z4.d} , za.d[w10 , 20]
diff --git a/gas/testsuite/gas/aarch64/sme2p1-3.d b/gas/testsuite/gas/aarch64/sme2p1-3.d
new file mode 100644
index 00000000000..f9f20eb8a04
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-3.d
@@ -0,0 +1,26 @@ 
+#name: Test of SME2.1 movaz array to vector instructions.
+#as: -march=armv9.4-a+sme2p1
+#objdump: -dr
+
+[^:]+:     file format .*
+
+
+[^:]+:
+
+[^:]+:
+.*:	c0060a00 	movaz	{z0.d-z1.d}, za.d\[w8, 0, vgx2\]
+.*:	c0060a1e 	movaz	{z30.d-z31.d}, za.d\[w8, 0, vgx2\]
+.*:	c0066a00 	movaz	{z0.d-z1.d}, za.d\[w11, 0, vgx2\]
+.*:	c0060ae0 	movaz	{z0.d-z1.d}, za.d\[w8, 7, vgx2\]
+.*:	c0066afe 	movaz	{z30.d-z31.d}, za.d\[w11, 7, vgx2\]
+.*:	c0062a8e 	movaz	{z14.d-z15.d}, za.d\[w9, 4, vgx2\]
+.*:	c0064a66 	movaz	{z6.d-z7.d}, za.d\[w10, 3, vgx2\]
+.*:	c0064ac2 	movaz	{z2.d-z3.d}, za.d\[w10, 6, vgx2\]
+.*:	c0060e00 	movaz	{z0.d-z3.d}, za.d\[w8, 0, vgx4\]
+.*:	c0060e1c 	movaz	{z28.d-z31.d}, za.d\[w8, 0, vgx4\]
+.*:	c0066e00 	movaz	{z0.d-z3.d}, za.d\[w11, 0, vgx4\]
+.*:	c0060ee0 	movaz	{z0.d-z3.d}, za.d\[w8, 7, vgx4\]
+.*:	c0066efc 	movaz	{z28.d-z31.d}, za.d\[w11, 7, vgx4\]
+.*:	c0062e8c 	movaz	{z12.d-z15.d}, za.d\[w9, 4, vgx4\]
+.*:	c0064e64 	movaz	{z4.d-z7.d}, za.d\[w10, 3, vgx4\]
+.*:	c0064ec0 	movaz	{z0.d-z3.d}, za.d\[w10, 6, vgx4\]
diff --git a/gas/testsuite/gas/aarch64/sme2p1-3.s b/gas/testsuite/gas/aarch64/sme2p1-3.s
new file mode 100644
index 00000000000..3a822da478d
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-3.s
@@ -0,0 +1,19 @@ 
+/* MOVAZ (array to vector, two registers).  */
+movaz {z0.d - z1.d} , za.d[w8, 0, vgx2]
+movaz {z30.d - z31.d} , za.d[w8, 0, vgx2]
+movaz {z0.d - z1.d} , za.d[w11, 0, vgx2]
+movaz {z0.d - z1.d} , za.d[w8, 7, vgx2]
+movaz {z30.d - z31.d} , za.d[w11, 7, vgx2]
+movaz {z14.d - z15.d} , za.d[w9, 4, vgx2]
+movaz {z6.d - z7.d} , za.d[w10, 3, vgx2]
+movaz {z2.d - z3.d} , za.d[w10, 6]
+
+/* MOVAZ (array to vector, four registers).  */
+movaz {z0.d - z3.d} , za.d[w8, 0, vgx4]
+movaz {z28.d - z31.d} , za.d[w8, 0, vgx4]
+movaz {z0.d - z3.d} , za.d[w11, 0, vgx4]
+movaz {z0.d - z3.d} , za.d[w8, 7, vgx4]
+movaz {z28.d - z31.d} , za.d[w11, 7, vgx4]
+movaz {z12.d - z15.d} , za.d[w9, 4, vgx4]
+movaz {z4.d - z7.d} , za.d[w10, 3, vgx4]
+movaz {z0.d - z3.d} , za.d[w10, 6]
diff --git a/gas/testsuite/gas/aarch64/sme2p1-4-bad.d b/gas/testsuite/gas/aarch64/sme2p1-4-bad.d
new file mode 100644
index 00000000000..4656ad626b2
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-4-bad.d
@@ -0,0 +1,4 @@ 
+#name: Negative test of SME2.1 MOVAZ (tile to vector, single) instructions.
+#as: -march=armv9.4-a+sme2p1
+#source: sme2p1-4-bad.s
+#error_output: sme2p1-4-bad.l
diff --git a/gas/testsuite/gas/aarch64/sme2p1-4-bad.l b/gas/testsuite/gas/aarch64/sme2p1-4-bad.l
new file mode 100644
index 00000000000..fd35f4f2ffe
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-4-bad.l
@@ -0,0 +1,76 @@ 
+.*: Assembler messages:
+.*: Error: operand mismatch -- `movaz z0.b,za0h.s\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.b, za0h.b \[w12, 0\]
+.*: Error: operand mismatch -- `movaz z31.d,za0h.b\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z31.b, za0h.b \[w12, 0\]
+.*: Error: operand mismatch -- `movaz z0.b,za0v.h\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.b, za0v.b \[w12, 0\]
+.*: Error: expected a ZA tile slice at operand 2 -- `movaz z0.q,za0vh.b\[w15,0\]'
+.*: Error: operand mismatch -- `movaz z0.s,za0h.b\[w10,15\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.b, za0h.b \[w10, 15\]
+.*: Error: ZA tile number out of range at operand 2 -- `movaz z31.b,za1v.b\[w25,15\]'
+.*: Error: immediate offset out of range 0 to 15 at operand 2 -- `movaz z15.b,za0h.b\[w13,31\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz z7.h,za0h.b\[w14\]'
+.*: Error: operand mismatch -- `movaz z0.s,za0h.h\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.h, za0h.h \[w12, 0\]
+.*: Error: operand mismatch -- `movaz z31.h,za0h.d\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z31.h, za0h.h \[w12, 0\]
+.*: Error: ZA tile number out of range at operand 2 -- `movaz z0.h,za1h.b\[w12,0\]'
+.*: Error: expected a ZA tile slice at operand 2 -- `movaz z0.q,za0vh.h\[w12,0\]'
+.*: Error: expected a selection register in the range w12-w15 at operand 2 -- `movaz z0.h,za0h.h\[w17,0\]'
+.*: Error: immediate offset out of range 0 to 15 at operand 2 -- `movaz z0.h,za0h.h\[w12,27\]'
+.*: Error: ZA tile number out of range at operand 2 -- `movaz z31.h,za3v.h\[w15,7\]'
+.*: Error: expected a selection register in the range w12-w15 at operand 2 -- `movaz z15.h,za0h.h\[w2,3\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz z7.d,za0h.h\[w14\]'
+.*: Error: operand mismatch -- `movaz z0.b,za0h.s\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.b, za0h.b \[w12, 0\]
+.*: Error: operand mismatch -- `movaz z31.s,za0h.h\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z31.h, za0h.h \[w12, 0\]
+.*: Error: operand mismatch -- `movaz z0.s,za3h\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.s, za3h.s \[w12, 0\]
+.*: Error: expected a selection register in the range w12-w15 at operand 2 -- `movaz z0.s,za0v.s\[w1,0\]'
+.*: Error: operand mismatch -- `movaz z0.q,za0h.s\[w25,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.s, za0h.s \[w25, 0\]
+.*: Error: ZA tile number out of range at operand 2 -- `movaz z31.s,za5v.s\[w15,3\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz z15.s,za1h.s\[w13\]'
+.*: Error: operand mismatch -- `movaz z7.b,za2h.d\[w14,1\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z7.b, za2h.b \[w14, 1\]
+.*: Error: operand mismatch -- `movaz z0.b,za0h.d\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.b, za0h.b \[w12, 0\]
+.*: Error: operand mismatch -- `movaz z31.d,za0h.h\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z31.h, za0h.h \[w12, 0\]
+.*: Error: ZA tile number out of range at operand 2 -- `movaz z0.d,za7h.s\[w12,0\]'
+.*: Error: operand mismatch -- `movaz z0.s,za0v.q\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.s, za0v.s \[w12, 0\]
+.*: Error: expected a ZA tile slice at operand 2 -- `movaz z0.d,za0vh.d\[w15,0\]'
+.*: Error: ZA tile number out of range at operand 2 -- `movaz z31.d,za11v.d\[w1,1\]'
+.*: Error: expected a selection register in the range w12-w15 at operand 2 -- `movaz z15.d,za3h.d\[w23,0\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz z7.s,za4h.q\[w14\]'
+.*: Error: operand mismatch -- `movaz z0.b,za0h.q\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.b, za0h.b \[w12, 0\]
+.*: Error: expected a ZA tile slice at operand 2 -- `movaz z31.q,za0vh.s\[w12,0\]'
+.*: Error: ZA tile number out of range at operand 2 -- `movaz z0.q,za15h.h\[w20,0\]'
+.*: Error: operand mismatch -- `movaz z0.s,za0v.d\[w12,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z0.s, za0v.s \[w12, 0\]
+.*: Error: expected a selection register in the range w12-w15 at operand 2 -- `movaz z0.q,za0h.q\[w1,0\]'
+.*: Error: operand mismatch -- `movaz z31.q,za15v\[w15,0\]'
+.*: Info:    did you mean this\?
+.*: Info:    	movaz z31.q, za15v.q \[w15, 0\]
+.*: Error: expected a ZA tile slice at operand 2 -- `movaz z5.q,za27.q\[w13,0\]'
+.*: Error: missing immediate offset at operand 2 -- `movaz z7.q,za6h\[w14\]'
diff --git a/gas/testsuite/gas/aarch64/sme2p1-4-bad.s b/gas/testsuite/gas/aarch64/sme2p1-4-bad.s
new file mode 100644
index 00000000000..1a13191d5b2
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-4-bad.s
@@ -0,0 +1,48 @@ 
+/* MOVAZ (tile to vector, single).  */
+movaz z0.b, za0h.s[w12, 0]
+movaz z31.d, za0h.b[w12, 0]
+movaz z0.b, za0v.h[w12, 0]
+movaz z0.q, za0vh.b[w15, 0]
+movaz z0.s, za0h.b[w10, 15]
+movaz z31.b, za1v.b[w25, 15]
+movaz z15.b, za0h.b[w13, 31]
+movaz z7.h, za0h.b[w14]
+
+movaz z0.s, za0h.h[w12, 0]
+movaz z31.h, za0h.d[w12, 0]
+movaz z0.h, za1h.b[w12, 0]
+movaz z0.q, za0vh.h[w12, 0]
+movaz z0.h, za0h.h[w17, 0]
+movaz z0.h, za0h.h[w12, 27]
+movaz z31.h, za3v.h[w15, 7]
+movaz z15.h, za0h.h[w2, 3]
+movaz z7.d, za0h.h[w14]
+
+movaz z0.b, za0h.s[w12, 0]
+movaz z31.s, za0h.h[w12, 0]
+movaz z0.s, za3h[w12, 0]
+movaz z0.s, za0v.s[w1, 0]
+movaz z0.q, za0h.s[w25, 0]
+movaz z0.s, za0h.s[w12, 13]
+movaz z31.s, za5v.s[w15, 3]
+movaz z15.s, za1h.s[w13]
+movaz z7.b, za2h.d[w14, 1]
+
+movaz z0.b, za0h.d[w12, 0]
+movaz z31.d, za0h.h[w12, 0]
+movaz z0.d, za7h.s[w12, 0]
+movaz z0.s, za0v.q[w12, 0]
+movaz z0.d, za0vh.d[w15, 0]
+movaz z0.d, za0h.d[w12, 1]
+movaz z31.d, za11v.d[w1, 1]
+movaz z15.d, za3h.d[w23, 0]
+movaz z7.s, za4h.q[w14]
+
+movaz z0.b, za0h.q[w12, 0]
+movaz z31.q, za0vh.s[w12, 0]
+movaz z0.q, za15h.h[w20, 0]
+movaz z0.s, za0v.d[w12, 0]
+movaz z0.q, za0h.q[w1, 0]
+movaz z31.q, za15v[w15, 0]
+movaz z5.q, za27.q[w13, 0]
+movaz z7.q, za6h[w14]
diff --git a/gas/testsuite/gas/aarch64/sme2p1-4.d b/gas/testsuite/gas/aarch64/sme2p1-4.d
new file mode 100644
index 00000000000..add27084245
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-4.d
@@ -0,0 +1,53 @@ 
+#name: Test of SME2.1 MOVAZ (tile to vector, single) instructions.
+#as: -march=armv9.4-a+sme2p1
+#objdump: -dr
+
+[^:]+:     file format .*
+
+
+[^:]+:
+
+[^:]+:
+.*:	c0020200 	movaz	z0.b, za0h.b \[w12, 0\]
+.*:	c002021f 	movaz	z31.b, za0h.b \[w12, 0\]
+.*:	c0028200 	movaz	z0.b, za0v.b \[w12, 0\]
+.*:	c0026200 	movaz	z0.b, za0h.b \[w15, 0\]
+.*:	c00203e0 	movaz	z0.b, za0h.b \[w12, 15\]
+.*:	c002e3ff 	movaz	z31.b, za0v.b \[w15, 15\]
+.*:	c002226f 	movaz	z15.b, za0h.b \[w13, 3\]
+.*:	c0024227 	movaz	z7.b, za0h.b \[w14, 1\]
+.*:	c0420200 	movaz	z0.h, za0h.h \[w12, 0\]
+.*:	c042021f 	movaz	z31.h, za0h.h \[w12, 0\]
+.*:	c0420300 	movaz	z0.h, za1h.h \[w12, 0\]
+.*:	c0428200 	movaz	z0.h, za0v.h \[w12, 0\]
+.*:	c0426200 	movaz	z0.h, za0h.h \[w15, 0\]
+.*:	c04202e0 	movaz	z0.h, za0h.h \[w12, 7\]
+.*:	c042e3ff 	movaz	z31.h, za1v.h \[w15, 7\]
+.*:	c042226f 	movaz	z15.h, za0h.h \[w13, 3\]
+.*:	c0424227 	movaz	z7.h, za0h.h \[w14, 1\]
+.*:	c0820200 	movaz	z0.s, za0h.s \[w12, 0\]
+.*:	c082021f 	movaz	z31.s, za0h.s \[w12, 0\]
+.*:	c0820380 	movaz	z0.s, za3h.s \[w12, 0\]
+.*:	c0828200 	movaz	z0.s, za0v.s \[w12, 0\]
+.*:	c0826200 	movaz	z0.s, za0h.s \[w15, 0\]
+.*:	c0820260 	movaz	z0.s, za0h.s \[w12, 3\]
+.*:	c082e3ff 	movaz	z31.s, za3v.s \[w15, 3\]
+.*:	c08222cf 	movaz	z15.s, za1h.s \[w13, 2\]
+.*:	c0824327 	movaz	z7.s, za2h.s \[w14, 1\]
+.*:	c0c20200 	movaz	z0.d, za0h.d \[w12, 0\]
+.*:	c0c2021f 	movaz	z31.d, za0h.d \[w12, 0\]
+.*:	c0c203c0 	movaz	z0.d, za7h.d \[w12, 0\]
+.*:	c0c28200 	movaz	z0.d, za0v.d \[w12, 0\]
+.*:	c0c26200 	movaz	z0.d, za0h.d \[w15, 0\]
+.*:	c0c20220 	movaz	z0.d, za0h.d \[w12, 1\]
+.*:	c0c2e3ff 	movaz	z31.d, za7v.d \[w15, 1\]
+.*:	c0c222cf 	movaz	z15.d, za3h.d \[w13, 0\]
+.*:	c0c24327 	movaz	z7.d, za4h.d \[w14, 1\]
+.*:	c0c30200 	movaz	z0.q, za0h.q \[w12, 0\]
+.*:	c0c3021f 	movaz	z31.q, za0h.q \[w12, 0\]
+.*:	c0c303e0 	movaz	z0.q, za15h.q \[w12, 0\]
+.*:	c0c38200 	movaz	z0.q, za0v.q \[w12, 0\]
+.*:	c0c36200 	movaz	z0.q, za0h.q \[w15, 0\]
+.*:	c0c3e3ff 	movaz	z31.q, za15v.q \[w15, 0\]
+.*:	c0c322ef 	movaz	z15.q, za7h.q \[w13, 0\]
+.*:	c0c342c7 	movaz	z7.q, za6h.q \[w14, 0\]
diff --git a/gas/testsuite/gas/aarch64/sme2p1-4.s b/gas/testsuite/gas/aarch64/sme2p1-4.s
new file mode 100644
index 00000000000..5c48af46cb7
--- /dev/null
+++ b/gas/testsuite/gas/aarch64/sme2p1-4.s
@@ -0,0 +1,48 @@ 
+/* MOVAZ (tile to vector, single).  */
+movaz z0.b, za0h.b[w12, 0]
+movaz z31.b, za0h.b[w12, 0]
+movaz z0.b, za0v.b[w12, 0]
+movaz z0.b, za0h.b[w15, 0]
+movaz z0.b, za0h.b[w12, 15]
+movaz z31.b, za0v.b[w15, 15]
+movaz z15.b, za0h.b[w13, 3]
+movaz z7.b, za0h.b[w14, 1]
+
+movaz z0.h, za0h.h[w12, 0]
+movaz z31.h, za0h.h[w12, 0]
+movaz z0.h, za1h.h[w12, 0]
+movaz z0.h, za0v.h[w12, 0]
+movaz z0.h, za0h.h[w15, 0]
+movaz z0.h, za0h.h[w12, 7]
+movaz z31.h, za1v.h[w15, 7]
+movaz z15.h, za0h.h[w13, 3]
+movaz z7.h, za0h.h[w14, 1]
+
+movaz z0.s, za0h.s[w12, 0]
+movaz z31.s, za0h.s[w12, 0]
+movaz z0.s, za3h.s[w12, 0]
+movaz z0.s, za0v.s[w12, 0]
+movaz z0.s, za0h.s[w15, 0]
+movaz z0.s, za0h.s[w12, 3]
+movaz z31.s, za3v.s[w15, 3]
+movaz z15.s, za1h.s[w13, 2]
+movaz z7.s, za2h.s[w14, 1]
+
+movaz z0.d, za0h.d[w12, 0]
+movaz z31.d, za0h.d[w12, 0]
+movaz z0.d, za7h.d[w12, 0]
+movaz z0.d, za0v.d[w12, 0]
+movaz z0.d, za0h.d[w15, 0]
+movaz z0.d, za0h.d[w12, 1]
+movaz z31.d, za7v.d[w15, 1]
+movaz z15.d, za3h.d[w13, 0]
+movaz z7.d, za4h.d[w14, 1]
+
+movaz z0.q, za0h.q[w12, 0]
+movaz z31.q, za0h.q[w12, 0]
+movaz z0.q, za15h.q[w12, 0]
+movaz z0.q, za0v.q[w12, 0]
+movaz z0.q, za0h.q[w15, 0]
+movaz z31.q, za15v.q[w15, 0]
+movaz z15.q, za7h.q[w13, 0]
+movaz z7.q, za6h.q[w14, 0]
diff --git a/include/opcode/aarch64.h b/include/opcode/aarch64.h
index 64959a8c50e..5a2b99d2bc5 100644
--- a/include/opcode/aarch64.h
+++ b/include/opcode/aarch64.h
@@ -789,6 +789,7 @@  enum aarch64_opnd
   AARCH64_OPND_SME_ZA_array_vrsh_2, /* Tile to vector, four registers (H).  */
   AARCH64_OPND_SME_ZA_array_vrss_2, /* Tile to vector, four registers (S). */
   AARCH64_OPND_SME_ZA_array_vrsd_2, /* Tile to vector, four registers (D).  */
+  AARCH64_OPND_SME_ZA_ARRAY4, /* Tile to vector, single (BHSDQ).  */
   AARCH64_OPND_SVE_Za_5,	/* SVE vector register in Za, bits [9,5].  */
   AARCH64_OPND_SVE_Za_16,	/* SVE vector register in Za, bits [20,16].  */
   AARCH64_OPND_SVE_Zd,		/* SVE vector register in Zd.  */
diff --git a/opcodes/aarch64-asm.c b/opcodes/aarch64-asm.c
index e621bd86e87..cd79ec19cdc 100644
--- a/opcodes/aarch64-asm.c
+++ b/opcodes/aarch64-asm.c
@@ -1521,6 +1521,49 @@  aarch64_ins_sme_za_vrs2 (const aarch64_operand *self,
   return true;
 }
 
+/* Encode in SME instruction such as MOVZA ZA tile slice to vector.  */
+bool
+aarch64_ins_sme_za_tile_to_vec (const aarch64_operand *self,
+				const aarch64_opnd_info *info,
+				aarch64_insn *code,
+				const aarch64_inst *inst ATTRIBUTE_UNUSED,
+				aarch64_operand_error *errors ATTRIBUTE_UNUSED)
+{
+  int fld_v = info->indexed_za.v;
+  int fld_rv = info->indexed_za.index.regno - 12;
+  int fld_zan_imm = info->indexed_za.index.imm;
+  int regno = info->indexed_za.regno;
+
+  switch (info->qualifier)
+    {
+    case AARCH64_OPND_QLF_S_B:
+      insert_field (FLD_imm4_5, code, fld_zan_imm, 0);
+      break;
+    case AARCH64_OPND_QLF_S_H:
+      insert_field (FLD_ZA8_1, code, regno, 0);
+      insert_field (FLD_imm3_5, code, fld_zan_imm, 0);
+      break;
+    case AARCH64_OPND_QLF_S_S:
+      insert_field (FLD_ZA7_2, code, regno, 0);
+      insert_field (FLD_off2, code, fld_zan_imm, 0);
+      break;
+    case AARCH64_OPND_QLF_S_D:
+      insert_field (FLD_ZA6_3, code, regno, 0);
+      insert_field (FLD_ol, code, fld_zan_imm, 0);
+      break;
+    case AARCH64_OPND_QLF_S_Q:
+      insert_field (FLD_ZA5_4, code, regno, 0);
+      break;
+    default:
+      return false;
+    }
+
+  insert_field (self->fields[0], code, fld_v, 0);
+  insert_field (self->fields[1], code, fld_rv, 0);
+
+  return true;
+}
+
 /* Encode in SME instruction such as MOVA ZA tile vector register number,
    vector indicator, vector selector and immediate.  */
 bool
diff --git a/opcodes/aarch64-asm.h b/opcodes/aarch64-asm.h
index 88143eecfcd..dca0690137c 100644
--- a/opcodes/aarch64-asm.h
+++ b/opcodes/aarch64-asm.h
@@ -104,6 +104,7 @@  AARCH64_DECL_OPD_INSERTER (ins_sve_shlimm);
 AARCH64_DECL_OPD_INSERTER (ins_sve_shrimm);
 AARCH64_DECL_OPD_INSERTER (ins_sme_za_vrs1);
 AARCH64_DECL_OPD_INSERTER (ins_sme_za_vrs2);
+AARCH64_DECL_OPD_INSERTER (ins_sme_za_tile_to_vec);
 AARCH64_DECL_OPD_INSERTER (ins_sme_za_hv_tiles);
 AARCH64_DECL_OPD_INSERTER (ins_sme_za_hv_tiles_range);
 AARCH64_DECL_OPD_INSERTER (ins_sme_za_list);
diff --git a/opcodes/aarch64-dis.c b/opcodes/aarch64-dis.c
index 81ebbe0bd55..6e945705319 100644
--- a/opcodes/aarch64-dis.c
+++ b/opcodes/aarch64-dis.c
@@ -1956,6 +1956,55 @@  aarch64_ext_sve_float_zero_one (const aarch64_operand *self,
   return true;
 }
 
+/* Decode SME instruction such as MOVZA ZA tile slice to vector.  */
+bool
+aarch64_ext_sme_za_tile_to_vec (const aarch64_operand *self,
+				aarch64_opnd_info *info, aarch64_insn code,
+				const aarch64_inst *inst ATTRIBUTE_UNUSED,
+				aarch64_operand_error *errors ATTRIBUTE_UNUSED)
+{
+  aarch64_insn Qsize;		/* fields Q:S:size.  */
+  int fld_v = extract_field (self->fields[0], code, 0);
+  int fld_rv = extract_field (self->fields[1], code, 0);
+  int fld_zan_imm =  extract_field (FLD_imm4_5, code, 0);
+
+  Qsize = extract_fields (inst->value, 0, 2, FLD_SME_size_22, FLD_SME_Q);
+  switch (Qsize)
+    {
+    case 0x0:
+      info->qualifier = AARCH64_OPND_QLF_S_B;
+      info->indexed_za.regno = 0;
+      info->indexed_za.index.imm = fld_zan_imm;
+      break;
+    case 0x2:
+      info->qualifier = AARCH64_OPND_QLF_S_H;
+      info->indexed_za.regno = fld_zan_imm >> 3;
+      info->indexed_za.index.imm = fld_zan_imm & 0x07;
+      break;
+    case 0x4:
+      info->qualifier = AARCH64_OPND_QLF_S_S;
+      info->indexed_za.regno = fld_zan_imm >> 2;
+      info->indexed_za.index.imm = fld_zan_imm & 0x03;
+      break;
+    case 0x6:
+      info->qualifier = AARCH64_OPND_QLF_S_D;
+      info->indexed_za.regno = fld_zan_imm >> 1;
+      info->indexed_za.index.imm = fld_zan_imm & 0x01;
+      break;
+    case 0x7:
+      info->qualifier = AARCH64_OPND_QLF_S_Q;
+      info->indexed_za.regno = fld_zan_imm;
+      break;
+    default:
+      return false;
+    }
+
+  info->indexed_za.index.regno = fld_rv + 12;
+  info->indexed_za.v = fld_v;
+
+  return true;
+}
+
 /* Decode ZA tile vector, vector indicator, vector selector, qualifier and
    immediate on numerous SME instruction fields such as MOVA.  */
 bool
diff --git a/opcodes/aarch64-dis.h b/opcodes/aarch64-dis.h
index a71524f9c64..2ffcef0e652 100644
--- a/opcodes/aarch64-dis.h
+++ b/opcodes/aarch64-dis.h
@@ -128,6 +128,7 @@  AARCH64_DECL_OPD_EXTRACTOR (ext_sve_shlimm);
 AARCH64_DECL_OPD_EXTRACTOR (ext_sve_shrimm);
 AARCH64_DECL_OPD_EXTRACTOR (ext_sme_za_vrs1);
 AARCH64_DECL_OPD_EXTRACTOR (ext_sme_za_vrs2);
+AARCH64_DECL_OPD_EXTRACTOR (ext_sme_za_tile_to_vec);
 AARCH64_DECL_OPD_EXTRACTOR (ext_sme_za_hv_tiles);
 AARCH64_DECL_OPD_EXTRACTOR (ext_sme_za_hv_tiles_range);
 AARCH64_DECL_OPD_EXTRACTOR (ext_sme_za_list);
diff --git a/opcodes/aarch64-opc.c b/opcodes/aarch64-opc.c
index 0e726102693..f65f83a0126 100644
--- a/opcodes/aarch64-opc.c
+++ b/opcodes/aarch64-opc.c
@@ -433,7 +433,11 @@  const aarch64_field fields[] =
     {  6,  1 }, /* ZAn: name of the bit encoded ZA tile.  */
     { 12,  4 },	/* opc2: in rcpc3 ld/st inst deciding the pre/post-index.  */
     { 30,  2 },	/* rcpc3_size: in rcpc3 ld/st, field controls Rt/Rt2 width.  */
-    { 5,  1 },	/* FLD_brbop: used in BRB to mean IALL or INJ.  */
+    {  5,  1 },	/* FLD_brbop: used in BRB to mean IALL or INJ.  */
+    {  8,  1 }, /* ZA8_1: name of the 1 bit encoded ZA tile ZA0-ZA1.  */
+    {  7,  2 }, /* ZA7_2: name of the 2 bits encoded ZA tile ZA0-ZA3.  */
+    {  6,  3 }, /* ZA6_3: name of the 3 bits encoded ZA tile ZA0-ZA7.  */
+    {  5,  4 }, /* ZA5_4: name of the 4 bits encoded ZA tile ZA0-ZA15.  */
 };
 
 enum aarch64_operand_class
@@ -2066,6 +2070,12 @@  operand_general_constraint_met_p (const aarch64_opnd_info *opnds, int idx,
 	    return 0;
 	  break;
 
+	case AARCH64_OPND_SME_ZA_ARRAY4:
+	  if (!check_za_access (opnd, mismatch_detail, idx, 12, 15, 1,
+				get_opcode_dependent_value (opcode)))
+	    return 0;
+	  break;
+
 	case AARCH64_OPND_SME_ZA_array_vrss_2:
 	case AARCH64_OPND_SME_ZA_array_vrsd_2:
 	  if (!check_za_access (opnd, mismatch_detail, idx, 12, 0, 4,
@@ -4408,6 +4418,7 @@  aarch64_print_operand (char *buf, size_t size, bfd_vma pc,
     case AARCH64_OPND_SME_ZA_array_vrsh_2:
     case AARCH64_OPND_SME_ZA_array_vrss_2:
     case AARCH64_OPND_SME_ZA_array_vrsd_2:
+    case AARCH64_OPND_SME_ZA_ARRAY4:
       snprintf (buf, size, "%s [%s, %s%s%s]",
 		style_reg (styler, "za%d%c%s%s",
 			   opnd->indexed_za.regno,
diff --git a/opcodes/aarch64-opc.h b/opcodes/aarch64-opc.h
index 49310960305..b3ef440f98b 100644
--- a/opcodes/aarch64-opc.h
+++ b/opcodes/aarch64-opc.h
@@ -235,6 +235,10 @@  enum aarch64_field_kind
   FLD_opc2,
   FLD_rcpc3_size,
   FLD_brbop,
+  FLD_ZA8_1,
+  FLD_ZA7_2,
+  FLD_ZA6_3,
+  FLD_ZA5_4,
 };
 
 /* Field description.  */
diff --git a/opcodes/aarch64-tbl.h b/opcodes/aarch64-tbl.h
index eccfac53ad1..38be471965c 100644
--- a/opcodes/aarch64-tbl.h
+++ b/opcodes/aarch64-tbl.h
@@ -2269,6 +2269,10 @@ 
   QLF3(S_H,S_S,S_S),                                    \
   QLF3(S_S,S_D,S_D),                                    \
 }
+#define OP_SVE_VV_D					\
+{							\
+  QLF2(S_D, S_D)					\
+}
 #define OP_SVE_VV_BHS_HSD                               \
 {                                                       \
   QLF2(S_B,S_H),                                        \
@@ -6651,6 +6655,19 @@  const struct aarch64_opcode aarch64_opcode_table[] =
   SME2p1_INSN ("luti4", 0xc09a4000, 0xfffe4c08, sme_size_12_bh, 0, OP3 (SME_Ztx2_STRIDED, SME_ZT0, SME_Zn_INDEX2_15), OP_SVE_VUU_BH, 0, 0),
   SME2p1_INSN ("luti4", 0xc09a9000, 0xfffefc0c, sme_misc, 0, OP3 (SME_Ztx4_STRIDED, SME_ZT0, SME_Zn_INDEX1_16), OP_SVE_HUU, 0, 0),
 
+  /* SME2.1 MOVAZ (array to vector, two registers).  */
+  SME2p1_INSN ("movaz", 0xc0060a00, 0xffff9f01, sme2_movaz, 0, OP2 (SME_Zdnx2, SME_ZA_array_off3_5), OP_SVE_VV_D, F_OD (2), 0),
+
+  /* SME2.1 MOVAZ (array to vector, four registers).  */
+  SME2p1_INSN ("movaz", 0xc0060e00, 0xffff9f03, sme2_movaz, 0, OP2 (SME_Zdnx4, SME_ZA_array_off3_5), OP_SVE_VV_D, F_OD (4), 0),
+
+  /* SME2.1 MOVAZ (tile to vector, single).  */
+  SME2p1_INSN ("movaz", 0xc0020200, 0xffff1e00, sme2_movaz, 0, OP2 (SVE_Zd, SME_ZA_ARRAY4), OP_SVE_BB, 0, 0),
+  SME2p1_INSN ("movaz", 0xc0420200, 0xffff1e00, sme2_movaz, 0, OP2 (SVE_Zd, SME_ZA_ARRAY4), OP_SVE_HH, 0, 0),
+  SME2p1_INSN ("movaz", 0xc0820200, 0xffff1e00, sme2_movaz, 0, OP2 (SVE_Zd, SME_ZA_ARRAY4), OP_SVE_SS, 0, 0),
+  SME2p1_INSN ("movaz", 0xc0c20200, 0xffff1e00, sme2_movaz, 0, OP2 (SVE_Zd, SME_ZA_ARRAY4), OP_SVE_DD, 0, 0),
+  SME2p1_INSN ("movaz", 0xc0c30200, 0xffff1e00, sme2_movaz, 0, OP2 (SVE_Zd, SME_ZA_ARRAY4), OP_SVE_QQ, 0, 0),
+
 /* SVE2p1 Instructions.  */
   SVE2p1_INSN("addqv",0x04052000, 0xff3fe000, sve2_urqvs, 0, OP3 (Vd, SVE_Pg3, SVE_Zn), OP_SVE_vUS_BHSD_BHSD, F_OPD_SIZE, 0),
   SVE2p1_INSN("andqv",0x041e2000, 0xff3fe000, sve2_urqvs, 0, OP3 (Vd, SVE_Pg3, SVE_Zn), OP_SVE_vUS_BHSD_BHSD, F_OPD_SIZE, 0),
@@ -7325,6 +7342,8 @@  const struct aarch64_opcode aarch64_opcode_table[] =
       F(FLD_SME_V,FLD_SME_Rv,FLD_off2), "2 bit ZA tile")		\
     Y(ZA_ACCESS, sme_za_vrs2, "SME_ZA_array_vrsd_2", 0,			\
       F(FLD_SME_V,FLD_SME_Rv,FLD_ZAn_3), "3 bit ZA tile")		\
+    Y(ZA_ACCESS, sme_za_tile_to_vec, "SME_ZA_ARRAY4", 0,		\
+      F(FLD_SME_V,FLD_SME_Rv), "ZA tile to vector register")		\
     Y(SVE_REG, regno, "SVE_Za_5", 0, F(FLD_SVE_Za_5),			\
       "an SVE vector register")						\
     Y(SVE_REG, regno, "SVE_Za_16", 0, F(FLD_SVE_Za_16),			\