了解如何手动发出处理器指令

我正在阅读一篇关于如何构buildJit编译器的文章,作者基本上使用这个代码:

// Processor instructions for: // mov eax, 0 // ret unsigned char code[] = {0xb8, 0x00, 0x00, 0x00, 0x00, 0xc3}; void *mem = mmap(NULL, sizeof(code), PROT_WRITE | PROT_EXEC, MAP_ANON | MAP_PRIVATE, -1, 0); memcpy(mem, code, sizeof(code)); int (*func)() = mem; return func(); 

除了他知道如何手动将汇编指令映射到数字代码外,我得到关于代码的所有信息。 我需要学习什么才能理解?

Solutions Collecting From Web of "了解如何手动发出处理器指令"

我是文章作者,希望你喜欢它!

为了构建这些价值观,我基本上做到了

 $ cat test.S .intel_syntax noprefix mov eax, 0 ret $ gcc -c -o test.o test.S $ objdump -d -M intel test.o test.o: file format elf64-x86-64 Disassembly of section .text: 0000000000000000 <.text>: 0: b8 00 00 00 00 mov eax,0x0 5: c3 ret 

您可以在左列中看到指令的字节。 除非你有一个很好的理由,否则我不建议深入学习指令编码。 它们非常复杂,汇编器非常擅长生成这些东西。 在这个水平上还有很多其他的东西需要学习,这样可以更好地利用你的大脑能量。 阅读Agner Fog的手册可以获得一个很好的开始。

有一些参考资料( 如Intel 64和IA-32的资料 )涵盖了如何将汇编指令映射到实际的机器码上。 这当然会在CPU /环境之间进行 – 例如,以上方法在ARM系统上将不起作用。

或者,这些值可能会从现有的生成输出中复制,例如从汇编器的输出中复制。

你可以使用许多库来编写一个JIT。 AsmJit将帮助您发出机器代码指令(在x86上)。 GNU闪电 , libjit , LLVM会将一些抽象指令集(或抽象语法树)转换成机器码。

处理器指令集体系结构被记录下来(长时间无聊的文件)。 对于x86,您可能需要读取数千页。