Python跨版本字节码反编译器
项目描述
decompyle3
A native Python cross-version decompiler and fragment decompiler. A reworking of uncompyle6.
简介
decompyle3 将Python字节码转换回等效的Python源代码。它接受从Python 3.7版本开始的字节码。
有关旧版Python字节码的反编译,请参阅 uncompyle6。
为什么是这个?
Uncompyle6非常棒,但它处理控制流的方式存在一个基本问题。在Python的早期,由于优化很少,代码是以非常模板化的方式生成的,因此可以通过简单地查看代码模式来推断控制流结构。
随着时间的推移,代码优化越来越多,特别是在处理跳转方面,使得仅从代码模式严格检测控制流变得更加困难。这个问题早在Python 2.4(2004年)就被注意到了,但由于这是一个困难的问题,到目前为止还没有得到令人满意的解决。
最初尝试解决这个问题是在指令流中添加标记,最初这是一个 COME_FROM 指令,然后使用它在模式检测中使用。
多年来,我将这个概念扩展得更加具体,因此添加了 COME_FROM_LOOP 和 COME_FROM_WITH。在语法减少时,我还添加了检查,以确保跳转与假设的 COME_FROM 目标相匹配。
然而,所有这些都相当复杂,不够稳健,极大地减缓了反解析速度,实际上也难以维持。
因此,在这个项目中,我们开始重写和重构语法。
然而,很明显,即使这样做也不够。需要通过使用支配集和逆支配集来解决控制流问题,这些可以在 python-control-flow 项目中找到。
我最终慢慢地在这个又一个非公开项目中做这件事。这是一项大量工作。虽然非常感谢赞助,但资助并不与工作量相匹配,而且我目前有一份全职工作。因此,如果可能的话,它可能需要一段时间才能公开,如果那时还没有的话。
要求
这里的代码可以在 Python 3.7 或 3.8 版本上运行。它可以读取的字节码文件已经在 Python 3.7 和 3.8 版本的字节码上进行了测试。
安装
您可以使用 decompyle3 名称从 PyPI 安装。
pip install decompyle3
要从源代码安装,此项目使用 setup.py,因此它遵循标准的 Python 流程。
$ pip install -e . # set up to run from source tree
或
$ python setup.py install # may need sudo
还提供了一个 GNU Makefile,因此可以使用 make install
(可能是作为 root 或 sudo)执行上述步骤。
运行测试
make check
添加了 GNU makefile,以简化设置运行正确命令和从最快到最慢运行测试的过程。
如果您已安装 remake,您可以通过 remake --tasks
命令查看所有任务,包括测试。
使用
运行
$ decompyle3 *compiled-python-file-pyc-or-pyo*
对于使用帮助
$ decompyle3 -h
验证
如果您想验证反编译过程的正确性,请添加 --syntax-verify
选项。然而,由于 Python 语法会发生变化,您应该在使用此选项时,确保字节码是即将检查语法的 Python 解释器的正确字节码。
您还可以与其他 Python 反编译器(如 unpyc37)的结果进行比较。由于它们的工作方式不同,这里的错误通常不在于那个,反之亦然。
这类程序中有一个有趣的类别,可以通过运行测试来提供更强的验证:当运行时自我测试的程序。我们的测试套件包括这些。
Python 还附带了一系列类似程序:它的标准库测试套件。我们在 test/stdlib
中有一些代码来促进这种类型的检查。
已知错误/限制
我们只支持已发布版本,不支持候选版本。 然而,请注意,发布版本的魔法通常与发布前的最后一个候选版本相同。
我们也不处理 PJOrion 或其他混淆代码。对于 PJOrion,尝试:PJOrion Deobfuscator 来解混淆字节码,在尝试此工具之前获取有效的字节码;pydecipher 可能会帮助。
此程序无法反编译由 Py2EXE 创建的 Microsoft Windows EXE 文件,尽管我们可以在正确提取字节码后可能反编译代码。 Pydeinstaller 可能有助于解包 Pyinstaller 打包器。
处理表达式或语句的长列表会很慢。我们不处理不使用字节码的 Cython 或 MicroPython。
反编译中存在许多错误。而且这适用于我遇到的所有其他 CPython 反编译器,即使是那些声称在某些特定版本(如 2.4)上“完美”的。
随着Python的发展,反编译也越来越困难,因为编译过程更加复杂,语言本身也更加复杂。我认为,类似unpyc37(基于3.3版本的反编译器)这样的临时尝试会越来越少,仅仅是因为这样做更加困难。好消息是,至少从我个人的角度来看,我认为我理解了如何以更稳健的方式解决这些问题。但是,现在项目资金尚未得到改善,我不打算对Python 3.8或3.9版本做出任何严肃的努力,包括可能出现的错误。我想在某些时候我可能会对它感兴趣。
您可以通过运行Python使用的标准测试套件来轻松找到错误。在任何给定时间,都有数十个已知问题相当孤立,如果投入时间可以解决。问题是,从事错误修复工作的人并不多。
您可能会遇到一个想要报告的错误。请这样做。但请注意,它可能不会立即引起我的注意。如果您以某种方式赞助或支持项目,我会优先考虑您的问题,而不是其他我可能正在做的事情。
另请参阅
https://github.com/andrew-tavera/unpyc37/:是https://code.google.com/archive/p/unpyc3/的间接分支。上述项目使用与这里不同的反编译技术。指令被逐步执行。一些指令使用堆栈生成字符串,而另一些则不。因为直接处理控制流,所以它也遭受了各种uncompyle和decompyle程序相同的问题。
https://github.com/rocky/python-xdis:跨Python版本的反汇编器
https://github.com/rocky/python-xasm:跨Python版本的汇编器
https://github.com/rocky/python-decompile3/wiki:维基文档,更详细地描述了代码及其各个方面
项目详情
下载文件
下载您平台的文件。如果您不确定要选择哪个,请了解更多关于安装包的信息。