diff --git a/Python/ceval.c b/Python/ceval.c index 1b8650a650412dc..20623fab77749c9 100644 --- a/Python/ceval.c +++ b/Python/ceval.c @@ -2767,6 +2767,13 @@ _PyUopExecute(_PyExecutorObject *executor, _PyInterpreterFrame *frame, PyObject #define ENABLE_SPECIALIZATION 0 #include "executor_cases.c.h" + case JUMP_TO_TOP: + { + pc = 0; + CHECK_EVAL_BREAKER(); + break; + } + case SAVE_IP: { frame->prev_instr = ip_offset + oparg; diff --git a/Python/opcode_metadata.h b/Python/opcode_metadata.h index 70e1ca44ce76632..75a188a0013fd68 100644 --- a/Python/opcode_metadata.h +++ b/Python/opcode_metadata.h @@ -21,18 +21,19 @@ #define EXIT_TRACE 300 #define SAVE_IP 301 -#define _GUARD_BOTH_INT 302 -#define _BINARY_OP_MULTIPLY_INT 303 -#define _BINARY_OP_ADD_INT 304 -#define _BINARY_OP_SUBTRACT_INT 305 -#define _GUARD_BOTH_FLOAT 306 -#define _BINARY_OP_MULTIPLY_FLOAT 307 -#define _BINARY_OP_ADD_FLOAT 308 -#define _BINARY_OP_SUBTRACT_FLOAT 309 -#define _GUARD_BOTH_UNICODE 310 -#define _BINARY_OP_ADD_UNICODE 311 -#define _LOAD_LOCALS 312 -#define _LOAD_FROM_DICT_OR_GLOBALS 313 +#define JUMP_TO_TOP 302 +#define _GUARD_BOTH_INT 303 +#define _BINARY_OP_MULTIPLY_INT 304 +#define _BINARY_OP_ADD_INT 305 +#define _BINARY_OP_SUBTRACT_INT 306 +#define _GUARD_BOTH_FLOAT 307 +#define _BINARY_OP_MULTIPLY_FLOAT 308 +#define _BINARY_OP_ADD_FLOAT 309 +#define _BINARY_OP_SUBTRACT_FLOAT 310 +#define _GUARD_BOTH_UNICODE 311 +#define _BINARY_OP_ADD_UNICODE 312 +#define _LOAD_LOCALS 313 +#define _LOAD_FROM_DICT_OR_GLOBALS 314 #ifndef NEED_OPCODE_METADATA extern int _PyOpcode_num_popped(int opcode, int oparg, bool jump); @@ -1284,18 +1285,19 @@ const struct opcode_macro_expansion _PyOpcode_macro_expansion[256] = { const char * const _PyOpcode_uop_name[512] = { [300] = "EXIT_TRACE", [301] = "SAVE_IP", - [302] = "_GUARD_BOTH_INT", - [303] = "_BINARY_OP_MULTIPLY_INT", - [304] = "_BINARY_OP_ADD_INT", - [305] = "_BINARY_OP_SUBTRACT_INT", - [306] = "_GUARD_BOTH_FLOAT", - [307] = "_BINARY_OP_MULTIPLY_FLOAT", - [308] = "_BINARY_OP_ADD_FLOAT", - [309] = "_BINARY_OP_SUBTRACT_FLOAT", - [310] = "_GUARD_BOTH_UNICODE", - [311] = "_BINARY_OP_ADD_UNICODE", - [312] = "_LOAD_LOCALS", - [313] = "_LOAD_FROM_DICT_OR_GLOBALS", + [302] = "JUMP_TO_TOP", + [303] = "_GUARD_BOTH_INT", + [304] = "_BINARY_OP_MULTIPLY_INT", + [305] = "_BINARY_OP_ADD_INT", + [306] = "_BINARY_OP_SUBTRACT_INT", + [307] = "_GUARD_BOTH_FLOAT", + [308] = "_BINARY_OP_MULTIPLY_FLOAT", + [309] = "_BINARY_OP_ADD_FLOAT", + [310] = "_BINARY_OP_SUBTRACT_FLOAT", + [311] = "_GUARD_BOTH_UNICODE", + [312] = "_BINARY_OP_ADD_UNICODE", + [313] = "_LOAD_LOCALS", + [314] = "_LOAD_FROM_DICT_OR_GLOBALS", }; #endif // NEED_OPCODE_METADATA #endif diff --git a/Python/optimizer.c b/Python/optimizer.c index 1d731ed2309c3c6..b0f05a7cb7e2e01 100644 --- a/Python/optimizer.c +++ b/Python/optimizer.c @@ -426,6 +426,18 @@ translate_bytecode_to_trace( oparg = (oparg & 0xffffff00) | executor->vm_data.oparg; } switch (opcode) { + case JUMP_BACKWARD: + { + if (instr + 2 - oparg == initial_instr + && trace_length + 3 <= max_length) + { + ADD_TO_TRACE(JUMP_TO_TOP, 0); + } + else { + DPRINTF(2, "JUMP_BACKWARD not to top ends trace\n"); + } + goto done; + } default: { const struct opcode_macro_expansion *expansion = &_PyOpcode_macro_expansion[opcode]; diff --git a/Tools/cases_generator/generate_cases.py b/Tools/cases_generator/generate_cases.py index 14269ca8cbe750b..e2ec7f45348da48 100644 --- a/Tools/cases_generator/generate_cases.py +++ b/Tools/cases_generator/generate_cases.py @@ -1344,6 +1344,7 @@ def add(name: str) -> None: counter += 1 add("EXIT_TRACE") add("SAVE_IP") + add("JUMP_TO_TOP") for instr in self.instrs.values(): if instr.kind == "op" and instr.is_viable_uop(): add(instr.name)