gpt4 book ai didi

assembly - 手工组装 x86 调用指令

转载 作者:行者123 更新时间:2023-12-04 02:24:38 24 4
gpt4 key购买 nike

出于好奇,我决定手工组装一些 x86 代码。到目前为止,我做的一切都很好,但我就是想不出 call 指令的正确编码。

我知道它基本上应该是 E8 xx xx xx xx,其中 xx xx xx xx 是我要跳转到的地址。

我尝试编码的方式是这样的 (NASM):

extern _printf

; ...

db 0xe8
dd _printf

汇编和链接都很好,但是程序崩溃了。

我查看了 NASM 如何汇编指令 call _printf,它生成的 xx xx xx xx 与我的不同。我想知道是我指定的地址不正确还是什么,但是代码

times 512 nop
dd _printf
times 512 nop

在我从手工组装的 call 中得到的相同地址周围产生了无数个 90,这意味着 _printf 的实际地址是这不是我应该传递的内容。

我在这里错过了什么?

(另外:我很好奇 call 的另一种编码,即以 FF 开头的编码。有什么区别?)

最佳答案

0xE8 与相对地址一起使用。所以下面的指令编码为E8 00 00 00 00

  call label
label:

一些以 0xFF 开头的编码可用于间接调用,其中目标地址存储在寄存器或内存中。如果要在特定地址调用过程,可以执行以下操作:

  mov  eax, 0x12345678 ; address of procedure (not relative)
call eax

0x9A 编码允许您进行更新 CS 寄存器的远程调用。例如:

  call 0x1234:0x55667788

将 CS 寄存器的值更新为 0x1234,将指令指针的值更新为 0x55667788。返回地址也与 CS 和指令指针的值一起被压入堆栈。

有关不同编码的更多信息,我推荐 this reference

关于assembly - 手工组装 x86 调用指令,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23491691/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com