我需要给出 1 字节指令长度到 13 字节指令的汇编命令列表:
- 1 字节:推,...
- 2 字节:添加 al, ...
- 3 字节:添加 ax, ...
- .
- .
- .
- 13 字节...
我在哪里可以找到这样的清单?
我可以看到汇编命令和指令长度(以字节为单位)。
我需要给出 1 字节指令长度到 13 字节指令的汇编命令列表:
我在哪里可以找到这样的清单?
我可以看到汇编命令和指令长度(以字节为单位)。
在 IDK 中,您可以找到按长度排序的列表,因为大多数指令采用 ModRM 字节,该字节可以编码可变长度寻址模式。
您可以按最小长度排序。英特尔的第 2 卷手册显示了编码,例如https://www.felixcloutier.com/x86/index.html处的 HTML 提取。
http://ref.x86asm.net/coder64.html按 1 字节和 2 字节操作码分组,并显示(在o
列中)该操作码是否采用 ModRM 字节来指示操作数。
https://codegolf.stackexchange.com/questions/132981/tips-for-golfing-in-x86-x64-machine-code有一堆关于 x86-64 机器代码中小东西的提示。
顺便说一句,你的一个例子被打破了:
add ax, imm8
在 64 位或 32 位模式下需要 16 位操作数大小的操作数大小前缀。编码至少需要 4 个字节。(66h
+操作码+ modrm + imm8)。
add ax, imm16
可以对隐式 AX 使用 no-modrm 短格式操作码,但需要一个额外的字节用于立即数。
或者你的意思是add r16, r/m16
,像add ax, cx
?是的,这是 3 个字节。但add ax, [1234 + edi + r8d*4]
还有更多:地址大小前缀(因为我没有使用 64 位寄存器)、SIB、disp32 和 r8 的 REX 前缀。因此,您不能将所有 add ax, ...
指令分组为相同的大小。即使排除了内存源操作数,也add ax, r8w
需要一个 REX 前缀。
但是,是的add al, imm8
,或寄存器有 2 字节编码:8 位操作数大小有自己的操作码,而不是 16/32/64 位操作码前面的前缀。
是的push
/ pop
rax..rdi 的注册是一个字节。 r8..r15 需要一个 REX 前缀。
我忘记了没有一堆前缀的最长指令是什么。例如lock add [fs:disp32 + r10], imm32
相当大。
或者一些 SIMD 指令有很多强制前缀,并且可以使用内存源操作数,因此可以有很大的寻址模式。
您可以在此处找到 Intel CPU 的手册:https ://software.intel.com/en-us/articles/intel-sdm
Intel-x86-64b-32b-manul-vol-2-instruction-set-reference-manual.pdf
可以在上面的链接中找到对指令编码的完整参考,您可以在其中下载。
然而,没有简单的指令长度映射,因为指令是经过编码的,它们的长度取决于操作码和涉及的寻址模式以及其他参数。
根据您的用例,您可能会考虑使用类似 capstone: http://www.capstone-engine.org/的东西,您可以使用它来反汇编二进制数据,并为您提供有关指令的信息。