提问人:dF. 提问时间:8/26/2008 最后编辑:dF. 更新时间:11/4/2012 访问量:4406
“safe_eval”真的安全吗?
Is "safe_eval" really safe?
问:
我正在寻找一个“安全”的 eval 函数,以实现类似电子表格的计算(使用 numpy/scipy)。
自 2.3 以来,由于明显无法修复的安全问题,执行此操作的功能(rexec 模块)已从 Python 中删除。有几个第三方黑客声称可以做到这一点 - 我发现的最深思熟虑的解决方案是这个 Python Cookbok 食谱,“safe_eval”。
如果我使用它(或类似的东西)来防止恶意代码,或者我是否坚持编写自己的解析器,我是否合理安全?有谁知道更好的选择?
编辑:我刚刚发现了RestrictedPython,它是Zope的一部分。欢迎对此提出任何意见。
答:
编写自己的解析器可能很有趣!这可能是一个更好的选择,因为人们在输入公式时希望使用熟悉的电子表格语法(Excel 等)而不是 Python。我不熟悉safe_eval但我想像这样的东西肯定有被利用的潜力。
虽然这个代码看起来很安全,但我一直认为,只要有足够的时间,任何有足够动力的人都可以破坏它。我确实认为要做到这一点需要相当大的决心,但我相对确定这是可以做到的。
丹尼尔,Jinja 实现了一个沙盒环境,它可能对您有用,也可能没有用。据我所知,它还没有“理解”列表推导式。
我想这取决于你对安全的定义。很多安全性取决于您传入的内容以及允许您在上下文中传递的内容。例如,如果传入一个文件,我可以打开任意文件:
>>> names['f'] = open('foo', 'w+')
>>> safe_eval.safe_eval("baz = type(f)('baz', 'w+')", names)
>>> names['baz']
<open file 'baz', mode 'w+' at 0x413da0>
此外,环境非常受限(你不能传入模块),因此,你不能简单地传入一个实用函数的模块,如re或random。
另一方面,你不需要编写自己的解析器,你可以为 python ast 编写自己的赋值器:
>>> import compiler
>>> ast = compiler.parse("print 'Hello world!'")
这样,希望您可以实施安全导入。另一个想法是使用 Jython 或 IronPython 并利用 Java/.Net 沙盒功能。
如果你只需要在 Python 中写下和读取一些数据结构,并且不需要执行自定义代码的实际容量,那么这个更适合:http://code.activestate.com/recipes/364469-safe-eval/
它保证不执行任何代码,只评估静态数据结构:字符串、列表、元组、字典。
所需的功能位于编译器语言服务中,请参阅 http://docs.python.org/library/language.html 如果将应用定义为仅接受表达式,则可以将输入编译为表达式,如果不是表达式,则会收到异常,例如,如果存在分号或语句形式。
上一个:网站编程漏洞清单
下一个:通过公共网络安全同步文件夹
评论