GH-91389: Fix dis position information for CACHEs (GH-93663)

This commit is contained in:
Brandt Bucher 2022-06-16 13:49:32 -07:00 committed by GitHub
parent 4f85cec9e2
commit f8e576be0a
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 58 additions and 12 deletions

View file

@ -1197,8 +1197,10 @@ class DisTests(DisTestBase):
caches = list(self.get_cached_values(quickened, adaptive))
for cache in caches:
self.assertRegex(cache, pattern)
self.assertEqual(caches.count(""), 8)
self.assertEqual(len(caches), 22)
total_caches = 22
empty_caches = 8 if adaptive and quickened else total_caches
self.assertEqual(caches.count(""), empty_caches)
self.assertEqual(len(caches), total_caches)
class DisWithFileTests(DisTests):
@ -1751,6 +1753,36 @@ class InstructionTests(InstructionTestCase):
self.assertIsNone(positions.col_offset)
self.assertIsNone(positions.end_col_offset)
@requires_debug_ranges()
def test_co_positions_with_lots_of_caches(self):
def roots(a, b, c):
d = b**2 - 4 * a * c
yield (-b - cmath.sqrt(d)) / (2 * a)
if d:
yield (-b + cmath.sqrt(d)) / (2 * a)
code = roots.__code__
ops = code.co_code[::2]
cache_opcode = opcode.opmap["CACHE"]
caches = sum(op == cache_opcode for op in ops)
non_caches = len(ops) - caches
# Make sure we have "lots of caches". If not, roots should be changed:
assert 1 / 3 <= caches / non_caches, "this test needs more caches!"
for show_caches in (False, True):
for adaptive in (False, True):
with self.subTest(f"{adaptive=}, {show_caches=}"):
co_positions = [
positions
for op, positions in zip(ops, code.co_positions(), strict=True)
if show_caches or op != cache_opcode
]
dis_positions = [
instruction.positions
for instruction in dis.get_instructions(
code, adaptive=adaptive, show_caches=show_caches
)
]
self.assertEqual(co_positions, dis_positions)
# get_instructions has its own tests above, so can rely on it to validate
# the object oriented API
class BytecodeTests(InstructionTestCase, DisTestBase):