反编译pyc源码-Python反编译,这些你不知道的心机和陷阱

说到Python文件后缀,不夸张的说你眼花缭乱,来看看你都遇到过哪些类型吧!

.py

如果你不知道这个,呵呵……那请你出去左转,你还是那种付钱的男孩,没有丝毫的改变。 我们去玩游戏吧...

.pyc

这个后缀应该算是Python的py代码之外最常遇到的文件类型了。

虽然Python通常被认为是一种解释性语言,但谁说它不能编译和执行呢?

Python通过编译生成的pyc文件,然后由Python虚拟机执行。 与py文件相比,编译成pyc本质上和py没有太大区别,只是这个模块的加载速度提高了,而代码并没有增强。 执行速度快,通常不需要主动编译pyc文件。

pyc文件存在的意义是什么?

除了稍微增强模块加载率之外,更多的是在一定意义上保护源代码不被泄露。

当然,为什么说它有一定的意义呢? 因为既然有编译,显然就有反编译,这个稍后再说……

如何将py文件编译成pyc文件? 有以下三种方法:

1.使用Python直接编译

python -m sample.py

2. py_编译

import py_compile
py_compile.compile('sample.py')

3. 编译全部

import compileall
compileall.compile_file('sample.py')
compileall.compile_dir(dirpath)

三种形式一目了然,区别在于compileall可以一次性递归编译文件夹下的所有py文件

.pyo

pyo是优化编译后的源文件,pyo文件的大小一般大于或等于pyc文件。

这个优化并没有多大作用,只是删除了断言。 原文如下:

当使用 -O 标志调用 Python 解释器时,会生成优化代码并将其存储在 .pyo 文件中。 优化器目前没有多大帮助; 它仅删除断言语句。 当使用-O时,所有字节码都会被优化; 。 pyc 文件将被忽略,.py 文件将被编译为优化的字节码。

指示:

反编译软件源代码怎么编译_反编译pyc源码_源码反编译固证

python -O -m py_compile sample.py

.pyd

看完前几个,相信你也能猜出字母d了。 是Python的动态链接库; 动态链接库(DLL)文件是一个可执行文件,允许程序共享代码和执行特殊任务所需的其他文件。 资源。

您可以在Python安装目录的DLL文件夹中看到它们。

.pyz(w)

从Python 3.5开始,.pyz和.pyzw分别被定义为“Python Zip应用程序”和“Windows下的Python Zip应用程序”的扩展名。

添加了外部zipapp模块以方便管理,并且可以使用Zip将Python程序打包成可执行的.pyz文件。

使用起来也比较简单,但是它不能像pyinstaller等打包的exe工具那样独立于Python环境运行,而且此类文件往往需要使用文本编辑器来查看其源代码信息,一般来说没什么用处。

。EXE文件

为什么单独提到exe文件,因为Python有很多工具可以将Python源代码打包成exe,使其可以脱离Python环境独立运行。

python反编译

源码反编译固证_反编译pyc源码_反编译软件源代码怎么编译

所谓道高一尺,魔高一尺。 无论是Python、JAVA还是C语言,只要有编译反编译pyc源码,就一定有反编译操作。

无论你怎么看待加密,都一定有人能够破解,只是成本不同,所以编译只能作为一种防君子小人的操作。

今天主要和大家聊聊pyc文件的反编译,有哪些小心的做法和陷阱。

首先,由于反编译是一种异常方法,Python自然不会原生自带这个模块。

我们需要先安装依赖项:

# 安装依赖
pip install uncompyle6

操作也比较简单,在命令行输入:

uncompyle6 sample.pyc(pyo) > sample.py

这就是结局? 阴谋和陷阱又如何呢? 哈哈,继续关注...

使用注释的技巧

我们创建一个名为 BreezePython.py 的文件,并对下面的代码进行编译和反编译,看看反编译内容与原始代码的区别

import platform

def test():
    """
    这是一个测试方法,用来验证反编译
    :return: None
    """

    # 打印系统详情
    print(platform.platform())

test()

编译:

python -m BreezePython.py

反编译:

uncompyle6 BreezePython.cpython-37.pyc > output.py

我们看一下反编译后的文件有什么不同:

# uncompyle6 version 3.6.4
# Python bytecode 3.7 (3394)
# Decompiled from: Python 3.7.3 (v3.7.3:ef4ec6ed12, Mar 25 2019, 22:22:05) [MSC v.1916 64 bit (AMD64)]
# Embedded file name: C:UsersAdministratorDesktopuncompileBreezePython.py
# Size of source mod 2**32: 453 bytes
import platform

def test():
    """
    这是一个测试方法,用来验证反编译
    :return: None
    """

    print(platform.platform())


test()
# okay decompiling BreezePython.cpython-37.pyc

与原来的代码相比有什么不同?

没错,注释...文档注释默认保留,但是用#所做的注释在编译+反编译过程中会丢失。

所以如果你是个心机小子,就用#来写代码注释吧。 即使代码被反编译了,没有注释,连我们自己都会被一大段没有注释的代码逼疯,哈哈。

反编译陷阱

反编译万无一失吗? 不...让我给你举个例子。 这段代码是随机的,只是为了让它在反编译时抛出错误:

class Demo:
    def __init__(self, color):
        self.color = color

    def jduge(self):
        if not self.color:
            return "get None"
        if not self.color == 'red':
            mood = "disappointed"
            return "I'm %s,I like white best" % mood
        return "get None..."


if __name__ == '__main__':
    Main = Demo("red")
    print(Main.jduge())

通常此代码应返回: get None...

但是这段代码反编译后是什么样子呢?

# uncompyle6 version 3.6.4
# Python bytecode 3.7 (3394)
# Decompiled from: Python 3.7.3 (v3.7.3:ef4ec6ed12, Mar 25 2019, 22:22:05) [MSC v.1916 64 bit (AMD64)]
# Embedded file name: C:UsersAdministratorDesktopuncompileBreezePython.py
# Size of source mod 2**32: 391 bytes

class Demo:
    def __init__(self, color):
        self.color = color
    def jduge(self):
        if not self.color:
            return 'get None'
        else:
            mood = self.color == 'red' or 'disappointed'
            return "I'm %s,I like white best" % mood
        return 'get None...'

if __name__ == '__main__':
    Main = Demo('red')
    print(Main.jduge())
# okay decompiling __pycache__BreezePython.cpython-37.pyc

编译后的代码返回:我是真的,我最喜欢白色

我勒个去? 这都搞成什么乱七八糟的事情了。

根据多年的挖掘经验,当反编译代码遇到多个if not时,最后一个if not就会被所谓的缩写弄巧成拙,最终导致反编译错误。

这是个坑,你也能利用吗?

这就是今天文章的全部内容。 希望这篇文章能让你了解Python的文件类型以及编译和反编译操作。 如果您有所收获反编译pyc源码,期待您的支持和转发。

留言送书

今天捐赠一本书:《Java高并发与网络编程亿万流量实战》

PS:最近当当网有满100立减5的活动