我需要复制大量内存(大约47k((例如,从USB缓冲区复制到更永久的缓冲区(。
这是使用ARM Cortex A8。
(ARM有NEON代码。(
ARM NEON指令一次可以复制4个32位元素(每条指令(
ARM LDM和STM指令一次可以加载和存储(复制(4个以上的寄存器(每条指令(。
问题:
-
ARM NEON指令或ARM LDM和STM指令哪一个对复制大量(例如47k(内存更有效?(我没有可用的基准测试工具;这是在嵌入式系统上(。
-
ARM NEON指令用于复制内存的优势是什么?
-
该项目主要是C语言,但也有一些汇编语言。是否有一种方法可以建议编译器在不进行优化的情况下使用ARM NEON或LDM/STM指令?(我们推出的代码没有经过优化,因此产品返回时没有差异。优化可能会导致产品出现问题。(
工具:
ARM Cortex A8处理器
IAR Electronic Workbench IDE&编译器
在Windows 10 PC上进行开发,以实现远程嵌入式ARM处理器(通过JTAG(。
霓虹灯具有负载和存储不对齐的优点,但它消耗更多的功率。
由于你要从USB缓冲区复制到一个可以完全控制对齐和大小的永久缓冲区,所以没有霓虹灯会更好,因为内存速度是一样的。
标准的memcpy
很可能已经使用了neon(这取决于BSP(,因此我会编写一个使用ldrd
和strd
的迷你版本,它比ldm
和stm
稍快。
.balign 64
push {r4-r11}
sub r1, r1, #8
sub r0, r0, #8
b 1f
.balign 64
1:
ldrd r4, r5, [r1, #8]
ldrd r6, r7, [r1, #16]
ldrd r8, r9, [r1, #24]
ldrd r10, r11, [r1, #32]!
subs r2, r2, #32
strd r4, r5, [r0, #8]
strd r6, r7, [r0, #16]
strd r8, r9, [r0, #24]
strd r10, r11, [r0, #32]!
bgt 1b
.balign 16
pop {r4-r11}
bx lr
我认为将缓冲区大小设为32的倍数是没有问题的,并且两个缓冲区都对齐为64字节(缓存行长度(,甚至更好,为4096字节(页面大小(。