从exe程序反汇编得到py源码

背景

手上有个简单的小程序,用来识别公司应用的登录窗口,自动填写用户名密码,点击登录(要是有保存用户名密码功能多好啊)

今天忽然想看一下实现原理是啥,源码是啥

主要工具及环境

DIE pyinstxtractor uncompyle6 pycdc 编译好的pycdc vs2019 win10x64 python3.9.6

分析exe

下载Detect It Easy 软件,并打开我们的小程序从exe程序反汇编得到py源码_第1张图片
上面的PyInstaller表明这是一个python程序,使用pyinstaller打包成exe

首先解包这个exe

既然是python打包的,先解包看看里面有啥

  • 下载pyinstxtractor ,随后使用python pyinstxtractor xxx.exe解包,输出如下

E:\xxxx>python pyinstxtractor.py xxxx.exe
[+] Processing xxxx.exe
[+] Pyinstaller version: 2.1+
[+] Python version: 309
[+] Length of package: 59527603 bytes
[+] Found 1053 files in CArchive
[+] Beginning extraction…please standby
will make file struct.pyc
will make file pyimod01_os_path.pyc
will make file pyimod02_archive.pyc
will make file pyimod03_importers.pyc
will make file pyimod04_ctypes.pyc
[+] Possible entry point: pyiboot01_bootstrap.pyc
[+] Possible entry point: pyi_rth_subprocess.pyc
[+] Possible entry point: pyi_rth_pkgutil.pyc
[+] Possible entry point: pyi_rth_multiprocessing.pyc
[+] Possible entry point: pyi_rth_inspect.pyc
[+] Possible entry point: pyi_rth__tkinter.pyc
[+] Possible entry point: xxxx.pyc

will make file tk\xmfbox.tcl
will make file PYZ-00.pyz
[+] Found 536 files in PYZ archive
[+] Successfully extracted pyinstaller archive: xxxx.exe
You can now use a python decompiler on the pyc files within the extracted directory

  • 由此我们得到了所有的pyc文件存放于xxxx_extracted目录下,pyc文件是python编译后产生的文件,还需将其反编译成py文件才能得到源码

反编译pyc文件

解出来了一堆pyc文件,pyc是py文件编译后生成的,需要反编译一下

  • 首先安装pip install uncompyle6,也可从网站下载源码
  • 运行命令uncompyle6 xxxx_extracted\xxxx.pyc
  • 如果pyc是python3.8及以下版本,则可直接得到源码文件,否则将得到如下提示
    从exe程序反汇编得到py源码_第2张图片

换个方式反编译pyc文件

由于这个exe是python3.9生成的,uncompyle6不支持。只能另觅他法,我们换pycdc再试一下

  • 下载pycdc 这是一个c++写的反编译pyc的工具
  • 使用cmake配置好pycdc工程,编译得到pycdas.exe pycdc.exe两个程序,拷贝到我们的e:\xxxx目录下,编译好的pycdc
  • 运行命令pycdc xxxx_extracted\xxxx.pyc > xxxx.py
  • 如果幸运则直接得到完整python文件,如果pyc内有pycdc不支持的指令,则只能得到部分py代码,并报错
    含有pycdc不支持的指令
    打开xxxx.py看一下
    从exe程序反汇编得到py源码_第3张图片中间代码略
    从exe程序反汇编得到py源码_第4张图片可以看出由于有不支持的指令JUMP_IF_NOT_EXC_MATCH,反编译工作只执行了一部分
    到底少了点什么呢?

大杀器–反编译字节码看看

既然不能直接得到py文件,我们使用大杀器吧

  • 执行命令pycdas.exe xxxx.exe_extracted\xxxx.pyc > xxxx.txt
    打开xxxx.txt
    从exe程序反汇编得到py源码_第5张图片我们看到已经得到了完整的字节码,LOAD_GLOBAL 读取一个全局变量,类似java字节码的感觉,对照一下左右的代码很容易读懂。

  • 随后就需要我们耐心的读xxxx.txt中的字节码,将pycdc生成的xxxx.py中缺少的部分自行补上,

  • 最后由于生成的xxxx.py部分语句并不符合语法,需要自己修改一下,再通读一下代码进行修正。

总结

  1. 我们首先使用DIE 工具探测出exe文件 是pyinstaller生成的
  2. 随后使用了uncompyle6 尝试反编译,由于uncompyle6不支持python3.9生成的pyc,这一步没有成功
  3. 随后使用了pycdc尝试反编译,由于碰到了不支持的JUMP_IF_NOT_EXC_MATCH指令,成功了一部分
  4. 最后使用了大杀器pycdas,得到了字节码,补全了代码(照着字节码看我们自己也能翻译出来python源码)

你可能感兴趣的:(程序人生,python,反编译)