能否通过内联汇编将%rsp值存入C变量?代码正确性疑问
问题解答
你的代码确实会尝试把%rsp的值写入extra_args变量,但存在几个关键问题导致你觉得“没指向正确位置”:
变量声明非法:
void extra_args;是无效的C语法,void不能作为普通变量的类型。编译器会对这个错误声明做不确定的处理(比如默认当成int类型),这会导致存储rsp值的内存位置本身就不符合预期,甚至可能引发未定义行为。正确的做法是用void *或者uintptr_t(需包含<stdint.h>)来存储指针值,因为rsp是64位寄存器,变量宽度必须匹配。栈帧的干扰:在
main函数执行这段汇编时,%rsp已经不是程序刚进入main时的原始栈顶了。编译器会为main创建栈帧,可能已经分配了局部变量空间、保存了寄存器,所以你拿到的rsp是main函数栈帧内的栈指针,并非命令行第7个及以后参数所在的位置(x86-64 System V ABI下,这些参数存在调用main之前的栈帧里)。可选优化:约束选择:你用的
"=m"约束是让汇编直接把rsp写入变量内存,这没问题,但用"=r"约束让编译器分配一个寄存器中转,效率会更高,也更符合内联汇编的常规写法。另外,建议加上__volatile__关键字,防止编译器在extra_args未被使用时优化掉这段汇编代码。
修正后的示例代码
#include <stdint.h> #include <stdio.h> int main() { uintptr_t extra_args; // 用寄存器约束更高效,也可以继续用"=m" __asm__ __volatile__("mov %%rsp, %0" : "=r"(extra_args)); printf("当前rsp的值: 0x%lx\n", extra_args); return 0; }
内容的提问来源于stack exchange,提问作者Connor
相关产品推荐
相关产品推荐

