You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

x86-64下MOV EAX, moffs32指令反汇编异常原因咨询

问题

在学习x86-64架构时,我发现了MOV EAX, moffs32指令。根据理解,当moffs32为0x12345678时,该指令的编码应为A1 78 56 34 12。但使用objdump和ndisasm以64位模式反汇编时,得到错误的指令解析:

objdump -D -b binary -mi386 -Mx86-64 -Mintel file.bin
00000000 <.data>:
   0:   a1                      .byte 0xa1
   1:   78 56                   js     0x59
   3:   34 12                   xor    al,0x12
ndisasm -b 64 file.bin
00000000  A1                db 0xa1
00000001  7856              js 0x59
00000003  3412              xor al,0x12

只有以32位模式(ndisasm -b 32)反汇编时,才能得到正确结果:

00000000  A178563412        mov eax,[0x12345678]

指令表显示该指令支持64位模式,为何会出现这种情况?我似乎遗漏了某些关键知识点,希望得到解答。

解答

在x86-64长模式下,MOV EAX, moffs系列指令的编码规则和32位模式存在差异,这是反汇编出错的核心原因:

  • 32位模式中,A1 opcode直接对应MOV EAX, moffs32,指令总长度为5字节(opcode + 4字节偏移),因此ndisasm用32位模式能正确识别。
  • 64位模式下,默认地址大小为64位,此时A1 opcode对应的是MOV EAX, moffs64,需要8字节的偏移量。你提供的二进制只有5字节(A1 + 4字节),反汇编器无法识别为完整指令,于是将A1标记为无效字节,后续字节被拆分成独立的短指令(js 0x59和xor al,0x12)。
  • 若要在64位模式下使用32位宽度的moffs偏移,需要添加地址大小前缀67,正确编码应为67 A1 78 56 34 12。此时反汇编器会将其解析为mov eax, dword ptr [0x12345678],地址大小前缀会强制使用32位偏移(并自动零扩展为64位地址)。

指令表标注该指令支持64位模式,指的是存在适配长模式的版本,而非直接兼容32位模式的编码格式。

内容的提问来源于stack exchange,提问作者NyxCode

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.22 20:34:49