为什么我们必须在这里取消引用标准输出?
Why do we have to dereference stdout here?
我正在尝试从程序集调用 fputs(str, stdout);
。
为什么我应该 push dword [stdout]
而不是 push stdout
?
既然在 C 中我们不做 fputs(str, *stdout)
,为什么我们需要在汇编中取消引用 stdout
?
完整代码:
extern fputs
extern stdout
section .data
hw: db "Hello World!", 10, 0
section .text
global main
main:
enter 0,0
push dword [stdout]
;push stdout
push hw
call fputs
leave
mov eax, 0
ret
您正在取消引用 asm 标签 stdout
,它相当于 C 中的 &stdout
。它是内存中的静态位置,FILE*
value 已存储。
只有 C 数组类型的行为类似于 asm 标签,其中 C 中的名称是地址,而不是内容。
另见 Why in NASM do we have to use square brackets ([ ]) to MOV to memory location?
在NASM中,裸符号名就是静态地址。在 C 中,裸名是值 .
(真正的 C 数组除外,其中裸名是第一个元素的地址。)
在C中,自动存储的变量class(即局部变量)也可以有名字,而不仅仅是静态的。在 asm 中,符号只能放在静态地址上。 (C 中的自动存储通常是 x86 asm 中的寄存器,或者堆栈 space,如 [ebp - 8]
,如果你需要 spill/reload。堆栈地址不是 link-时间常数,所以不能有标签。你相对于 ESP 或 EBP 寻址堆栈。)
具有动态存储的对象在 C 中不能有名称,只能由命名指针指向。
我正在尝试从程序集调用 fputs(str, stdout);
。
为什么我应该 push dword [stdout]
而不是 push stdout
?
既然在 C 中我们不做 fputs(str, *stdout)
,为什么我们需要在汇编中取消引用 stdout
?
完整代码:
extern fputs
extern stdout
section .data
hw: db "Hello World!", 10, 0
section .text
global main
main:
enter 0,0
push dword [stdout]
;push stdout
push hw
call fputs
leave
mov eax, 0
ret
您正在取消引用 asm 标签 stdout
,它相当于 C 中的 &stdout
。它是内存中的静态位置,FILE*
value 已存储。
只有 C 数组类型的行为类似于 asm 标签,其中 C 中的名称是地址,而不是内容。
另见 Why in NASM do we have to use square brackets ([ ]) to MOV to memory location?
在NASM中,裸符号名就是静态地址。在 C 中,裸名是值 .
(真正的 C 数组除外,其中裸名是第一个元素的地址。)
在C中,自动存储的变量class(即局部变量)也可以有名字,而不仅仅是静态的。在 asm 中,符号只能放在静态地址上。 (C 中的自动存储通常是 x86 asm 中的寄存器,或者堆栈 space,如 [ebp - 8]
,如果你需要 spill/reload。堆栈地址不是 link-时间常数,所以不能有标签。你相对于 ESP 或 EBP 寻址堆栈。)
具有动态存储的对象在 C 中不能有名称,只能由命名指针指向。