test_gdb.test_pycfunction: test more calling conventions (GH-13668)

As the code paths for various METH_* conventions are diverging due
to optimizations, we should check they continue to be covered by
GDB integration.
This commit is contained in:
Petr Viktorin 2019-06-02 23:11:24 +02:00 committed by GitHub
parent cdce0574d0
commit 64e2c64f7f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 33 additions and 20 deletions

View File

@ -867,27 +867,40 @@ id(42)
# unless we add LD_PRELOAD=PATH-TO-libpthread.so.1 as a workaround
def test_pycfunction(self):
'Verify that "py-bt" displays invocations of PyCFunction instances'
# Tested function must not be defined with METH_NOARGS or METH_O,
# otherwise call_function() doesn't call PyCFunction_Call()
cmd = ('from time import gmtime\n'
'def foo():\n'
' gmtime(1)\n'
'def bar():\n'
' foo()\n'
'bar()\n')
# Verify with "py-bt":
gdb_output = self.get_stack_trace(cmd,
breakpoint='time_gmtime',
cmds_after_breakpoint=['bt', 'py-bt'],
)
self.assertIn('<built-in method gmtime', gdb_output)
# Various optimizations multiply the code paths by which these are
# called, so test a variety of calling conventions.
for py_name, py_args, c_name, expected_frame_number in (
('gmtime', '', 'time_gmtime', 1), # METH_VARARGS
('len', '[]', 'builtin_len', 2), # METH_O
('locals', '', 'builtin_locals', 2), # METH_NOARGS
('iter', '[]', 'builtin_iter', 2), # METH_FASTCALL
('sorted', '[]', 'builtin_sorted', 2), # METH_FASTCALL|METH_KEYWORDS
):
with self.subTest(c_name):
cmd = ('from time import gmtime\n' # (not always needed)
'def foo():\n'
f' {py_name}({py_args})\n'
'def bar():\n'
' foo()\n'
'bar()\n')
# Verify with "py-bt":
gdb_output = self.get_stack_trace(
cmd,
breakpoint=c_name,
cmds_after_breakpoint=['bt', 'py-bt'],
)
self.assertIn(f'<built-in method {py_name}', gdb_output)
# Verify with "py-bt-full":
gdb_output = self.get_stack_trace(cmd,
breakpoint='time_gmtime',
cmds_after_breakpoint=['py-bt-full'],
)
self.assertIn('#1 <built-in method gmtime', gdb_output)
# Verify with "py-bt-full":
gdb_output = self.get_stack_trace(
cmd,
breakpoint=c_name,
cmds_after_breakpoint=['py-bt-full'],
)
self.assertIn(
f'#{expected_frame_number} <built-in method {py_name}',
gdb_output,
)
@unittest.skipIf(python_is_optimized(),
"Python was compiled with optimizations")