Skip to content

Commit e4e7507

Browse files
committed
Revert "builder: emitCallExceptionHandler → C orchestrator (W27c #2b Cat B)"
This reverts commit 7329403.
1 parent 7329403 commit e4e7507

2 files changed

Lines changed: 58 additions & 22 deletions

File tree

Python/jit/hir/builder.cpp

Lines changed: 55 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1326,10 +1326,18 @@ bool HIRBuilder::getSimpleExceptInfo(
13261326
return true;
13271327
}
13281328

1329-
// W27c #2a + #2b: OpcodeArrayEntry C++/C bridge struct eliminated. The
1330-
// pre-resolve loop now runs entirely C-side via
1331-
// build_inline_except_opcode_array_c in builder_emit_c.c, sharing the
1332-
// helper between emitInlineExceptionMatch and emitCallExceptionHandler.
1329+
// OpcodeArrayEntry — mirror of the C-side struct in builder_emit_c.c.
1330+
// 5 fields per entry. Layout MUST match (verified via static_assert).
1331+
struct OpcodeArrayEntry_CXX {
1332+
int opcode;
1333+
int oparg;
1334+
int base_offset;
1335+
void* const_obj;
1336+
void* jump_target_block;
1337+
};
1338+
static_assert(sizeof(OpcodeArrayEntry_CXX) <= 64,
1339+
"OpcodeArrayEntry size sanity");
1340+
13331341
extern "C" void hir_builder_emit_inline_exception_match_c(
13341342
void* tc, void* func, void* builder,
13351343
int bc_base_offset,
@@ -1383,7 +1391,9 @@ extern "C" void hir_builder_emit_call_exception_handler_c(
13831391
int except_body_offset,
13841392
HirType return_type,
13851393
void* result,
1386-
void* match_and_clear_fn);
1394+
void* match_and_clear_fn,
1395+
const OpcodeArrayEntry_CXX* opcodes,
1396+
size_t opcode_count);
13871397

13881398
void HIRBuilder::emitCallExceptionHandler(
13891399
CFG& /*cfg*/,
@@ -1399,12 +1409,46 @@ void HIRBuilder::emitCallExceptionHandler(
13991409
// preserved for Simplify, register allocation, other deopt paths.
14001410
// 2. Pop the result that emitAnyCall pushed onto the stack — the C
14011411
// body's deopt path expects a clean stack at the CALL offset.
1402-
// W27c #2b: pre-resolve opcode array now built C-side via
1403-
// build_inline_except_opcode_array_c (shared with W27c #2a
1404-
// emitInlineExceptionMatch).
14051412
call_instr->setSuppressExceptionDeopt(true);
14061413
static_cast<Register*>(phx_ptr_arr_pop(&tc.frame.stack));
14071414

1415+
// Build OpcodeArray identical-shape to emitInlineExceptionMatch — the
1416+
// dispatch loop in the shared C helper expects this layout. Pre-resolves
1417+
// const_obj (LOAD_CONST/RETURN_CONST) + jump_target_block (JUMP_BACKWARD*)
1418+
// to keep PyCodeObject + getBlockAtOff access on the C++ side.
1419+
std::vector<OpcodeArrayEntry_CXX> opcodes;
1420+
BytecodeInstruction ebc{code_, info.except_body};
1421+
bool emitted_terminator = false;
1422+
while (!emitted_terminator) {
1423+
OpcodeArrayEntry_CXX entry{
1424+
ebc.opcode(),
1425+
ebc.oparg(),
1426+
ebc.baseOffset().value(),
1427+
nullptr,
1428+
nullptr};
1429+
int op = entry.opcode;
1430+
if (op == LOAD_CONST || op == RETURN_CONST) {
1431+
entry.const_obj = PyTuple_GET_ITEM(code_->co_consts, entry.oparg);
1432+
}
1433+
if (op == JUMP_BACKWARD || op == JUMP_BACKWARD_NO_INTERRUPT) {
1434+
entry.jump_target_block =
1435+
static_cast<void*>(getBlockAtOff(ebc.getJumpTarget()));
1436+
}
1437+
if (op == RETURN_VALUE || op == RETURN_CONST
1438+
|| op == JUMP_BACKWARD || op == JUMP_BACKWARD_NO_INTERRUPT) {
1439+
emitted_terminator = true;
1440+
} else if (op != POP_EXCEPT && op != POP_TOP && op != SWAP
1441+
&& op != LOAD_FAST && op != LOAD_FAST_CHECK
1442+
&& op != LOAD_FAST_AND_CLEAR && op != LOAD_CONST
1443+
&& op != STORE_FAST && op != BINARY_OP) {
1444+
emitted_terminator = true;
1445+
}
1446+
opcodes.push_back(entry);
1447+
if (!emitted_terminator) {
1448+
ebc = ebc.nextInstr();
1449+
}
1450+
}
1451+
14081452
hir_builder_emit_call_exception_handler_c(
14091453
static_cast<void*>(&tc),
14101454
static_cast<void*>(current_func_),
@@ -1415,7 +1459,9 @@ void HIRBuilder::emitCallExceptionHandler(
14151459
info.except_body.value(),
14161460
Type::toHirType(preloader_.returnType()),
14171461
static_cast<void*>(result),
1418-
reinterpret_cast<void*>(JITRT_MatchAndClearException));
1462+
reinterpret_cast<void*>(JITRT_MatchAndClearException),
1463+
opcodes.data(),
1464+
opcodes.size());
14191465
}
14201466

14211467
BasicBlock* HIRBuilder::getBlockAtOff(BCOffset off) {

Python/jit/hir/builder_emit_c.c

Lines changed: 3 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -3568,23 +3568,15 @@ void hir_builder_emit_call_exception_handler_c(
35683568
int except_body_offset,
35693569
HirType return_type,
35703570
void *result,
3571-
void *match_and_clear_fn) {
3571+
void *match_and_clear_fn,
3572+
const OpcodeArrayEntry *opcodes,
3573+
size_t opcode_count) {
35723574
HirType t_object = HIR_TYPE_OBJECT;
35733575

35743576
/* (D1) Pre-amble (setSuppressExceptionDeopt + pop result) is done on
35753577
* the C++ stub side BEFORE this C body — see builder.cpp emitter.
35763578
* The C body's first action is the ok/exc branch on result. */
35773579

3578-
/* W27c #2b: pre-resolve opcode array C-side (was C++ stub). Shares
3579-
* the helper with hir_builder_emit_inline_exception_match_c (W27c #2a).
3580-
* code accessible via tc->frame.code (set by frame init in
3581-
* hir_builder_state_emit_phase). */
3582-
OpcodeArrayEntry *opcodes = NULL;
3583-
size_t opcode_count = 0;
3584-
build_inline_except_opcode_array_c(
3585-
(PyCodeObject*)tc->frame.code, builder, except_body_offset,
3586-
&opcodes, &opcode_count);
3587-
35883580
void *ok_block = hir_cfg_alloc_block(func);
35893581
void *exc_match_block = hir_cfg_alloc_block(func);
35903582
phx_tc_emit(tc, hir_c_create_cond_branch_cpp(result, ok_block, exc_match_block));
@@ -3605,8 +3597,6 @@ void hir_builder_emit_call_exception_handler_c(
36053597
tc->block = ok_block;
36063598
phx_tc_emit(tc, hir_c_create_refine_type_reg(result, t_object, result));
36073599
phx_ptr_arr_push(&tc->frame.stack, result);
3608-
3609-
PyMem_RawFree(opcodes);
36103600
}
36113601

36123602
/* emitAnyCall full conversion — W26 (theologian L2462+L2466).

0 commit comments

Comments
 (0)