diff options
author | Gregory P. Smith <greg@mad-scientist.com> | 2010-03-19 16:53:08 (GMT) |
---|---|---|
committer | Gregory P. Smith <greg@mad-scientist.com> | 2010-03-19 16:53:08 (GMT) |
commit | 32ec9da16617d7773d2a52a7fbba935aa9a1eba0 (patch) | |
tree | f3cb7fb1b088c4f5f635f7b2af3764502366e806 /Lib/test | |
parent | 3f88c0ece636ce533c6cbbfdd72e99518c6db974 (diff) | |
download | cpython-32ec9da16617d7773d2a52a7fbba935aa9a1eba0.zip cpython-32ec9da16617d7773d2a52a7fbba935aa9a1eba0.tar.gz cpython-32ec9da16617d7773d2a52a7fbba935aa9a1eba0.tar.bz2 |
* Fix a refleak when a preexec_fn was supplied (preexec_fn_args_tuple was not
being defref'ed).
* Fixes another potential refleak of a reference to the gc
module in the unlikely odd case where gc module isenabled or disable calls
fail.
* Adds a unittest for the above case to verify behavior and lack of leaks.
Diffstat (limited to 'Lib/test')
-rw-r--r-- | Lib/test/test_subprocess.py | 42 |
1 files changed, 42 insertions, 0 deletions
diff --git a/Lib/test/test_subprocess.py b/Lib/test/test_subprocess.py index 74d9ce4..9f8512d 100644 --- a/Lib/test/test_subprocess.py +++ b/Lib/test/test_subprocess.py @@ -9,6 +9,10 @@ import tempfile import time import re import sysconfig +try: + import gc +except ImportError: + gc = None mswindows = (sys.platform == "win32") @@ -650,6 +654,44 @@ class POSIXProcessTestCase(unittest.TestCase): self.fail("Exception raised by preexec_fn did not make it " "to the parent process.") + @unittest.skipUnless(gc, "Requires a gc module.") + def test_preexec_gc_module_failure(self): + # This tests the code that disables garbage collection if the child + # process will execute any Python. + def raise_runtime_error(): + raise RuntimeError("this shouldn't escape") + enabled = gc.isenabled() + orig_gc_disable = gc.disable + orig_gc_isenabled = gc.isenabled + try: + gc.disable() + self.assertFalse(gc.isenabled()) + subprocess.call([sys.executable, '-c', ''], + preexec_fn=lambda: None) + self.assertFalse(gc.isenabled(), + "Popen enabled gc when it shouldn't.") + + gc.enable() + self.assertTrue(gc.isenabled()) + subprocess.call([sys.executable, '-c', ''], + preexec_fn=lambda: None) + self.assertTrue(gc.isenabled(), "Popen left gc disabled.") + + gc.disable = raise_runtime_error + self.assertRaises(RuntimeError, subprocess.Popen, + [sys.executable, '-c', ''], + preexec_fn=lambda: None) + + del gc.isenabled # force an AttributeError + self.assertRaises(AttributeError, subprocess.Popen, + [sys.executable, '-c', ''], + preexec_fn=lambda: None) + finally: + gc.disable = orig_gc_disable + gc.isenabled = orig_gc_isenabled + if not enabled: + gc.disable() + def test_args_string(self): # args is a string fd, fname = mkstemp() |