Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/assembly/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
ARM-为什么gcc为单个字符分配12个字节?_C_Assembly_Stack_Arm - Fatal编程技术网

ARM-为什么gcc为单个字符分配12个字节?

ARM-为什么gcc为单个字符分配12个字节?,c,assembly,stack,arm,C,Assembly,Stack,Arm,我有以下代码: int main() { volatile char a; return 0; } 当我使用arm linux gnueabihf gcc-o align.txt-O0-S align.c对其进行反汇编时,我得到以下结果: push {r7} sub sp, sp, #12 ... 现在,我知道ARM EABI要求堆栈是8字节对齐的,这可以解释gcc分配的空间比a所需的单个字节多。然而,我认为它应该分配4个字节来为a和3个填充字节腾出空间 看起来它分配

我有以下代码:

int main()
{
    volatile char a;

    return 0;
}
当我使用arm linux gnueabihf gcc-o align.txt-O0-S align.c对其进行反汇编时,我得到以下结果:

push    {r7}
sub sp, sp, #12
...
现在,我知道ARM EABI要求堆栈是8字节对齐的,这可以解释gcc分配的空间比
a
所需的单个字节多。然而,我认为它应该分配4个字节来为
a
和3个填充字节腾出空间

看起来它分配了4个字节来对齐推送的r7,然后再分配8个字节(1个用于
a
,7个用于填充)。如果我定义一个9成员的字符数组,它将分配20个字节


为什么推R7需要自己的填充?在C/C++中,

< P>,在32/64位机器上,8位或16位的参数被作为32位参数传递(可能在64位机器上有64位)。然后,被调用函数只使用32位参数中较低的8位或16位。某些(或大多数)32/64位处理器没有或使用推送字节或推送短字符进行堆栈操作。如果使用快速调用API,则前几个参数将使用32位或64位寄存器


示例汇编代码可能将堆栈与16字节边界对齐,也可能对局部变量进行默认分配,或者调试器使用堆栈

愚蠢的问题,暗中捅了一刀:如果你删除了“volatile”,并使用
a
,这样它就不会被编译掉,这是一样的吗?请注意,当你不启用优化时,gcc做了很多非常幼稚的事情。是的,你应该使用
-O3
,然后更改
返回0
返回a这样它就不会被优化了。您将看到分配了8个字节。@MarcusMüller是。我也尝试了Jester的建议,它只是编译成
movsr0,#0
。gcc似乎变得更加智能化了,在上进行了优化。
-Os
会发生什么?