Skip to content

Commit e219a26

Browse files
committed
Mark replaced uops in expansion table
1 parent 436ad9b commit e219a26

File tree

4 files changed

+27
-11
lines changed

4 files changed

+27
-11
lines changed

Include/internal/pycore_opcode_metadata.h

Lines changed: 9 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Lib/test/test_capi/test_opt.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -176,6 +176,7 @@ def f():
176176
with temporary_optimizer(opt):
177177
f()
178178
exe = get_first_executor(f)
179+
self.assertIsNotNone(exe)
179180
self.assertTrue(exe.is_valid())
180181
_testinternalcapi.invalidate_executors(f.__code__)
181182
self.assertFalse(exe.is_valid())
@@ -196,7 +197,7 @@ def testfunc(x):
196197
self.assertIsNotNone(ex)
197198
uops = {opname for opname, _, _ in ex}
198199
self.assertIn("_SET_IP", uops)
199-
self.assertIn("LOAD_FAST", uops)
200+
self.assertIn("_LOAD_FAST", uops)
200201

201202
def test_extended_arg(self):
202203
"Check EXTENDED_ARG handling in superblock creation"

Python/optimizer.c

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -633,14 +633,6 @@ translate_bytecode_to_trace(
633633
oparg += extras;
634634
}
635635
}
636-
if (_PyUOp_Replacements[uop]) {
637-
uop = _PyUOp_Replacements[uop];
638-
if (uop == _FOR_ITER_TIER_TWO) {
639-
target += 1 + INLINE_CACHE_ENTRIES_FOR_ITER + oparg + 1;
640-
assert(_PyCode_CODE(code)[target-1].op.code == END_FOR ||
641-
_PyCode_CODE(code)[target-1].op.code == INSTRUMENTED_END_FOR);
642-
}
643-
}
644636
break;
645637
case OPARG_CACHE_1:
646638
operand = read_u16(&instr[offset].cache);
@@ -661,7 +653,15 @@ translate_bytecode_to_trace(
661653
oparg = offset;
662654
assert(uop == _SAVE_RETURN_OFFSET);
663655
break;
664-
656+
case OPARG_REPLACED:
657+
uop = _PyUOp_Replacements[uop];
658+
assert(uop != 0);
659+
if (uop == _FOR_ITER_TIER_TWO) {
660+
target += 1 + INLINE_CACHE_ENTRIES_FOR_ITER + oparg + 1;
661+
assert(_PyCode_CODE(code)[target-1].op.code == END_FOR ||
662+
_PyCode_CODE(code)[target-1].op.code == INSTRUMENTED_END_FOR);
663+
}
664+
break;
665665
default:
666666
fprintf(stderr,
667667
"opcode=%d, oparg=%d; nuops=%d, i=%d; size=%d, offset=%d\n",

Tools/cases_generator/opcode_metadata_generator.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,8 @@
3535
"OPARG_TOP": 5,
3636
"OPARG_BOTTOM": 6,
3737
"OPARG_SAVE_RETURN_OFFSET": 7,
38+
# Skip 8 as the other powers of 2 are sizes
39+
"OPARG_REPLACED": 9
3840
}
3941

4042

@@ -244,6 +246,8 @@ def generate_expansion_table(
244246
# Skip specializations
245247
if "specializing" in part.annotations:
246248
continue
249+
if "replaced" in part.annotations:
250+
size = OPARG_SIZES["OPARG_REPLACED"]
247251
expansions.append((part.name, size, offset if size else 0))
248252
offset += part.size
249253
expansions_table[inst.name] = expansions
@@ -267,9 +271,11 @@ def is_viable_expansion(inst: Instruction) -> bool:
267271
"An instruction can be expanded if all its parts are viable for tier 2"
268272
for part in inst.parts:
269273
if isinstance(part, Uop):
270-
# Skip specializations
274+
# Skip specializing and replaced uops
271275
if "specializing" in part.annotations:
272276
continue
277+
if "replaced" in part.annotations:
278+
continue
273279
if part.properties.tier_one_only or not part.is_viable():
274280
return False
275281
return True

0 commit comments

Comments
 (0)