random...@fastmail.us wrote:
> Out of curiosity, is there a way to use eval "safely" (i.e. strictly > limiting what it has access to) across a privilege boundary? This also > comes up for pickle and other serialization formats that can store > arbitrary classes (i.e. call arbitrary constructors). Not really. If there is, it is very hard. Ned has a good write-up here: http://nedbatchelder.com/blog/201206/eval_really_is_dangerous.html Some years ago, Tav made an attempt to secure the interpreter against file system writes: http://tav.espians.com/a-challenge-to-break-python-security.html That didn't work so well, although Tav's efforts towards building a Capabilities version of Python are promising: http://tav.espians.com/paving-the-way-to-securing-the-python-interpreter.html Without a full parser, it's hard to defend against Denial Of Service attacks like this: # don't try this at home eval("100**100**100") We can *mitigate* the danger in a number of ways: - Combination of blacklists and whitelists. - Avoid *easy* access to built-ins by specifying the namespace that the code should be executed in: eval("code goes here", {'__builtins__'={}}) - If you need access to specific built-ins, add them to your namespace: eval("code goes here", {'__builtins__'={}, 'int'=int}) - Disallow any expression which includes underscore _ characters, this will make it harder (but maybe not impossible?) for an attacker to break out of your sandbox. - Have a short limit on the length of the expression. The shorter the expression, the less surface an attacker has to attack. (An attacker may find some clever trick to escape the sandbox, but it's harder to do so in 20 characters than in 200.) - Run untrusted code in a separate process, with a timeout. - Use your OS facilities to run that process in a chroot jail. But even better is to avoid eval completely. If all you want is to evaluate a few simple constant expressions: py> from ast import literal_eval py> literal_eval('[None, 23, "hello", {0.5: "x"}]') [None, 23, 'hello', {0.5: 'x'}] -- Steven -- https://mail.python.org/mailman/listinfo/python-list