我在互联网上搜索二进制编程,人们似乎唯一愿意给出的回答是:“你为什么要用二进制编程?” “这很愚蠢,使用装配。” “你没有什么可以摆脱它,学习没有意义。”
如果你是这些人之一,我感谢你的意见,但它没有回答我的问题。
虽然我不打算真正尝试在Binary中编程,但我知道的理由是:
我有兴趣了解汇编命令背后的二进制指令。
我正在设计一个实验,其中生成随机二进制指令。我希望它们是有效的二进制命令,我希望能够解释这些命令在运行时会做什么。
话虽如此,有没有人知道任何可以学习二进制编程的资源?
答案 0 :(得分:6)
通常,汇编指令和机器代码(你称之为二进制代码)之间存在一对一的映射。您可以在指令集架构文档中找到这些映射,以了解您关心的任何机器。热门的例子:
您将能够找到您想要使用的任何架构的类似文档。您可以使用这些手册中的信息来解码给定程序的机器指令,并确定它们是如何从汇编源生成的,或者如果您愿意,也可以手工组装您自己的程序。
答案 1 :(得分:2)
这是我学习二进制文件的方法: 1.打开命令提示符并输入“debug”作为命令。
请注意,要以实际二进制编程,您需要一个十六进制编辑器。这是我使用的那个:
http://www.chmaas.handshake.de/delphi/freeware/xvi32/xvi32.htm
我学习更多复杂语言(如c ++)的另一个想法是和汇编一样,但是在十六进制编辑器中打开它。
答案 2 :(得分:1)
指令集手册非常有用,并且具有一定程度的计算机硬件架构知识。以下是一些示例文档:
答案 3 :(得分:1)
好吧,作为一个从二进制时代起就一直这样做的老黑客: - )
让我试着让它更具可读性。
Binary正如您所描述的那样,它被称为机器代码。
为了更进一步,CPU是硬编码以响应某些指令,作为一个例子(请注意我暂时没有任何参考)
6502机器代码中的值A9表示LDA(在其他架构上,这可能意味着不同的东西)
所以,如果你在6502 CPU上工作,那么序列A920就意味着用十六进制值0f 0x20加载累加器。
根据所讨论的CPU以及指令集的编码方式,数字中的不同位将导致CPU(这是纯粹的逻辑)执行不同的操作。
并且,根据制造商的规格,不同的位位置指定每个操作的内容。
例如,在臂处理器中,位30和30。 31是分支说明符,其中在6502中它们是零页内存指示符。
本质上,二进制指令特定于所讨论的CPU,并且通常不能移植到另一个CPU(或任何其他智能硅设备),因此移植和编写软件通常是非常困难的任务,除非你有深入了解您的编程芯片。
除非您在英特尔或芯片制造商这样的公司工作,否则这些天真的没有必要知道这些东西。然而,如果你的速度迷喜欢击中金属并挤压每一滴性能,那么你仍然可以使用工具来进行这种编程。
答案 4 :(得分:1)
很棒的答案。我只想为谁使用linux添加一个简单的脚本,它显示任何指令的二进制表示。您需要一份NASM(但您可以轻松编辑它以便它使用GAS或任何其他汇编程序)和objdump:
echo "$1" > testProgram.asm
nasm testProgram.asm -o testProgram.out -f elf -g
chmod 744 testProgram.out
objdump ./testProgram.out -d -M intel | grep ' 0:'
rm testProgram.out testProgram.asm
以下是一些例子:
blackbear@blackbear-laptop:~$ ./viewOpcode.sh "add ecx, 5"
0: 81 c1 05 00 00 00 add ecx,0x5
blackbear@blackbear-laptop:~$ ./viewOpcode.sh "int 0x80"
0: cd 80 int 0x80
blackbear@blackbear-laptop:~$ ./viewOpcode.sh "fmul st0, st1"
0: d8 c9 fmul st,st(1)
blackbear@blackbear-laptop:~$ ./viewOpcode.sh "andps xmm0, xmm1"
0: 0f 54 c1 andps xmm0,xmm1
blackbear@blackbear-laptop:~$ ./viewOpcode.sh "movntq [edi], mm0"
0: 0f e7 07 movntq QWORD PTR [edi],mm0
blackbear@blackbear-laptop:~$