我正在执行一组活动以确保Redis在一组嵌入式系统(包括Raspberry PI)中运行良好。为了修复执行未对齐内存访问的Redis的某些代码路径(由于Redis 3.2中引入了更改),我试图强制PI在未对齐的内存访问上记录消息,或者在进程发送信号时有时候是这样的。通过这种方式,我可以确保Redis能够在未对齐的访问违规的情况下运行良好,并且在平台上可以更快地运行,而这种访问可以执行但速度较慢。 ARM V6,在PI V1所使用的一个,显然能够处理未对齐的存储器访问,所以如果使用下面的命令,以便配置Linux到的信号发送到处理执行对齐访问:Raspberry PI版本1未检测到未对齐的访问
echo 4 > /proc/cpu/alignment
然后运行下面的程序:
#include <stdio.h>
#include <stdint.h>
int main(int argc, char **argv) {
char *buf = "foobareklsjdfklsjdfslkjfskdljfskdfjdslkjfdslkjfsd";
uint32_t *l = (uint32_t*) (buf+1);
printf("%p\n", l);
printf("%d\n", (int)*l);
return 0;
}
我看不到由处理接收到的任何信号,或者在/proc/cpu/alignment
递增的计数器。
我的猜测是,这是由于ARM v6能够自动处理未对齐的地址,如果给定的CPU配置标志被设置。我的问题是,我的假设是否正确?如果是这样,如何强制PI版本1在未对齐访问的情况下实际引发异常,以便Linux内核根据/ proc/cpu/alignment可以捕获它并发送信号,记录访问等等。设置?
编辑:值得注意的是,即使在ARM v6中,并非所有的指令都可以执行未对齐的访问。例如STMDB,STMFD,LDMDB,LDMEA和类似的多字指令确实会引发异常,并且会被Linux内核困住。
ARMv4和v5也允许进行未对齐的访问,某些arm core在默认情况下启用其他的不启用,无论是哪种情况,您都可以启用或禁用它。对于未对齐的访问,较旧的内核行为与预期的不同/奇怪,它会旋转单词中的字节,而不是浸入下一个地址。这是非常有意义的,因为你是如何在字节存取(或半字)的零字节通道上获得正确的字节,不止一种方式来表示该猫的皮肤。 –
请注意,如果您只是希望在软件中发现通常存在未对齐的访问,而不是专门针对ARM,则可以让x86陷入Linux下未对齐的访问。 – EOF
EOF是的,我发现,如果你指的是AC寄存器。但是,如果不通过gdb set命令,我没有找到一种可靠的方法在我的程序中实现它。 – antirez