ARM NEON汇编程序 - 使用和理解

Hec*_*tor 2 assembly android arm neon armv6

我是汇编程序和NEON编程的新手.我的任务是使用NEON指令将部分算法从C转换为ARM Assembler.该算法采用int32数组,从该数组加载不同的值,执行一些位移和Xor并将结果写入另一个数组.稍后我将使用64位值的数组,但是现在我只是尝试重写代码.

C Pseudo code:

out_array[index] = shiftSome( in_array[index] ) ^ shiftSome( in_array[index] );
Run Code Online (Sandbox Code Playgroud)

以下是关于NEON指令的问题:

1.)如果我加载这样的寄存器:

vld1.32 d0, [r1]
Run Code Online (Sandbox Code Playgroud)

它会从内存加载32Bit还是2x32Bit来填充64Bit Neon D-Register?

2.)如何访问D-Register的2/4/8(i32,i16,i8)部分?

3.)我试图从数组加载不同的值与偏移量,但它似乎不起作用...我做错了什么...这是我的代码:(它是一个整数数组所以我m试图加载例如3元素,它应该具有64Bit = 8 Byte的偏移量

asm volatile(
"vld1.32 d0, [%0], #8 \n"     
"vst1.32 d0, [%1]" : : "r" (a), "r" (out): "d0", "r5");
Run Code Online (Sandbox Code Playgroud)

其中"a"是数组,"out"是指向整数的指针(用于调试).

4.)从数组加载一个值后,我需要将它移到右边,但它似乎不起作用:

vshr.u32 d0, d0, #24     // C code:   x >> 24;
Run Code Online (Sandbox Code Playgroud)

5.)是否可以只在霓虹灯寄存器中加载1个字节,这样我就不必移动/屏蔽某些东西只能得到我需要的一个字节?

6.)我需要使用内联汇编程序,但我不确定最后一行是什么:

input list : output list : what is this for?
Run Code Online (Sandbox Code Playgroud)

7.)你知道任何有关代码示例的NEON参考资料吗?

该程序应该在三星Galaxy S2,cortex-A9处理器上运行,如果这有任何区别.谢谢您的帮助.

- - - - - - - - 编辑 - - - - - - - - - -

这就是我发现的:

  1. 它将始终加载完整的寄存器(64位)
  2. 您可以使用"vmov"指令将部分氖寄存器传输到臂寄存器.
  3. 偏移应位于arm寄存器中,并在存储器访问添加到基址.
  4. 这是"破坏的登记名单".输入或输出列表中使用的每个寄存器都应写在此处.

Bit*_*ank 10

我可以回答你的大多数问题:(更新:澄清"车道"问题)

1)NEON指令一次只能在存储器中加载和存储整个寄存器(64位,128位).MOV指令变体允许将单个"通道"移入或移出ARM寄存器.

2)您可以使用NEON MOV指令影响单个通道.在执行太多单个元素操作时,性能将受到影响.NEON指令通过对向量(浮点数/整数组)执行并行操作来提高应用程序性能.

3)ARM汇编语言中的立即值偏移是字节,而不是元素/寄存器.NEON指令允许使用寄存器进行后递增,而不是立即值.对于普通的ARM指令,后递增8将向源指针添加8(字节).

4)NEON中的移位会影响向量的所有元素.使用vshr.u32的24位右移将使32位无符号长整数移位24位并丢弃移出的位.

5)NEON指令允许将单个元素移入和移出普通ARM寄存器,但不允许从内存中直接加载或存储到"通道"中.

6)?

7)从这里开始:http: //blogs.arm.com/software-enablement/161-coding-for-neon-part-1-load-and-stores/ ARM网站有一个很好的NEON教程.

  • 关于1和5:可以在NEON寄存器中加载和存储单个元素.只需在NEON寄存器后用[]指定元素索引即可.例如,相同的符号可用于将向量与来自另一向量的单个元素相乘. (2认同)
  • 除了后增量以外,这是正确的.您无法使用NEON将立即值添加为后期增量.您可以使用寄存器ARM寄存器来执行此操作或使用!这将增加readed数据的大小. (2认同)