练习编写Python编译器

10

最近我一直在阅读关于CPU和架构方面的内容,主要是操作码、集成电路等。我已经做了几年的Python开发,想练习一下编写机器码。

我觉得很有趣,可以将一个非常简单的Python脚本编译成机器码,作为练习的方式。脚本如下:

a = 2
b = 3
c = a + b
print c

我正在使用Python编写编译器,因为我在Python方面比C更加擅长。我稍微查看了一下,发现有以下Python库可以帮助我:

binascii.hexify(hex(2))  <-- should convert 2 to binary, correct?

file = open('/usr/local/bin/my_sample_program','wb') <-- should write the resulting binary file

我还需要找到Intel Core i5的操作码,但这应该很容易。

我的问题如下:

1)我如何将操作码写入文件?换句话说,假设将寄存器设置为包含值2的操作码是0010,我如何将其作为程序第一行执行的前四个数字写入?

2)我如何告诉OS X或Ubuntu将程序加载到物理内存中?我假设编译器做的第一件事是将指令写入结果二进制文件的OS上?

3)如果您知道任何可以帮助我的资源,将不胜感激。


你尝试过查看Python解释器的源代码吗? - user849425
你所要做的事情很困难。要生成特定于平台的机器码可执行文件,你需要熟悉特定于平台的格式。例如,Ubuntu使用ELF格式(http://en.wikipedia.org/wiki/Elf_format)。 - Charles Salvia
@CharlesSalvia 我的印象是它与架构有关。也就是说,任何针对Intel i5的机器码都应该在任何其他i5 CPU和任何其他操作系统上运行,其余部分仅取决于操作系统?这样说对吗? - Sam Hammamy
@CharlesSalvia 请阅读维基百科。我认为它回答了我的问题中的第二个问题。谢谢,我会更深入地研究ELF。 - Sam Hammamy
2个回答

7
那是一个相当大的项目。除了学习编译器的工作原理外,您还需要阅读关于可加载文件格式(如ELF)和操作系统细节的大量信息。
我建议您将一个“汇编文件”作为编译器的输出。然后,您可以使用现有的汇编器将该文件转换为机器码。实际上,这就是大多数C编译器(包括GCC)在“表面下”所做的事情。
编辑:编译器或汇编器的输出通常是一个“目标文件”。这稍后会由链接器与其他目标文件组合。编写整个工具链,包括编译器、汇编器、链接器和其他相关工具,需要耗费多年的人力。因此,我认为您不应该认为像使用现有汇编器和链接器这样的直接解决方案是欺骗行为。

关于gcc编译器的有趣之处,我之前并不知道。使用汇编器也可以使输出程序更少地依赖于特定平台,对吧?因此,理论上我应该能够在Ubuntu和OS X下运行我的简单程序,只需要确保在编译时使用正确的汇编器即可... - Sam Hammamy
我也认为使用汇编器应该是“第一阶段”。我仍然想学习更多,所以在我完成第一阶段之后,我将不得不深入研究ELF。 - Sam Hammamy

3
编译Python并不容易。您可以看看具有即时编译器的pypy
另一个选择是从Python字节码开始,该字节码保存在.pyc文件中,如果使用标准Cpython解释器运行Python程序,则会生成一部分汇编/可执行代码以针对您的CPU进行处理。
请注意,您还需要编写大量的代码来实现所有内置类型和函数!

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接