在这种情况下最好的办法就是尝试一下。这是一个示例程序:
int main(int argc, char **argv)
{
int adad=12345;
volatile char character;
character=*((char *)(&adad)+2);
return 0;
}
我添加了volatile
以避免分配行被完全优化掉。现在,这是编译器提出的(-Oz
在我的 Mac 上):
_main:
pushq %rbp
movq %rsp,%rbp
movl $0x00003039,0xf8(%rbp)
movb 0xfa(%rbp),%al
movb %al,0xff(%rbp)
xorl %eax,%eax
leave
ret
我们关心的只有三行是:
movl $0x00003039,0xf8(%rbp)
movb 0xfa(%rbp),%al
movb %al,0xff(%rbp)
是的movl
初始化adad
。然后,如您所见,它读出 的第 3 个字节adad
,并将其存储回内存中(volatile
强制该存储返回)。
我想一个很好的问题是为什么生成什么程序集对你很重要?例如,只需将我的优化标志更改-O0
为 ,代码中有趣部分的汇编输出就是:
movl $0x00003039,0xf8(%rbp)
leaq 0xf8(%rbp),%rax
addq $0x02,%rax
movzbl (%rax),%eax
movb %al,0xff(%rbp)
这很直接地被视为您的代码的确切逻辑操作:
- 初始化
adad
- 取地址
adad
- 将 2 添加到该地址
- 通过取消引用新地址来加载一个字节
- 将一个字节存入
character
各种优化会改变输出......如果您出于某种原因确实需要一些特定的行为/寻址模式,您可能必须自己编写程序集。