- android - RelativeLayout 背景可绘制重叠内容
- android - 如何链接 cpufeatures lib 以获取 native android 库?
- java - OnItemClickListener 不起作用,但 OnLongItemClickListener 在自定义 ListView 中起作用
- java - Android 文件转字符串
这是我遵循的步骤。
1) 我从 Kip Irvine 的《x86 处理器的汇编语言》一书中获取了三个不同小程序的汇编语言代码。
2) 我组装、链接以生成有效的可执行文件,在每种情况下都没有错误。
3) 对于每个可执行文件,我使用 NASM 生成反汇编
ndisasm -u -p intel add3.exe > add3_ndisasm.txt
4) 在每种情况下,我都使用 dumpbin.exe 获得了反汇编输出
dumpbin /disasm add3.exe > add3_dumpbin_disasm.txt
令人惊讶的是,我在第 4 步得到的反汇编与第 3 步完全不同。
这是我使用的汇编代码(在 3 种情况之一中)。
; This program adds and subtracts 32-bit integers.
.386
.model flat,stdcall
.stack 4096
ExitProcess PROTO, dwExitCode:DWORD
DumpRegs PROTO
.code
main PROC
mov eax,10000h ; EAX = 10000h
add eax,40000h ; EAX = 50000h
sub eax,20000h ; EAX = 30000h
call DumpRegs
INVOKE ExitProcess,0
main ENDP
END main
这是第 3 步 (NDISASM) 的反汇编示例
00000000 4D dec ebp
00000001 5A pop edx
00000002 90 nop
00000003 0003 add [ebx],al
00000005 0000 add [eax],al
00000007 000400 add [eax+eax],al
0000000A 0000 add [eax],al
0000000C FF db 0xff
0000000D FF00 inc dword [eax]
这是来自第 4 步 (dumpbin.exe)
Microsoft (R) COFF/PE Dumper Version 14.11.25508.2
Copyright (C) Microsoft Corporation. All rights reserved.
Dump of file add3.exe
File Type: EXECUTABLE IMAGE
00401000: 50 push eax
00401001: E8 EF 0F 00 00 call 00401FF5
00401006: C3 ret
00401007: 55 push ebp
00401008: 8B EC mov ebp,esp
0040100A: 83 C4 E8 add esp,0FFFFFFE8h
0040100D: 60 pushad
0040100E: 80 3D 00 40 40 00 cmp byte ptr ds:[00404000h],0
00
00401015: 75 05 jne 0040101C
我从第 3 步的输出中提取了一些指令代码,并试图在第 4 步的反汇编列表中搜索它们,但找不到它们。
5) 然后我对可执行文件进行了十六进制转储(使用 frhed)并将其中的字节值与两个步骤中的输出进行比较。
0000 4d 5a 90 00 03 00 00 00 04 00 00 00 ff ff 00 00 b8 00 00 00 00 00 00 00 40 00 00 MZ..........ÿÿ..¸.......@..
001b 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ...........................
0036 00 00 00 00 00 00 d8 00 00 00 0e 1f ba 0e 00 b4 09 cd 21 b8 01 4c cd 21 54 68 73 ......Ø.....º..´.Í!¸.LÍ!Ths
0051 69 20 70 72 6f 67 72 61 6d 20 63 61 6e 6e 6f 74 20 62 65 20 72 75 6e 20 69 6e 20 i program cannot be run in
006c 44 4f 53 20 6d 6f 64 65 2e 0d 0d 0a 24 00 00 00 00 00 00 00 5b 39 0b f3 1f 58 65 DOS mode....$.......[9.ó.Xe
我在第 5 步中看到的字节值与第 3 步中的字节值匹配,但与第 4 步中的字节值不匹配。
如何解释这些差异?我一定是在某处遗漏了一些简单的小细节,那是什么?
最佳答案
简答: .exe
≠ .com
提示:注意 MZ
签名作为第 5 步输出中的前两个字节 :-P
长答案:
Microsoft 的可执行.exe
格式不仅仅包含代码。首先,它以一个特殊的签名(格式创建者的首字母缩写)开头,然后是描述代码组织的大量信息。
相比之下,.com
文件只是一个代码,这意味着它的第一个字节是文件加载到内存后执行的内容。
你得到的第一个反汇编是错误的(是的,第一个是错误的,不是第二个!)因为它试图从第一个字节开始解析而不是跳到实际代码。
dumpbin
足够智能,可以正确解析 .exe
文件的 header 并开始实际代码的反汇编。
解决方案
如果您想比较反汇编输出,您要么必须确保您的 NASM 知道文件类型并正确解析其 header ,要么...简化您的生活并转换 .exe
到 .com
中,在这种情况下,两个反汇编操作应该产生相同的输出(当然,除了潜在的错误)
我上次将 .exe
文件转换为 .com
是多年前使用名为 exe2bin
的实用程序。在线快速搜索显示这是在 Windows XP 时代,操作系统不再附带。如果你从某个地方下载它,我认为没有理由不工作。
关于windows - 为什么 NASM 和 dumpbin.exe 对同一个可执行文件的反汇编输出不同?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48473521/
我刚刚在学习 NASM,我有点想弄清楚这个问题。你如何在 NASM 中声明变量?例如,如何在 NASM 中声明 unsigned int i?谢谢 最佳答案 汇编语言中没有 unsigned int
我正在阅读这篇关于操作系统编程的精彩脚本 http://www.cs.bham.ac.uk/~exr/lectures/opsys/10_11/lectures/os-dev.pdf 第 12 页有一
我正在尝试使用 nasm 打印给我的程序的命令行参数: GLOBAL main EXTERN printf section .rodata fmt db "Argument: %s", 10, 0 s
这两种工具都将汇编指令直接翻译成机器代码,但是否有可能确定哪一种产生最快和最干净的代码? 最佳答案 当您使用汇编程序编写时,您准确地描述了生成 的说明所以它不依赖于汇编程序。这取决于你。您编写的助记符
代码: %define x 0x03 x equ 0x03 它们之间有什么区别? 最佳答案 %define是一种更强大的宏处理方式,类似于 C 预处理器。在您的简单情况下,使用 x 没有太大区
关闭。这个问题不符合Stack Overflow guidelines .它目前不接受答案。 关闭 8 年前。 这个问题似乎是题外话,因为它缺乏足够的信息来诊断问题。更详细地描述您的问题或inclu
我目前正在关注 a tutorial on OS development ,其中包括对引导加载程序的讨论。 我的引导加载程序当前处于 16 位实模式,因此,我能够使用提供的 BIOS 中断(例如 VG
len: equ 2 len: db 2 它们是否相同,产生的标签可以代替2使用?如果不是,那么每种声明形式的优点或缺点是什么?它们可以互换使用吗? 最佳答案 第一个是equate,类似于C
我的循环有问题,其中包含的代码很长,它给了我错误“短跳超出范围”,所以我想知道是否有一种方法可以通过不减少来使循环工作其中代码量有多少? 示例1: label: my code LOOP la
在阅读了至少约4本关于汇编编程的不同书籍的前3或4章之后,我进入了一个阶段,可以使用MASM 6.11将“Hello World”放置在dosbox控制台上。想象一下我的喜悦! 我程序的第一个版本使用
我正在做一个项目,将我编写的子程序附加到老师包含的主文件中。他给了我们使我们的子程序成为全局性的说明,但显然我是个白痴。这两个 asm 文件在同一个文件夹中,我正在使用 nasm -f elf -g
我最近开始使用 NASM 程序集编写代码,但我的问题是我不知道如何以正确的方式访问结构元素。我已经在这个网站和谷歌上搜索了解决方案,但我看到到处都有人说不同的话。我的程序崩溃了,我感觉问题出在访问结构
我正在尝试从用户那里获取输入,然后我想根据用户输入的内容输出一些文本。 我的问题是出于某种原因,它总是认为它是 A,我不知道为什么。你可以在下面找到我的代码: bits 16
我熟悉 TASM 但不太熟悉 NASM。我读过 NASM 允许使用本地标签,这些标签在名称前用点表示。例如代码 .loop: ;some code jmp .loop 定义一个局部标号,
您将如何在寄存器上对 NASM 进行位移?我读了手册,似乎只提到了这些运算符 >> , > 和 >仅用于整数常量。这就是“标量值”的含义。您可以使用 shl 移位寄存器中的值或 shr指示。它们用于将
首先,这是一个家庭作业。 我有一个循环来分别获取两位数的值,并通过将第一个数字乘以 10 并与第二个数字相加得到一个整数来加入它们。 我正在做这一切并保存在我的AL注册,现在我想将该整数插入一个数组,
我一直在做基本的 NASM 编码,我想知道是否可以使用 NASM 模拟按键。如果是这样,怎么做? 如果重要的话,我正在使用 Ubuntu linux 10.04 和 Pentium R T4300 处
我可以在 NASM 中创建一个新标签,它指向一个新的内存位置,该位置与另一个标签指向的内存位置偏移几个字节。 例如:如果 label1 指向内存位置 0x40h,有没有办法使用 label1 定义指向
我需要设置一些标签地址/偏移量的最高位。 我试过: 测试.nasm: BITS 32 dw mylabel | 0x8000 mylabel: dd 0 但是当我尝试组装它时,我得到: nasm -f
如果能向我解释以下使用 printf、使用 nasm 和 gcc 编译的示例中发生了什么,我将不胜感激。为什么“sud”只打印在屏幕上?我也不明白,当我将“push 'sud'”与“push 'sud
我是一名优秀的程序员,十分优秀!