4 ms·
Building a truly safe Python sandbox (well, in CPython at least) is widely considered a fool's errand [0]. However, a Python sandbox can be relatively safely do
by bryanh 12y ago
Building a truly safe Python sandbox (well, in CPython at least) is widely considered a fool's errand [0]. However, a Python sandbox can be relatively safely done in two ways:
1. By completely reimplementing Python at a lower level and intercepting system calls, like PyPy's sandbox feature [1].
2. By utilizing other, more mature OS level constructs (IE: think containerization like LXC (which is imperfect), stacking OS features like seccomp/chroot/etc. or better, true virtualization like Xen).
Ideally, you'd combine them both and then run them on a "dumb box" which is just a REST API with no other keys or system access. The key to designing moderately secure sandboxes is just accepting that there are angles of attack you haven't considered yet, so design in layers.
If you find yourself inspecting code to decide if it is safe, you are fighting a losing battle... I'd love to hear of any success stories here though!
Great detailed write up of the pitfalls @op, thanks.
[0] https://github.com/haypo/pysandbox/ https://github.com/haypo/pysandbox/ or https://lwn.net/Articles/574215/ https://lwn.net/Articles/574215/
[1] http://pypy.readthedocs.org/en/latest/sandbox.html http://pypy.readthedocs.org/en/latest/sandbox.html
- usaar333 12y ago#2 alone - running items in an LXC jail without root access is far - is quite secure (and what we relied on at PiCloud to set up our python sandboxes). If you still insist on trying to build safe-code inspectors, be very skeptical of what your protection is capable of. For instance, why even bother blocking static strings? Such trivially-breakable "security" being placed in your code only serves to distract you and give false confidence.
- bryanh 12y agoAs a rule, an LXC jail is definitely very much better than code-inspection, but it is worth taking the time reading up on some of the rather specific configuration needed to tighten up LXC/namespaces. Docker (previously DotCloud) obviously has a lot riding on this, so they are taking secure-by-default configuration pretty seriously. [0] [0] https://docs.docker.com/articles/security/ https://docs.docker.com/articles/security/
- deckiedan 12y agoI wrote a very locked down python "expression evaluator" library ( https://github.com/danthedeckie/simpleeval https://github.com/danthedeckie/simpleeval ) which uses code inspection and is reasonably safe (caveats listed in the README). Any comments or loopholes found would be appreciated...
- eru 12y ago> If you find yourself inspecting code to decide if it is safe, you are fighting a losing battle... I'd love to hear of any success stories here though! NaCL, seL4 and the original proof-carrying code examples of packet filter are inspecting code, but on a very rigorous level.
- nhaehnle 12y agoNaCL is a good example that shows how inspecting code is not actually the mistake that was made by the Python sandbox that was attacked in the article. The mistake was that the inspection was based on a blacklist rather than a whitelist. Sandboxing based on blacklists is a recipe for disaster, and it's an unfortunate accident of history that the default Python implementation (CPython) makes whitelisting practically impossible. Luckily, there are alternatives as others in the thread have pointed out.
- Erwin 12y agoAs far as I know, Zope's sandbox has not been broken: https://pypi.python.org/pypi/RestrictedPython https://pypi.python.org/pypi/RestrictedPython The approach there is to rewrite your Python code to disallow any potentially bad operation. E.g. your code cannot access identifiers starting with _ and the list of builtins is restricted (no "open" by default obviously, but also no "type"!) Any sandbox code doing X.Y is rewritten to _your_getattr(X, "Y") which can decide whether to allow access or not at runtime. The main thing to be careful of, is not accidentally injecting any callables like "file" into there, as just calling an object does not undergo a security check (given that you might want to pass some data INTO your sandbox). This does not limit resource usage however, i.e. you can still try to allocate memory/use up CPU time.
- JohnnyGrey 12y agoThat's exactly what I though, the python code need to be alternated to get the returning approach. Thanks for pointing that out!
- nl 12y agoNote that the documentation contains the following: "RestrictedPython was bad idea and mostly causes headache. Avoid through-the-web Zope scripts if possible."[1] [1]http://docs.plone.org/develop/plone/security/sandboxing.html http://docs.plone.org/develop/plone/security/sandboxing.html
- dalke 12y agoQuoting from the bug page for "Zope sandbox escape via SecureModuleImporter from Products/PageTemplates/ZRPythonExpr.py" at https://bugs.launchpad.net/zope2/+bug/1047318 https://bugs.launchpad.net/zope2/+bug/1047318 : > Restricted code doesn't actually protect against malicious users. It's only a best-effort attempt against introducing accidental security issues for semi-professional developers. BTW, another attack vector (besides resource use) is to use code that causes Python itself to crash. For example, "{[{}]}".format({"{}": 5}) will segfault Python 3.3 (see http://bugs.python.org/issue17644 http://bugs.python.org/issue17644 ). The harder question is, are any of the ways to segfault Python exploitable?
- xorcist 12y agoWhat about the Python sandbox on App Engine? I believe it is fairly secure, but I don't know if it's comparable to the ones you mentioned.
- nl 12y agoThat's implemented on top of Linux Containers.
- nl 12y agoPython on ZeroVM is pretty safe[1]. Of course, you make all kinds of sacrifices using ZeroVM. Nevertheless, it's pretty robust and lightweight. I managed to get Python-on-ZeroVM running on Docker (ie, LXC) which gave me a pretty decently safe platform for running arbitrary code. It's atrophied since it was working, but I think it had some real potential. [1] https://github.com/zerovm/zpython2 https://github.com/zerovm/zpython2
- Pxtl 12y agoYup. I remember working on q game engine many years ago and we wanted to use python as a scripting language and found the trail of broken dreams that is the various attempts to sandbox Python. Just use Lua if you need a sandboxed dynamically-typed environment.