学习大会[关闭]


102

我决定学习汇编语言。这样做的主要原因是能够理解反汇编的代码,也许能够编写更有效的代码部分(例如,通过c ++),执行诸如代码探洞之类的工作,等等。 ,因此,出于上述目的,我应该如何开始?我应该学习哪种组装?我想先做一些简单的程序(例如计算器)来学习,但是目标是自己熟悉它,这样我才能理解显示的代码,例如IDA Pro。

我正在使用Windows(如果有任何区别)。

编辑:所以,似乎每个人都指向MASM。尽管我明白它具有高级功能,但对汇编代码程序员来说都很好,但这不是我想要的。它似乎具有流行的反汇编程序(如IDA)中未显示的if,invoke等指令。因此,如果可能的话,我想听听任何人使用ASM来满足我的要求(在IDA中读取反汇编exe的代码),而不仅仅是“通用”汇编程序员的意见。

编辑:确定。我已经在学习汇编了。我正在学习MASM,而不是使用对我来说无关紧要的高级知识。我现在正在做的是在c ++中的__asm指令上尝试我的代码,因此,与使用MASM从头开始做所有事情相比,我可以更快地进行尝试。



是的,我也正在读那个。我想说的是,我的问题更加“专注”。
吞噬了极乐世界09年

如果在Windows上,目标(即处理器,因此指令集)为x86或x86-64。除非您获得另一台机器或MCU板或使用仿真器。那么,我应该使用哪个汇编程序的问题?还是您真的在问目标是什么架构?我个人很喜欢m68k系列芯片上不错的正交指令集,可惜,alack。
dmckee ---前主持人小猫,

2
“似乎有if,invoke等指令”-这些是宏(“ MASM”中的'M'),即使汇编程序支持它们也不必使用它们。
ChrisW

3
要问这个问题第65次投票是一个艰难的决定,而64位是一个如此漂亮的数字。。。
735Tesla 2014年

Answers:


40

MASM32开始,然后从那里查看FASM。但是您将通过MASM获得乐趣。


我已经收到MASM的来信。如果我没有记错的话,它具有许多“高级”功能,当我查看分散代码时,看不到它们。如果这很有意义,我想必须编写与大多数反汇编程序输出代码完全一样的东西。
吞噬了极乐世界09年

1
基本上,这就像编写操作代码,这没有任何意义。学习MASM32将帮助您了解代码在调试器中的外观。您可能还想看看OllyDbg:ollydbg.de
Noon Silk

7
你不懂汇编。您需要了解它。操作码是数字。调试器将尝试将操作码解析为其指令(有时是困难的)。您需要了解基本说明。学习MASM将帮助您做到这一点。无需多说。
中午,丝绸

5
您不必仅仅因为它们存在就使用了所有MASM功能。如果您认为这样会学到更多,则可以使所需的内容难以阅读。
2009年

3
MASM的怪癖,错误和所谓的高级功能在使汇编程序设计师(无论是初学者还是专家)上所做的工作比我想象的要多得多。
IJ肯尼迪

44

我已经做了很多次,并继续这样做。在这种情况下,您的主要目标是阅读而不是编写汇编程序,我认为这是适用的。

编写自己的反汇编程序。不是为了制造下一个最大的反汇编程序,而是严格地为您准备。目的是学习指令集。是否在新平台上学习汇编程序,是否还记得我曾经知道的平台的汇编程序。从仅几行代码开始,例如添加寄存器,然后在反汇编二进制输出与在输入端添加越来越复杂的指令之间进行乒乓操作:

1)学习特定处理器的指令集

2)了解如何以汇编方式为所述处理器编写代码的细微差别,以便您可以摆动每条指令中的每个操作码位

3)您比大多数使用该指令集谋生的工程师学得更好的指令集

在您的情况下,有两个问题,我通常建议您从ARM指令集开始,今天发货的基于ARM的产品比任何其他产品(包括x86计算机)都多。但是您现在使用ARM并且不了解足够的汇编程序来编写启动代码或其他知道ARM的例程的可能性可能会也可能不会帮助您尝试执行的操作。首先使用ARM的第二个也是更重要的原因是因为指令长度是固定大小且对齐的。诸如x86之类的可变长度指令的拆卸可能是您的第一个项目,这是一场噩梦,这里的目标是学习指令集而不是创建研究项目。第三ARM是一个做得很好的指令集,寄存器的创建是相等的,并且没有单独的特殊差别。

因此,您将必须弄清楚要使用哪种处理器。我建议先使用msp430或ARM,然后再使用ARM,然后再使用x86的混乱。无论使用哪种平台,任何值得使用的平台都具有数据手册或程序员参考手册,这些手册可从供应商获得,其中包括指令集以及操作码的编码(机器语言的位和字节)。为了学习编译器的功能以及如何编写编译器不必为之苦恼的代码,最好了解一些指令集,并了解在每个编译器进行每次优化时,如何在每个指令集上实现相同的高级代码设置。您不想仅仅为了发现代码已使一个编译器/平台变得更好而对其他编译器/平台却变得更差而优化代码。

哦,这是为了分解可变长度的指令集,而不是像在ARM中那样从头开始简单地通过内存线性地分解每个四个字节的单词,或者像msp430那样每两个字节线性地分解(msp430具有可变长度的指令,但是您仍然可以通过如果从中断向量表的入口点开始,则线性地通过内存)。对于可变长度,您想基于向量表或有关处理器如何启动并按执行顺序遵循代码的知识来找到入口点。您必须完全解码每条指令才能知道使用了多少字节,然后,如果该指令不是无条件分支,则假定该指令之后的下一个字节是另一条指令。您还必须存储所有可能的分支地址,并假设这些是更多指令的起始字节地址。有一次我成功通过二进制文件进行了多次传递。从入口点开始,我将该字节标记为一条指令的开始,然后通过内存进行线性解码,直到遇到无条件分支为止。所有分支目标都标记为指令的起始地址。我多次遍历二进制文件,直到没有找到新的分支目标为止。如果您在任何时候发现说一个3字节的指令,但由于某种原因将第二个字节标记为指令的开头,则您遇到了问题。如果代码是由高级编译器生成的,那么除非编译器做恶事,否则不应该发生这种情况,如果代码具有手写汇编程序(例如旧的街机游戏),则很有可能存在永远不会发生的条件分支,如r0 = 0,然后是跳转(如果不为零)。您可能需要手动编辑二进制以外的内容才能继续。对于我认为将在x86上执行的近期目标,我认为您不会遇到问题。

我建议使用gcc工具,如果以x86为目标,则mingw32是在Windows上使用gcc工具的简便方法。如果不是mingw32 plus,那么msys是一个优秀的平台,可以从binutils和gcc源生成交叉编译器(通常非常简单)。mingw32与cygwin相比有一些优势,例如程序速度明显提高,并且可以避免cygwin dll地狱。gcc和binutils将允许您使用C或汇编语言进行编写和反汇编代码,并且网页数量比您所读的更多,向您展示了如何进行这三种方法中的任何一种或全部。如果要使用可变长度的指令集进行此操作,我强烈建议您使用包含反汇编程序的工具集。例如,使用x86的第三方反汇编程序将是一个挑战,因为您永远不知道它是否正确反汇编。其中一些也依赖于操作系统,目标是将模块编译为二进制格式,其中包含来自数据的信息标记指令,以便反汇编程序可以执行更准确的工作。对于这个主要目标,您的另一个选择是拥有一个可以直接编译为汇编程序以供您检查的工具,然后希望当它编译为二进制格式时会创建相同的指令。

简短的回答(可以稍微短一点)。编写反汇编器以学习指令集。我将从像ARM这样具有风险且易于学习的内容开始。一旦知道了一个指令集,通常在几个小时内,其他指令就变得容易得多,通过第三个指令集,您几乎可以立即使用数据手册/参考手册中的语法开始编写代码。所有值得使用的处理器都有一个数据表或参考手册,其中描述了指令的内容,包括操作码的位和字节。学习足够的ARM之类的RISC处理器和x86之类的CISC,足以了解它们之间的差异,诸如必须对所有内容进行寄存器检查或能够使用更少或没有寄存器直接在内存上执行操作。三个操作数指令对两个指令,等等。在调整高级代码时,编译多个处理器并比较输出。您将学到的最重要的事情是,无论编写的高级代码的质量如何,编译器的质量和做出的优化选择都将在实际指令中产生巨大的差异。我建议llvm和gcc(与binutils),都不产生好的代码,但是它们是多平台和多目标的,并且都具有优化器。两者都是免费的,您可以轻松地从源代码为各种目标处理器构建交叉编译器。


谢谢回复。但是我什至不知道如何编写反汇编程序。
吞噬了极乐世界09年

8
“编写自己的反汇编程序”-我同意,这是我学到的最好的方法。(“我什至不知道如何编写反汇编程序”这是怎么回事?)大声笑。
slashmais

我和你一起去!刚买了MSP430和一本书……:)
Pepe

1
我有一些MSP430例子github.com/dwelch67加上几个指令集仿真器与包括学习ASM等实验
old_timer

我真的非常喜欢这个想法。
米莉·史密斯

33

从较高的角度来看,您将要手工编写的程序集和由编译器生成的程序集通常会有很大的不同。当然,该程序的内在方式将非常相似(a = b + c毕竟,编码的方式只有很多种不同),但是当您尝试进行逆向工程时,它们并不是麻烦。编译器甚至会为简单的可执行文件添加大量样板代码:我上次比较时,GCC编译的“ Hello World”约为4kB,而如果用手工编写的话,则约为100字节。在Windows上更糟:我上次比较(不可否认,这是上个世纪)当时我可以选择的Windows编译器最小的“ Hello World”是52kB!通常,此样板仅执行一次(如果有的话),因此它不会对程序速度产生太大的影响-就像我上面说的那样,程序的核心是花费大部分执行时间的部分,无论是编译还是编译,通常都非常相似亲手写的。

归根结底,这意味着专家汇编程序员和专家汇编程序是两个不同的专业。通常,它们是在同一个人中找到的,但它们实际上是分开的,而学习如何成为一名出色的汇编编码者对学习逆向工程不会有太大帮助。

您要做的是从IntelAMD那里获取IA-32和AMD64体系结构手册,并仔细阅读有关指令和操作码的早期内容。也许读了一两个关于汇编语言的教程,只是为了了解汇编语言的基础知识。然后抓一您感兴趣的示例程序并对其进行反汇编:逐步执行其控制流程,并尝试了解其功能。看看是否可以打补丁以做其他事情。然后再尝试另一个程序,并重复进行直到您足够舒适以尝试实现更有用的目标为止。您可能对逆向工程社区产生的“裂缝”之类的东西感兴趣,这对那些对逆向工程感兴趣的人尝试一下并希望从中学到的东西构成了挑战。它们的难度范围从基本(从这里开始!)到不可能。

最重要的是,您只需要练习。与许多其他学科一样,通过逆向工程,实践可以达到完美……或至少更好


我知道,当您使用高级语言编译任何东西时,您会得到很多不需要的“垃圾”代码,因为它们是直接在汇编中进行编码的。我也确实知道,专家汇编程序员和专家反汇编程序之间是有区别的。但是几乎所有其他内容都可以这样说。
吞噬了极乐世界09年

3
我的担心是,虽然理论上我可以阅读论文并理解它们的含义,但是直到我自己开始写东西之前,我都不相信我会真正理解它。您说我可以从更改代码的一小部分开始,但是要做到这一点,我首先必须知道例如IDA pro使用哪种汇编“风味” IDA pro。
吞噬了极乐世界09年

另外,MSVC ++对内联汇编代码使用什么?MASM?
吞噬了极乐世界09年

15

我将与大多数答案背道而驰,并推荐Knuth的MIPS RISC体系结构的MMIX变体。它实际上不会像x86或ARM汇编语言那样有用(不是说它们在当今大多数现实工作中都起着至关重要的作用……;-),但是它将为您释放Knuth最新技术的魔力。是对算法和数据结构的深入了解的最伟大杰作的版本-TAOCP,“计算机编程的艺术”。我引用的两个URL中的链接是开始探索这种可能性的好方法!


12

(我不认识你,但我对集会感到兴奋)

您的PC中已经安装了一个用于测试装配的简单工具。

转到“开始”菜单->“运行”,然后键入debug

调试(命令)

debug是在DOS,MS-DOS,OS / 2和Microsoft Windows(仅x86版本,而不是x64)中运行的命令debug.exe(或DOS早期版本中的DEBUG.COM)中的命令。Debug可以充当汇编程序,反汇编程序或十六进制转储程序,允许用户以交互方式检查内存内容(以汇编语言,十六进制或ASCII),进行更改并有选择地执行COM,EXE和其他文件类型。它还具有几个子命令,这些子命令用于访问特定的磁盘扇区,I / O端口和内存地址。MS-DOS Debug在 16位进程级别运行,因此仅限于16位计算机程序。FreeDOS Debug有一个“ DEBUGX”版本,它也支持32位DPMI程序。

教程:


如果您想了解在IDA Pro(或OllyDbg)中看到的代码,则需要学习编译后的代码的结构。我推荐这本书《逆向:逆向工程的秘密》

debug当我开始学习汇编语言时(15年前),我做了几个星期的实验。
请注意,它debug在基本计算机级别上起作用,没有高级汇编命令。

现在

举一个简单的例子:给出a开始编写汇编代码的方法-输入以下程序-最后给出g运行程序的代码。

替代文字


(如果寄存器设置为- 终止程序,则INT 21在屏幕上显示存储在DL寄存器中的ASCII字符)AH2INT 20


在输入“ g”之前,我必须先按ctrl-c。
ericp

2
@ericp,您不必点击ctrl-c。例如,您键入a&[输入]开始编写汇编代码。如果您按两次[enter],则退出汇编模式。g&[输入]以运行它(默认偏移100)。
Nick Dandoulakis 09年

它实际上会导致堆栈溢出还是只是将其写入屏幕?
Janus Troelsen,

1
@user,它只是写了这个站点的名称:-)
Nick Dandoulakis

@JanusTroelsen这些数字(53、74、61等)是'S''t''a'的ASCII码...每个Int21调用一次都打印一个字符!这就是为什么汇编的速度
不快的

8

我发现了骇客:剥削的艺术是进入该主题的一种有趣且有用的方式……不能说我曾经直接使用该知识,但这并不是我读它的真正原因。它使您对代码所编译的指令有了更丰富的了解,这有时对理解更小的错误很有用。

不要被标题拖延。本书的第一部分大部分是埃里克·雷蒙德(Eric Raymond)所说的“黑客”:创造性,令人惊讶,几乎是偷偷摸摸的解决难题的方法。我(也许您)对安全方面的兴趣不大。


7

我不会专注于尝试用汇编语言编写程序,至少起初不会。如果您使用的是x86(我假设您正在使用Windows,因为您使用的是Windows),那么会有很多奇怪的特殊情况需要学习。例如,许多指令都假定您正在对未明确命名的寄存器进行操作,而其他指令则对某些寄存器有效,而对其他寄存器无效。

我会充分了解您打算了解的基础架构,从而了解基础知识,然后直接进入并尝试了解编译器的输出。使用Intel手册武装自己,然后直接深入研究编译器的输出。将感兴趣的代码隔离到一个小函数中,因此您可以确保理解整个过程。

我认为基础是:

  • 寄存器:有多少个,它们的名字是什么,大小是多少?
  • 操作数顺序:add eax, ebx表示“将ebx添加到eax并将结果存储在eax中”。
  • FPU:了解浮点堆栈的基础知识以及如何与fp进行转换。
  • 寻址模式:[基数+偏移量*乘数],但乘数只能是1、2或4(或8)?
  • 调用约定:参数如何传递给函数?

很多时候,编译器发出的内容会令人惊讶。弄清楚为什么编译器会认为这是个好主意,这令人困惑。它会教给你很多东西。

使用Agner Fog的手册,尤其是列出其中的说明,可能也有助于武装自己。它将大致告诉您每条指令的价格,尽管很难在现代处理器上直接进行量化。但这将有助于解释为什么编译器会过分地避免发出idiv指令。

我唯一的其他建议是,在选择时始终使用Intel语法而不是AT&T。在这一点上,我以前常常保持中立,直到那天我意识到某些指令在两者之间是完全不同的(例如,movslqAT&T语法是movsxdIntel语法)。由于手册都是使用Intel语法编写的,因此请坚持使用。

祝好运!


3

我开始学习MIPS,它是一种非常紧凑的32位体系结构。它是一套简化的指令集,但这对于初学者来说很容易掌握。您仍然可以了解组装的工作原理,而不会为复杂性所困扰。您甚至可以下载一个不错的小IDE,它将允许您编译MIPS代码:clicky 一旦掌握了它,我想转向更复杂的体系结构会容易得多。至少这就是我的想法:)在这一点上,您将具有内存分配和管理,逻辑流,调试,测试等基本知识。


3

使用调试的建议是一个有趣的建议,可以使用许多巧妙的技巧。但是,对于现代操作系统,学习16位汇编可能没那么有用。可以考虑使用ntsd.exe。它内置于Windows XP中(不幸的是,它已在Server 2003及更高版本中取消了),由于它广泛可用,因此使其成为学习的便捷工具。

也就是说,XP的原始版本存在许多错误。如果您确实要使用它(或cdb或windbg,它们本质上是具有相同命令语法和调试后端的不同接口),则应安装免费的Windows调试工具包。

当试图找出异常语法时,该软件包中包含的debugger.chm文件特别有用。

ntsd的伟大之处在于,您可以在附近的任何XP机器上弹出它,然后使用它进行组装或拆卸。它制作了/ great / X86汇编学习工具。例如(由于使用cdb,因为它在dos提示符下是内联的,因此在其他方面是相同的):

(由于它们不相关,因此跳过了符号错误-另外,我希望这种格式有效,这是我的第一篇文章)

C:\Documents and Settings\User>cdb calc

Microsoft (R) Windows Debugger Version 6.10.0003.233 X86
Copyright (c) Microsoft Corporation. All rights reserved.

CommandLine: calc
Symbol search path is: *** Invalid ***
Executable search path is:
ModLoad: 01000000 0101f000   calc.exe
ModLoad: 7c900000 7c9b2000   ntdll.dll
ModLoad: 7c800000 7c8f6000   C:\WINDOWS\system32\kernel32.dll
ModLoad: 7c9c0000 7d1d7000   C:\WINDOWS\system32\SHELL32.dll
ModLoad: 77dd0000 77e6b000   C:\WINDOWS\system32\ADVAPI32.dll
ModLoad: 77e70000 77f02000   C:\WINDOWS\system32\RPCRT4.dll
ModLoad: 77fe0000 77ff1000   C:\WINDOWS\system32\Secur32.dll
ModLoad: 77f10000 77f59000   C:\WINDOWS\system32\GDI32.dll
ModLoad: 7e410000 7e4a1000   C:\WINDOWS\system32\USER32.dll
ModLoad: 77c10000 77c68000   C:\WINDOWS\system32\msvcrt.dll
ModLoad: 77f60000 77fd6000   C:\WINDOWS\system32\SHLWAPI.dll
(f2c.208): Break instruction exception - code 80000003 (first chance)
eax=001a1eb4 ebx=7ffd6000 ecx=00000007 edx=00000080 esi=001a1f48 edi=001a1eb4
eip=7c90120e esp=0007fb20 ebp=0007fc94 iopl=0         nv up ei pl nz na po nc
cs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202
ntdll!DbgBreakPoint:
7c90120e cc              int     3
0:000> r eax
eax=001a1eb4
0:000> r eax=0
0:000> a eip
7c90120e add eax,0x100
7c901213
0:000> u eip
ntdll!DbgBreakPoint:
7c90120e 0500010000      add     eax,100h
7c901213 c3              ret
7c901214 8bff            mov     edi,edi
7c901216 8b442404        mov     eax,dword ptr [esp+4]
7c90121a cc              int     3
7c90121b c20400          ret     4
ntdll!NtCurrentTeb:
7c90121e 64a118000000    mov     eax,dword ptr fs:[00000018h]
7c901224 c3              ret
0:000> t
eax=00000100 ebx=7ffd6000 ecx=00000007 edx=00000080 esi=001a1f48 edi=001a1eb4
eip=7c901213 esp=0007fb20 ebp=0007fc94 iopl=0         nv up ei pl nz na pe nc
cs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000206
ntdll!DbgUserBreakPoint+0x1:
7c901213 c3              ret
0:000>`

另外,在使用IDA时,请务必查看Chris Eagle撰写的IDA Pro书籍(取消链接,因为StackOverflow不想让我在第一篇文章中发布两个以上的链接)。它是最好的参考资料。


1
克里斯·伊格(Chris Eagle)的书+1。一定会对r00t的Sk3wl充满爱意;)
mrduclaw

3

我最近参加了计算机系统课程。主题之一是作为与硬件通信的工具的组装。

对我来说,如果不了解计算机系统工作原理的细节,组装知识就不会完整。理解这一点,将使人们对为什么在一种处理器体系结构上的汇编指令好而在另一种体系结构上却糟的原因有了新的认识。

鉴于此,我倾向于推荐我的课堂教科书:

计算机系统:程序员的观点

计算机系统:程序员的观点
(来源:cmu.edu

它的确涵盖了x86汇编,但是这本书的内容要广泛得多。它涵盖了处理器管线和作为缓存的内存,虚拟内存系统等等。所有这些都会影响如何针对给定功能优化装配。


2

我认为您想学习ASCII化的操作码助记符(及其参数),这些助记符由反汇编程序输出,并且可以被汇编程序理解(可用作输入)。

任何汇编程序(例如MASM)都可以。

和/或对您而言,读一本关于它的书可能更好(有一些关于SO的书,我不记得是哪本书)。


2

您是否正在Windows上进行其他开发工作?在哪个IDE上?如果是VS,则无需额外的IDE即可读取反汇编的代码:调试应用程序(或附加到外部应用程序),然后打开反汇编窗口(默认设置为Alt + 8)。像通过普通代码那样逐步查看内存/寄存器。您可能还希望保持寄存器窗口保持打开状态(默认情况下为Alt + 5)。

英特尔提供免费手册,其中提供了基本体系结构(寄存器,处理器单元等)的调查以及完整的指令参考。随着体系结构的成熟和日益复杂,“基本体系结构”手册的可读性越来越低。如果您可以使用较旧的版本,则可能会有更好的起点(即使是P3手册,它们也能更好地解释相同的内容)。基本执行环境)。

如果您想购买一本书,是一个不错的介绍性文字。在亚马逊上搜索“ x86”,您还会得到许多其他信息。您可以从这里的其他问题中获得其他几个指导

最后,你可以从中受益不少阅读 一些 - 的博客。就我个人而言,这些字节大小的信息位最适合我。


2

这不一定会帮助您编写高效的代码!

i86操作码或多或少是一种“传统”格式,这种格式会持续存在,因为那里存在大量的Windows和Linux代码和可执行二进制文件。

这有点像拉丁美洲的老学者写作,像伽利略这样的意大利人会用拉丁语写作,而波兰人像哥白尼会理解他的论文。即使niether特别擅长拉丁语,这仍然是最有效的交流方式,而拉丁语是表达数学思想的一种垃圾语言。

因此,编译器默认情况下会生成x86代码,并且现代芯片会读取anceint Op代码并将其所看到的内容转换为并行的risc指令,并具有重新排序的执行,推测性的执行,流水线操作等,并且它们会充分利用处理器的32或64个寄存器实际上具有(与您在x86指令中看到的可悲的8相反。)

现在,所有优化的编译器都知道这确实发生了,因此他们编码了他们知道芯片可以有效优化的OP代码序列,即使其中一些序列对大约1990年的.asm程序员而言效率不高。

在某些时候,您需要接受编译器编写者投入的数万个人年的努力已经获得回报,并相信他们。

获得更高效的运行时的最简单,最简单的方法是购买英特尔C / C ++编译器。它们在efficeint编译器市场上占有一席之地,而且它们具有能够向芯片设计人员询问内部情况的优势。


您的故事有点暗示CISC处理器在内部已成为RISC处理器。我可能误会了,但这不是真的。和可悲的8?现代处理器(例如,自1999年以来)包括:10 gpr:EAX-EFLAGS,80位FP0-FP7、64位MMX0-MMX7、128位XMM0-XMM7,网段:CS-GS,特价:CR0-CR4 ,DR0-DR7,TR3-TR7,GDTR,IDTR,LDTR,MSR,并且在x86-64上也为R8-R15。并不是所有这些都可以从ring-3上访问,但是大多数(并且大多数)已被最近(2006年后)的GCC / VC ++编译器使用。总共比“可悲的8”略多;)。
亚伯2012年

2

为了完成您想做的事情,我只是拿了《英特尔指令集参考》(可能不是我所使用的确切的参考集,但是看起来已经足够了)和一些我在Visual Studio中编写的简单程序,并开始将它们扔进IDAPro / Windbg 。当我淘汰自己的程序时,crackmes的软件很有帮助。

我假设您对程序如何在Windows上执行有一些基本的了解。但是实际上,对于阅读汇编来说,只有几条指令需要学习,并且这些指令有几种风格(例如,有一个跳转指令,跳转具有几种风格,例如“如果相等就跳转”,“如果ecx等于零就跳转”)等)。一旦学习了基本说明,就很容易掌握程序执行的要旨。IDA的图形视图很有帮助,如果您要使用Windbg跟踪程序,则可以很容易地弄清楚指令的执行方式(如果不确定)。

像这样玩了一段时间之后,我买了《Hacker Disassembly Uncovered》。通常,我会远离书名中带有“ Hacker”一词的书籍,但我真的很喜欢这一本书对如何分解已编译的代码进行了非常深入的探讨。他还研究了编译器优化和一些有趣的效率方面的内容。

这完全取决于您是否希望能够深入理解该程序。如果您对目标进行反向工程以寻找漏洞,编写漏洞利用代码或分析打包的恶意软件以获取功能,则需要更多的准备时间才能真正解决问题(尤其是对于更高级的恶意软件而言) )。另一方面,如果您只想更改自己喜欢的视频游戏中角色的等级,则应该在相对较短的时间内就做好了。


1

MIPS是目前的一种标准的教学汇编语言。您可以获取MIPS模拟器(spim)和各种教学材料。

就个人而言,我不是粉丝。我更喜欢IA32。


MIPS很好。68000也是,如果您学习68000,则可以编写在MAME中运行的二进制文件。:-)
Nosredna

1

我个人最喜欢的是NASM,主要是因为它是多平台的,并且可以编译MMX,SSE,64位...

我开始使用gcc编译一些简单的C源文件,然后将汇编程序指令从gcc格式“转码”为NASM格式。然后,您可以更改一小段代码,并验证其带来的性能改进。

NASM文档确实很完整,我从不需要从书籍或其他来源中搜索信息。




0

为了真正实现您的目标,您可以考虑从所在的IDE开始。通常是一个反汇编程序窗口,因此您可以单步执行代码。通常存在某种视图,可让您查看寄存器并查看内存区域。

检查未优化的c / c ++代码将有助于建立与编译器为您的源代码生成的代码类型的链接。某些编译器具有某种ASM保留字,可让您在代码中插入机器指令。

我的建议是使用这些工具一段时间,弄湿你的脚,然后站起来?下?在您正在运行的任何平台上直接编译代码。

那里有很多很棒的工具,但是您可能会发现它更有趣,可以避免一开始就陡峭的学习曲线。


0

我们学习了使用微控制器开发套件(Motorola HC12)和厚数据表的组装方法。


0

我知道这是个离题的话题,但是由于您是Windows程序员,所以我不禁认为,这可能是更适当和/或更有效地利用您的时间来学习MSIL的。不,它不是汇编语言,但在此.NET时代可能更相关。


0

知道汇编对于调试很有用,但是我不会因为使用它来优化代码而感到兴奋。现在,现代编译器通常在优化人类方面要好得多。


嗯 您仍然可以自己花费很多额外的编码程序集,但是要击败编译器,需要花费更多的精力。
Nosredna

0

您可以查看xorpd x86 Assembly视频课程。(我写的)。课程本身是付费的,但是练习是开源的,在github上。如果您有一定的编程经验,我认为您应该能够练习并理解所有内容。

请注意,该代码适用于Windows平台,并且是使用Fasm汇编器编写的。该课程和练习不包含任何高级构造,但是,如果您愿意,可以使用Fasm创建非常复杂的宏。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.