diff options
| author | 2021-04-08 15:09:46 -0700 | |
|---|---|---|
| committer | 2021-04-08 15:09:46 -0700 | |
| commit | 93f99fb909a60b2bcc12c4967adf767c0a82c804 (patch) | |
| tree | 3df6941de7dd075c1a44c2a84d1f6242f8ad60fd | |
| parent | Bump urllib3 from 1.26.3 to 1.26.4 (diff) | |
| parent | Clarify documentation of None return code (diff) | |
Merge PR #100 - avoid decoding of invalid Unicode output
Use PYTHONIOENCODING to enable utf-8 stdout for the nsjail pipe,
and handle the potential case where this is bypassable.
| -rw-r--r-- | config/snekbox.cfg | 1 | ||||
| -rw-r--r-- | snekbox/api/resources/eval.py | 2 | ||||
| -rw-r--r-- | snekbox/nsjail.py | 10 | ||||
| -rw-r--r-- | tests/test_nsjail.py | 17 | 
4 files changed, 28 insertions, 2 deletions
| diff --git a/config/snekbox.cfg b/config/snekbox.cfg index 257b5ca..73e36e1 100644 --- a/config/snekbox.cfg +++ b/config/snekbox.cfg @@ -15,6 +15,7 @@ envar: "MKL_NUM_THREADS=1"  envar: "VECLIB_MAXIMUM_THREADS=1"  envar: "NUMEXPR_NUM_THREADS=1"  envar: "PYTHONPATH=/snekbox/user_base/lib/python3.9/site-packages" +envar: "PYTHONIOENCODING=utf-8:strict"  keep_caps: false diff --git a/snekbox/api/resources/eval.py b/snekbox/api/resources/eval.py index c567660..d96b811 100644 --- a/snekbox/api/resources/eval.py +++ b/snekbox/api/resources/eval.py @@ -41,7 +41,7 @@ class EvalResource:          The return codes mostly resemble those of a Unix shell. Some noteworthy cases:          - None -            The NsJail process failed to launch +            The NsJail process failed to launch or the output was invalid Unicode          - 137 (SIGKILL)              Typically because NsJail killed the Python process due to time or memory constraints          - 255 diff --git a/snekbox/nsjail.py b/snekbox/nsjail.py index 814b46c..9367cb2 100644 --- a/snekbox/nsjail.py +++ b/snekbox/nsjail.py @@ -208,7 +208,15 @@ class NsJail:              except ValueError:                  return CompletedProcess(args, None, "ValueError: embedded null byte", None) -            output = self._consume_stdout(nsjail) +            try: +                output = self._consume_stdout(nsjail) +            except UnicodeDecodeError: +                return CompletedProcess( +                    args, +                    None, +                    "UnicodeDecodeError: invalid Unicode in output pipe", +                    None, +                )              # When you send signal `N` to a subprocess to terminate it using Popen, it              # will return `-N` as its exit code. As we normally get `N + 128` back, we diff --git a/tests/test_nsjail.py b/tests/test_nsjail.py index 4d4676b..46193b2 100644 --- a/tests/test_nsjail.py +++ b/tests/test_nsjail.py @@ -100,6 +100,23 @@ class NsJailTests(unittest.TestCase):          self.assertEqual(result.stdout, "ValueError: embedded null byte")          self.assertEqual(result.stderr, None) +    def test_print_bad_unicode_encode_error(self): +        result = self.nsjail.python3("print(chr(56550))") +        self.assertEqual(result.returncode, 1) +        self.assertIn("UnicodeEncodeError", result.stdout) +        self.assertEqual(result.stderr, None) + +    def test_unicode_env_erase_escape_fails(self): +        result = self.nsjail.python3(dedent(""" +            import os +            import sys +            os.unsetenv('PYTHONIOENCODING') +            os.execl(sys.executable, 'python', '-c', 'print(chr(56550))') +        """).strip()) +        self.assertEqual(result.returncode, None) +        self.assertEqual(result.stdout, "UnicodeDecodeError: invalid Unicode in output pipe") +        self.assertEqual(result.stderr, None) +      @unittest.mock.patch("snekbox.nsjail.DEBUG", new=False)      def test_log_parser(self):          log_lines = ( | 
