ARM NEON 到 aarch64

ARM NEON to aarch64

我有 ARM NEON armv7-a 的代码:

vst2.u8   {d1,d3}, [%1]!

我像那样将它移植到 aarch64:

st2 {v1.8b,v3.8b},[%1],#16

出现错误:错误:操作数 1 的寄存器列表无效 -- `st2 {v1.8b,v3.8b},[x1],#16'

根据文档,这是有效的:

ST2 {Vt.<T>, Vt+2.<T>}, vaddr 

我想不通问题。

p.s。如果我把它改成

st2 {v1.8b,v2.8b},[%1],#16

编译器不会因错误消息而中断

我指的是这里的 ARM a64 instruction set architecture,最后更新于 2018 年。

您评论中的第一个 link 仅与 aarch32 指令集有关。第二个 link 是关于 aarch64 指令集的,但它在 pdf 标题中的标题为 iterim 并于 2011 年出版。格式

ST2 { <Vt>.<T>, <Vt+2>.<T> }, vaddr

那里提到了(第 89 页),但这不包括在当前版本中。

ST2

的编码

在当前版本中,ST2被编码为多个数据结构如下(见第1085页):

┌───┬───┬──────────┬───┬───────┬──────┬────┬───────┬───────┐
│ 0 │ Q │ 00110010 │ I │ mmmmm │ 1000 │ ss │ nnnnn │ ttttt │
└───┴───┴──────────┴───┴───────┴──────┴────┴───────┴───────┘
                           Rm          size    Rn      Rt

指令可以使用三种类型的偏移量:

  • 无偏移(Rm == 000000I == 0):

    ST2 { <Vt>.<T>, <Vt2>.<T> }, [<Xn|SP>]
    
  • 立即偏移量(Rm == 111111I == 1):

    ST2 { <Vt>.<T>, <Vt2>.<T> }, [<Xn|SP>], <imm>
    
  • 寄存器偏移量(Rm != 111111I == 1):

    ST2 { <Vt>.<T>, <Vt2>.<T> }, [<Xn|SP>], <Xm>
    

<imm>这里是#16或者#32,相对于Q。这里的编码只保存了第一个寄存器的索引t。第二个寄存器的索引始终计算为 t+1 mod 32.

这就是您收到错误的原因:寄存器必须一个接一个。根本没有足够的 space 来单独编码第二个寄存器。两个变址寄存器已经占了太多space.

考虑

不是可以对第二个寄存器进行编码吗?在 I == 0 的情况下,Rm 设置为 00000,但这只是约定俗成的。该寄存器可用于我们的目的,但仅限于未指定立即数或寄存器偏移量的情况。

我也看到了<Vt+2>的格式没有被草案采用的原因:只能针对这种特殊情况进行编码。实施会使芯片的实施更加复杂,根本不值得。