Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 6 additions & 2 deletions Lib/json/tests/test_tool.py
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,9 @@ def test_infile_stdout(self):
infile = self._create_infile()
rc, out, err = assert_python_ok('-m', 'json.tool', infile)
self.assertEqual(out.splitlines(), self.expect.encode().splitlines())
self.assertEqual(err, b'')
# If COUNT_ALLOCS is defined, don't check stderr
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')

def test_infile_outfile(self):
infile = self._create_infile()
Expand All @@ -66,4 +68,6 @@ def test_infile_outfile(self):
with open(outfile, "r") as fp:
self.assertEqual(fp.read(), self.expect)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
# If COUNT_ALLOCS is defined, don't check stderr
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')
3 changes: 3 additions & 0 deletions Lib/test/support/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -1795,6 +1795,9 @@ def py3k_bytes(b):
except TypeError:
return bytes(b)

requires_type_collecting = unittest.skipIf(hasattr(sys, 'getcounts'),
'types are immortal if COUNT_ALLOCS is defined')

def args_from_interpreter_flags():
"""Return a list of command-line arguments reproducing the current
settings in sys.flags."""
Expand Down
2 changes: 2 additions & 0 deletions Lib/test/test_abc.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

import unittest, weakref
from test import test_support
from support import requires_type_collecting

import abc
from inspect import isabstract
Expand Down Expand Up @@ -208,6 +209,7 @@ class C(A, B):
C()
self.assertEqual(B.counter, 1)

@requires_type_collecting
def test_cache_leak(self):
# See issue #2521.
class A(object):
Expand Down
4 changes: 3 additions & 1 deletion Lib/test/test_gc.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import unittest
from test.test_support import verbose, run_unittest, start_threads
from test.support import (verbose, run_unittest, start_threads,
requires_type_collecting)
import sys
import time
import gc
Expand Down Expand Up @@ -90,6 +91,7 @@ class A:
del a
self.assertNotEqual(gc.collect(), 0)

@requires_type_collecting
def test_newinstance(self):
class A(object):
pass
Expand Down
2 changes: 1 addition & 1 deletion Lib/test/test_hash.py
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@ def get_hash(self, repr_, seed=None):
env.pop('PYTHONHASHSEED', None)
cmd_line = [sys.executable, '-c', self.get_hash_command(repr_)]
p = subprocess.Popen(cmd_line, stdin=subprocess.PIPE,
stdout=subprocess.PIPE, stderr=subprocess.STDOUT,
stdout=subprocess.PIPE, stderr=subprocess.PIPE,
env=env)
out, err = p.communicate()
out = test_support.strip_python_stderr(out)
Expand Down
3 changes: 2 additions & 1 deletion Lib/test/test_module.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# Test the module type
import unittest
from test.test_support import run_unittest, gc_collect
from test.support import run_unittest, gc_collect, requires_type_collecting

import sys
ModuleType = type(sys)
Expand Down Expand Up @@ -65,6 +65,7 @@ def f():
gc_collect()
self.assertEqual(f().__dict__["bar"], 4)

@requires_type_collecting
def test_clear_dict_in_ref_cycle(self):
destroyed = []
m = ModuleType("foo")
Expand Down
4 changes: 3 additions & 1 deletion Lib/test/test_multiprocessing.py
Original file line number Diff line number Diff line change
Expand Up @@ -2610,7 +2610,9 @@ def test_noforkbomb(self):
else:
rc, out, err = test.script_helper.assert_python_ok(name)
self.assertEqual(out.rstrip(), '123')
self.assertEqual(err, '')
# If COUNT_ALLOCS is defined, don't check stderr
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, '')

#
# Issue 12098: check sys.flags of child matches that for parent
Expand Down
1 change: 1 addition & 0 deletions Lib/test/test_regrtest.py
Original file line number Diff line number Diff line change
Expand Up @@ -493,6 +493,7 @@ def check_leak(self, code, what):
self.assertIn(line2, reflog)

@unittest.skipUnless(Py_DEBUG, 'need a debug build')
@support.requires_type_collecting
def test_huntrleaks(self):
# test --huntrleaks
code = textwrap.dedent("""
Expand Down
17 changes: 17 additions & 0 deletions Lib/test/test_subprocess.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,12 @@
SETBINARY = ''



# bpo-31692: If COUNT_ALLOCS is defined, stderr is flooded with allocation
# statistics and so cannot be checked in a reliable way
skip_unless_usable_stderr = test_support.requires_type_collecting
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"types are immortal if COUNT_ALLOCS is defined" looks bad skip message for these tests.



class BaseTestCase(unittest.TestCase):
def setUp(self):
# Try to minimize the number of children we have so this test
Expand Down Expand Up @@ -272,6 +278,7 @@ def test_stdout_fileobj(self):
tf.seek(0)
self.assertEqual(tf.read(), "orange")

@skip_unless_usable_stderr
def test_stderr_pipe(self):
# stderr redirection
p = subprocess.Popen([sys.executable, "-c",
Expand All @@ -280,6 +287,7 @@ def test_stderr_pipe(self):
self.addCleanup(p.stderr.close)
self.assertStderrEqual(p.stderr.read(), "strawberry")

@skip_unless_usable_stderr
def test_stderr_filedes(self):
# stderr is set to open file descriptor
tf = tempfile.TemporaryFile()
Expand All @@ -291,6 +299,7 @@ def test_stderr_filedes(self):
os.lseek(d, 0, 0)
self.assertStderrEqual(os.read(d, 1024), "strawberry")

@skip_unless_usable_stderr
def test_stderr_fileobj(self):
# stderr is set to open file object
tf = tempfile.TemporaryFile()
Expand All @@ -301,6 +310,7 @@ def test_stderr_fileobj(self):
tf.seek(0)
self.assertStderrEqual(tf.read(), "strawberry")

@skip_unless_usable_stderr
def test_stderr_redirect_with_no_stdout_redirect(self):
# test stderr=STDOUT while stdout=None (not set)

Expand All @@ -322,6 +332,7 @@ def test_stderr_redirect_with_no_stdout_redirect(self):
self.assertStderrEqual(stderr, b'') # should be empty
self.assertEqual(p.returncode, 0)

@skip_unless_usable_stderr
def test_stdout_stderr_pipe(self):
# capture stdout and stderr to the same pipe
p = subprocess.Popen([sys.executable, "-c",
Expand All @@ -334,6 +345,7 @@ def test_stdout_stderr_pipe(self):
self.addCleanup(p.stdout.close)
self.assertStderrEqual(p.stdout.read(), "appleorange")

@skip_unless_usable_stderr
def test_stdout_stderr_file(self):
# capture stdout and stderr to the same open file
tf = tempfile.TemporaryFile()
Expand Down Expand Up @@ -451,6 +463,7 @@ def test_communicate_stdout(self):
self.assertEqual(stdout, "pineapple")
self.assertEqual(stderr, None)

@skip_unless_usable_stderr
def test_communicate_stderr(self):
p = subprocess.Popen([sys.executable, "-c",
'import sys; sys.stderr.write("pineapple")'],
Expand All @@ -459,6 +472,7 @@ def test_communicate_stderr(self):
self.assertEqual(stdout, None)
self.assertStderrEqual(stderr, "pineapple")

@skip_unless_usable_stderr
def test_communicate(self):
p = subprocess.Popen([sys.executable, "-c",
'import sys,os;'
Expand Down Expand Up @@ -525,6 +539,7 @@ def test_communicate_pipe_buf(self):
(stdout, stderr) = p.communicate(string_to_write)
self.assertEqual(stdout, string_to_write)

@skip_unless_usable_stderr
def test_writes_before_communicate(self):
# stdin.write before communicate()
p = subprocess.Popen([sys.executable, "-c",
Expand Down Expand Up @@ -1071,6 +1086,7 @@ def test_terminate_dead(self):
# Terminating a dead process
self._kill_dead_process('terminate')

@skip_unless_usable_stderr
def check_close_std_fds(self, fds):
# Issue #9905: test that subprocess pipes still work properly with
# some standard fds closed
Expand Down Expand Up @@ -1173,6 +1189,7 @@ def check_swap_fds(self, stdin_no, stdout_no, stderr_no):
# When duping fds, if there arises a situation where one of the fds is
# either 0, 1 or 2, it is possible that it is overwritten (#12607).
# This tests all combinations of this.
@skip_unless_usable_stderr
def test_swap_fds(self):
self.check_swap_fds(0, 1, 2)
self.check_swap_fds(0, 2, 1)
Expand Down
21 changes: 15 additions & 6 deletions Lib/test/test_sys.py
Original file line number Diff line number Diff line change
Expand Up @@ -129,7 +129,9 @@ def test_exit(self):
rc, out, err = assert_python_ok('-c', 'import sys; sys.exit()')
self.assertEqual(rc, 0)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
# If COUNT_ALLOCS is defined, don't check stderr
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')

# call with integer argument
with self.assertRaises(SystemExit) as cm:
Expand Down Expand Up @@ -157,23 +159,27 @@ def test_exit(self):
rc, out, err = assert_python_failure('-c', 'raise SystemExit, 46')
self.assertEqual(rc, 46)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')
# ... and normalized
rc, out, err = assert_python_failure('-c', 'raise SystemExit(47)')
self.assertEqual(rc, 47)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')

# test that the exit machinery handles long exit codes
rc, out, err = assert_python_failure('-c', 'raise SystemExit(47L)')
self.assertEqual(rc, 47)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')

rc, out, err = assert_python_ok('-c', 'raise SystemExit(0L)')
self.assertEqual(rc, 0)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')

def check_exit_message(code, expected, **env_vars):
rc, out, err = assert_python_failure('-c', code, **env_vars)
Expand Down Expand Up @@ -748,7 +754,10 @@ def delx(self): del self.__x
# tupleiterator
check(iter(()), size('lP'))
# type
s = vsize('P2P15Pl4PP9PP11PI' # PyTypeObject
fmt = 'P2P15Pl4PP9PP11PI'
if hasattr(sys, 'getcounts'):
fmt += '3P2P'
s = vsize(fmt + # PyTypeObject
'39P' # PyNumberMethods
'3P' # PyMappingMethods
'10P' # PySequenceMethods
Expand Down
11 changes: 8 additions & 3 deletions Lib/test/test_threading.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# Very rudimentary test of threading module

import test.test_support
from test.test_support import verbose, cpython_only
from test.support import verbose, cpython_only, requires_type_collecting
from test.script_helper import assert_python_ok

import random
Expand Down Expand Up @@ -360,7 +360,9 @@ def child():
self.assertEqual(stdout.strip(),
"Woke up, sleep function is: <built-in function sleep>")
stderr = re.sub(r"^\[\d+ refs\]", "", stderr, re.MULTILINE).strip()
self.assertEqual(stderr, "")
# If COUNT_ALLOCS is defined, don't check stderr
if not hasattr(sys, 'getcounts'):
self.assertEqual(stderr, "")

def test_enumerate_after_join(self):
# Try hard to trigger #1703448: a thread is still returned in
Expand Down Expand Up @@ -437,7 +439,9 @@ def background_thread(evt):
"""
_, out, err = assert_python_ok("-c", code)
self.assertEqual(out, '')
self.assertEqual(err, '')
# If COUNT_ALLOCS is defined, don't check stderr
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, '')

@unittest.skipUnless(hasattr(os, 'fork'), "needs os.fork()")
def test_is_alive_after_fork(self):
Expand Down Expand Up @@ -812,6 +816,7 @@ def run():
self.assertIn("ZeroDivisionError", err)
self.assertNotIn("Unhandled exception", err)

@requires_type_collecting
def test_print_exception_stderr_is_none_1(self):
script = r"""if 1:
import sys
Expand Down
10 changes: 7 additions & 3 deletions Lib/test/test_tools.py
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,9 @@ def test_selftest(self):

rc, out, err = assert_python_ok(self.script, '-d', data_path)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
# If COUNT_ALLOCS is defined, don't check stderr
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')
backup = data_path + '~'
self.assertTrue(os.path.exists(backup))
with open(backup) as f:
Expand All @@ -82,7 +84,8 @@ def test_selftest(self):

rc, out, err = assert_python_ok(self.script, '-c', data_path)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')
with open(backup) as f:
self.assertEqual(f.read(), clean)
with open(data_path) as f:
Expand All @@ -93,7 +96,8 @@ def test_selftest(self):
f.write(broken)
rc, out, err = assert_python_ok(self.script, '-r', data_path)
self.assertEqual(out, b'')
self.assertEqual(err, b'')
if not hasattr(sys, 'getcounts'):
self.assertEqual(err, b'')
with open(backup) as f:
self.assertEqual(f.read(), broken)
with open(data_path) as f:
Expand Down
4 changes: 4 additions & 0 deletions Lib/test/test_warnings.py
Original file line number Diff line number Diff line change
Expand Up @@ -419,6 +419,8 @@ def test_improper_option(self):
rc, out, err = assert_python_ok("-Wxxx", "-c", "pass")
self.assertIn(b"Invalid -W option ignored: invalid action: 'xxx'", err)

# Don't check stderr when COUNT_ALLOCS is defined
@test_support.requires_type_collecting
def test_warnings_bootstrap(self):
# Check that the warnings module does get loaded when -W<some option>
# is used (see issue #10372 for an example of silent bootstrap failure).
Expand Down Expand Up @@ -575,6 +577,8 @@ def test_filename_none(self):
finally:
globals_dict['__file__'] = oldfile

# Don't check stderr when COUNT_ALLOCS is defined
@test_support.requires_type_collecting
def test_stderr_none(self):
rc, stdout, stderr = assert_python_ok("-c",
"import sys; sys.stderr = None; "
Expand Down
1 change: 1 addition & 0 deletions Lib/test/test_weakref.py
Original file line number Diff line number Diff line change
Expand Up @@ -601,6 +601,7 @@ class D:
del c1, c2, C, D
gc.collect()

@test_support.requires_type_collecting
def test_callback_in_cycle_resurrection(self):
import gc

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
COUNT_ALLOCSi debug mode now writes allocations statistics into stderr,
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Typo: COUNT_ALLOCSi

rather than stdout.
2 changes: 1 addition & 1 deletion Python/pythonrun.c
Original file line number Diff line number Diff line change
Expand Up @@ -481,7 +481,7 @@ Py_Finalize(void)

/* Debugging stuff */
#ifdef COUNT_ALLOCS
dump_counts(stdout);
dump_counts(stderr);
#endif

PRINT_TOTAL_REFS();
Expand Down