Skip to content

Commit d88ba72

Browse files
committed
pythongh-93678: extract 'struct cfg' from the compiler so that the CFG can be manipulated directly
1 parent a280869 commit d88ba72

File tree

1 file changed

+24
-26
lines changed

1 file changed

+24
-26
lines changed

Python/compile.c

+24-26
Original file line numberDiff line numberDiff line change
@@ -9613,8 +9613,8 @@ unpack_instruction(PyObject *instr, int *label, int *opcode, int *oparg,
96139613
return 0;
96149614
}
96159615

9616-
static basicblock *
9617-
instructions_to_cfg(PyObject *instructions)
9616+
static int
9617+
instructions_to_cfg(PyObject *instructions, cfg_builder *g)
96189618
{
96199619
assert(PyList_Check(instructions));
96209620

@@ -9623,16 +9623,17 @@ instructions_to_cfg(PyObject *instructions)
96239623
basicblock **label2block = (basicblock **)PyMem_Malloc(sizeof(basicblock *) * max_labels);
96249624
if (!label2block) {
96259625
PyErr_NoMemory();
9626+
return -1;
96269627
}
96279628
memset(label2block, 0, sizeof(basicblock *) * max_labels);
96289629

9629-
basicblock *entryblock = new_basicblock();
9630-
if (entryblock == NULL) {
9630+
g->block_list = NULL;
9631+
basicblock *block = cfg_builder_new_block(g);
9632+
if (block == NULL) {
96319633
goto error;
96329634
}
9633-
basicblock *current_block = entryblock;
9635+
g->curblock = g->cfg_entryblock = block;
96349636

9635-
bool start_new_block = false;
96369637
for (Py_ssize_t i = 0; i < num_insts; i++) {
96379638
PyObject *instr_tuple = PyList_GET_ITEM(instructions, i);
96389639
int label, opcode, oparg, target;
@@ -9642,7 +9643,7 @@ instructions_to_cfg(PyObject *instructions)
96429643
}
96439644
if (label >= max_labels || target >= max_labels) {
96449645
PyErr_SetString(PyExc_ValueError, "label is out of range");
9645-
return NULL;
9646+
goto error;
96469647
}
96479648
basicblock *new_block = NULL;
96489649
if (label > 0 && label2block[label] != NULL) {
@@ -9652,44 +9653,37 @@ instructions_to_cfg(PyObject *instructions)
96529653
*/
96539654
assert(new_block->b_iused == 0);
96549655
}
9655-
else if (start_new_block || label > 0) {
9656-
new_block = new_basicblock();
9656+
else if (label > 0) {
9657+
new_block = cfg_builder_new_block(g);
96579658
if (new_block == NULL) {
96589659
goto error;
96599660
}
9660-
if (label > 0) {
9661-
assert(label < max_labels);
9662-
label2block[label] = new_block;
9663-
}
9661+
assert(label < max_labels);
9662+
label2block[label] = new_block;
96649663
}
96659664
if (new_block) {
9666-
current_block->b_next = new_block;
9667-
current_block = new_block;
9668-
start_new_block = false;
9665+
cfg_builder_use_next_block(g, new_block);
96699666
}
96709667
basicblock *target_block = NULL;
96719668
if (target > 0) {
96729669
target_block = label2block[target];
96739670
if (target_block == NULL) {
9674-
target_block = new_basicblock();
9671+
target_block = cfg_builder_new_block(g);
96759672
if (target_block == NULL) {
96769673
goto error;
96779674
}
96789675
label2block[target] = target_block;
96799676
}
96809677
}
9681-
if (!basicblock_addop(current_block, opcode, oparg, target_block, &loc)) {
9678+
if (!cfg_builder_addop(g, opcode, oparg, target_block, loc)) {
96829679
goto error;
96839680
}
9684-
if (IS_TERMINATOR_OPCODE(opcode)) {
9685-
start_new_block = true;
9686-
}
96879681
}
96889682
PyMem_Free(label2block);
9689-
return entryblock;
9683+
return 0;
96909684
error:
96919685
PyMem_Free(label2block);
9692-
return NULL;
9686+
return -1;
96939687
}
96949688

96959689
static PyObject *
@@ -9742,16 +9736,20 @@ _PyCompile_OptimizeCfg(PyObject *instructions, PyObject *consts)
97429736
if (const_cache == NULL) {
97439737
return NULL;
97449738
}
9745-
basicblock *entryblock = instructions_to_cfg(instructions);
9746-
if (optimize_cfg(entryblock, consts, const_cache)) {
9739+
cfg_builder g;
9740+
instructions_to_cfg(instructions, &g);
9741+
9742+
if (optimize_cfg(g.cfg_entryblock, consts, const_cache)) {
97479743
goto error;
97489744
}
9749-
PyObject *optimized_instructions = cfg_to_instructions(entryblock);
9745+
PyObject *optimized_instructions = cfg_to_instructions(g.cfg_entryblock);
97509746
if (optimized_instructions == NULL) {
97519747
goto error;
97529748
}
9749+
cfg_builder_free(&g);
97539750
return PyTuple_Pack(2, optimized_instructions, consts);
97549751
error:
9752+
cfg_builder_free(&g);
97559753
return NULL;
97569754
}
97579755

0 commit comments

Comments
 (0)