From 04e07c258f4f2ac85e25355242a113f98a706f04 Mon Sep 17 00:00:00 2001 From: Irit Katriel <1055913+iritkatriel@users.noreply.github.com> Date: Fri, 1 Apr 2022 13:59:38 +0100 Subject: bpo-47186: Replace JUMP_IF_NOT_EXC_MATCH by CHECK_EXC_MATCH + jump (GH-32231) --- Doc/library/dis.rst | 18 ++--- Doc/whatsnew/3.11.rst | 3 +- Include/opcode.h | 72 +++++++++--------- Lib/importlib/_bootstrap_external.py | 3 +- Lib/opcode.py | 2 +- Lib/test/test_dis.py | 85 +++++++++++----------- .../2022-04-01-11-53-59.bpo-47186.RBCPk8.rst | 1 + Objects/frameobject.c | 4 +- Python/ceval.c | 6 +- Python/compile.c | 10 ++- Python/opcode_targets.h | 14 ++-- 11 files changed, 107 insertions(+), 111 deletions(-) create mode 100644 Misc/NEWS.d/next/Core and Builtins/2022-04-01-11-53-59.bpo-47186.RBCPk8.rst diff --git a/Doc/library/dis.rst b/Doc/library/dis.rst index d1a0cec..b364e3f 100644 --- a/Doc/library/dis.rst +++ b/Doc/library/dis.rst @@ -628,6 +628,12 @@ iterations of the loop. .. versionadded:: 3.11 +.. opcode:: CHECK_EXC_MATCH + + Performs exception matching for ``except``. Tests whether the TOS1 is an exception + matching TOS. Pops TOS and pushes the boolean result of the test. + + .. versionadded:: 3.11 .. opcode:: WITH_EXCEPT_START @@ -916,18 +922,6 @@ iterations of the loop. .. versionadded:: 3.1 -.. opcode:: JUMP_IF_NOT_EXC_MATCH (target) - - Performs exception matching for ``except``. - Tests whether the second value on the stack is an exception matching TOS, - and jumps if it is not. Pops one value from the stack. - - .. versionadded:: 3.9 - - .. versionchanged:: 3.11 - This opcode no longer pops the active exception. - - .. opcode:: JUMP_IF_NOT_EG_MATCH (target) Performs exception matching for ``except*``. Applies ``split(TOS)`` on diff --git a/Doc/whatsnew/3.11.rst b/Doc/whatsnew/3.11.rst index 1580867..dc2d4b0 100644 --- a/Doc/whatsnew/3.11.rst +++ b/Doc/whatsnew/3.11.rst @@ -520,7 +520,8 @@ CPython bytecode changes * Add :opcode:`POP_JUMP_IF_NOT_NONE` and :opcode:`POP_JUMP_IF_NONE` opcodes to speed up conditional jumps. -* :opcode:`JUMP_IF_NOT_EXC_MATCH` no longer pops the active exception. +* Replaced :opcode:`JUMP_IF_NOT_EXC_MATCH` by :opcode:`CHECK_EXC_MATCH` which + performs the check but does not jump. * Replaced :opcode:`JUMP_ABSOLUTE` by the relative :opcode:`JUMP_BACKWARD`. diff --git a/Include/opcode.h b/Include/opcode.h index 3a7db43..c82d1fd 100644 --- a/Include/opcode.h +++ b/Include/opcode.h @@ -21,6 +21,7 @@ extern "C" { #define MATCH_SEQUENCE 32 #define MATCH_KEYS 33 #define PUSH_EXC_INFO 35 +#define CHECK_EXC_MATCH 36 #define WITH_EXCEPT_START 49 #define GET_AITER 50 #define GET_ANEXT 51 @@ -74,7 +75,6 @@ extern "C" { #define CONTAINS_OP 118 #define RERAISE 119 #define COPY 120 -#define JUMP_IF_NOT_EXC_MATCH 121 #define BINARY_OP 122 #define SEND 123 #define LOAD_FAST 124 @@ -136,39 +136,39 @@ extern "C" { #define COMPARE_OP_INT_JUMP 28 #define COMPARE_OP_STR_JUMP 29 #define JUMP_BACKWARD_QUICK 34 -#define LOAD_ATTR_ADAPTIVE 36 -#define LOAD_ATTR_INSTANCE_VALUE 37 -#define LOAD_ATTR_MODULE 38 -#define LOAD_ATTR_SLOT 39 -#define LOAD_ATTR_WITH_HINT 40 -#define LOAD_CONST__LOAD_FAST 41 -#define LOAD_FAST__LOAD_CONST 42 -#define LOAD_FAST__LOAD_FAST 43 -#define LOAD_GLOBAL_ADAPTIVE 44 -#define LOAD_GLOBAL_BUILTIN 45 -#define LOAD_GLOBAL_MODULE 46 -#define LOAD_METHOD_ADAPTIVE 47 -#define LOAD_METHOD_CLASS 48 -#define LOAD_METHOD_MODULE 55 -#define LOAD_METHOD_NO_DICT 56 -#define LOAD_METHOD_WITH_DICT 57 -#define LOAD_METHOD_WITH_VALUES 58 -#define PRECALL_ADAPTIVE 59 -#define PRECALL_BOUND_METHOD 62 -#define PRECALL_BUILTIN_CLASS 63 -#define PRECALL_BUILTIN_FAST_WITH_KEYWORDS 64 -#define PRECALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS 65 -#define PRECALL_NO_KW_BUILTIN_FAST 66 -#define PRECALL_NO_KW_BUILTIN_O 67 -#define PRECALL_NO_KW_ISINSTANCE 72 -#define PRECALL_NO_KW_LEN 73 -#define PRECALL_NO_KW_LIST_APPEND 76 -#define PRECALL_NO_KW_METHOD_DESCRIPTOR_FAST 77 -#define PRECALL_NO_KW_METHOD_DESCRIPTOR_NOARGS 78 -#define PRECALL_NO_KW_METHOD_DESCRIPTOR_O 79 -#define PRECALL_NO_KW_STR_1 80 -#define PRECALL_NO_KW_TUPLE_1 81 -#define PRECALL_NO_KW_TYPE_1 113 +#define LOAD_ATTR_ADAPTIVE 37 +#define LOAD_ATTR_INSTANCE_VALUE 38 +#define LOAD_ATTR_MODULE 39 +#define LOAD_ATTR_SLOT 40 +#define LOAD_ATTR_WITH_HINT 41 +#define LOAD_CONST__LOAD_FAST 42 +#define LOAD_FAST__LOAD_CONST 43 +#define LOAD_FAST__LOAD_FAST 44 +#define LOAD_GLOBAL_ADAPTIVE 45 +#define LOAD_GLOBAL_BUILTIN 46 +#define LOAD_GLOBAL_MODULE 47 +#define LOAD_METHOD_ADAPTIVE 48 +#define LOAD_METHOD_CLASS 55 +#define LOAD_METHOD_MODULE 56 +#define LOAD_METHOD_NO_DICT 57 +#define LOAD_METHOD_WITH_DICT 58 +#define LOAD_METHOD_WITH_VALUES 59 +#define PRECALL_ADAPTIVE 62 +#define PRECALL_BOUND_METHOD 63 +#define PRECALL_BUILTIN_CLASS 64 +#define PRECALL_BUILTIN_FAST_WITH_KEYWORDS 65 +#define PRECALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS 66 +#define PRECALL_NO_KW_BUILTIN_FAST 67 +#define PRECALL_NO_KW_BUILTIN_O 72 +#define PRECALL_NO_KW_ISINSTANCE 73 +#define PRECALL_NO_KW_LEN 76 +#define PRECALL_NO_KW_LIST_APPEND 77 +#define PRECALL_NO_KW_METHOD_DESCRIPTOR_FAST 78 +#define PRECALL_NO_KW_METHOD_DESCRIPTOR_NOARGS 79 +#define PRECALL_NO_KW_METHOD_DESCRIPTOR_O 80 +#define PRECALL_NO_KW_STR_1 81 +#define PRECALL_NO_KW_TUPLE_1 113 +#define PRECALL_NO_KW_TYPE_1 121 #define PRECALL_PYFUNC 141 #define RESUME_QUICK 143 #define STORE_ATTR_ADAPTIVE 150 @@ -205,7 +205,7 @@ static const uint32_t _PyOpcode_Jump[8] = { 0U, 0U, 536870912U, - 2316156928U, + 2282602496U, 4163U, 0U, 0U, @@ -259,6 +259,7 @@ const uint8_t _PyOpcode_Deopt[256] = { [CALL_FUNCTION_EX] = CALL_FUNCTION_EX, [CALL_PY_EXACT_ARGS] = CALL, [CALL_PY_WITH_DEFAULTS] = CALL, + [CHECK_EXC_MATCH] = CHECK_EXC_MATCH, [COMPARE_OP] = COMPARE_OP, [COMPARE_OP_ADAPTIVE] = COMPARE_OP, [COMPARE_OP_FLOAT_JUMP] = COMPARE_OP, @@ -294,7 +295,6 @@ const uint8_t _PyOpcode_Deopt[256] = { [JUMP_FORWARD] = JUMP_FORWARD, [JUMP_IF_FALSE_OR_POP] = JUMP_IF_FALSE_OR_POP, [JUMP_IF_NOT_EG_MATCH] = JUMP_IF_NOT_EG_MATCH, - [JUMP_IF_NOT_EXC_MATCH] = JUMP_IF_NOT_EXC_MATCH, [JUMP_IF_TRUE_OR_POP] = JUMP_IF_TRUE_OR_POP, [JUMP_NO_INTERRUPT] = JUMP_NO_INTERRUPT, [KW_NAMES] = KW_NAMES, diff --git a/Lib/importlib/_bootstrap_external.py b/Lib/importlib/_bootstrap_external.py index 744fefd..39a348a 100644 --- a/Lib/importlib/_bootstrap_external.py +++ b/Lib/importlib/_bootstrap_external.py @@ -397,6 +397,7 @@ _code_type = type(_write_atomic.__code__) # Python 3.11a6 3487 (Remove the adaptive "oparg counter" mechanism) # Python 3.11a6 3488 (LOAD_GLOBAL can push additional NULL) # Python 3.11a6 3489 (Add JUMP_BACKWARD, remove JUMP_ABSOLUTE) +# Python 3.11a6 3490 (remove JUMP_IF_NOT_EXC_MATCH, add CHECK_EXC_MATCH) # Python 3.12 will start with magic number 3500 @@ -411,7 +412,7 @@ _code_type = type(_write_atomic.__code__) # Whenever MAGIC_NUMBER is changed, the ranges in the magic_values array # in PC/launcher.c must also be updated. -MAGIC_NUMBER = (3489).to_bytes(2, 'little') + b'\r\n' +MAGIC_NUMBER = (3490).to_bytes(2, 'little') + b'\r\n' _RAW_MAGIC_NUMBER = int.from_bytes(MAGIC_NUMBER, 'little') # For import.c _PYCACHE = '__pycache__' diff --git a/Lib/opcode.py b/Lib/opcode.py index 6bc6417..e993a5c 100644 --- a/Lib/opcode.py +++ b/Lib/opcode.py @@ -76,6 +76,7 @@ def_op('MATCH_SEQUENCE', 32) def_op('MATCH_KEYS', 33) def_op('PUSH_EXC_INFO', 35) +def_op('CHECK_EXC_MATCH', 36) def_op('WITH_EXCEPT_START', 49) def_op('GET_AITER', 50) @@ -138,7 +139,6 @@ def_op('IS_OP', 117) def_op('CONTAINS_OP', 118) def_op('RERAISE', 119) def_op('COPY', 120) -jabs_op('JUMP_IF_NOT_EXC_MATCH', 121) def_op('BINARY_OP', 122, 1) jrel_op('SEND', 123) # Number of bytes to skip def_op('LOAD_FAST', 124) # Local variable number diff --git a/Lib/test/test_dis.py b/Lib/test/test_dis.py index 99db8ba..544e135 100644 --- a/Lib/test/test_dis.py +++ b/Lib/test/test_dis.py @@ -372,7 +372,8 @@ dis_traceback = """\ >> PUSH_EXC_INFO %3d LOAD_GLOBAL 0 (Exception) - JUMP_IF_NOT_EXC_MATCH 35 (to 70) + CHECK_EXC_MATCH + POP_JUMP_IF_FALSE 36 (to 72) STORE_FAST 0 (e) %3d LOAD_FAST 0 (e) @@ -683,8 +684,7 @@ class DisTests(DisTestBase): def test_widths(self): for opcode, opname in enumerate(dis.opname): if opname in ('BUILD_MAP_UNPACK_WITH_CALL', - 'BUILD_TUPLE_UNPACK_WITH_CALL', - 'JUMP_IF_NOT_EXC_MATCH'): + 'BUILD_TUPLE_UNPACK_WITH_CALL'): continue with self.subTest(opname=opname): width = dis._OPNAME_WIDTH @@ -1299,47 +1299,48 @@ expected_opinfo_jumpy = [ Instruction(opname='POP_EXCEPT', opcode=89, arg=None, argval=None, argrepr='', offset=322, starts_line=None, is_jump_target=False, positions=None), Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=324, starts_line=None, is_jump_target=False, positions=None), Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=326, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='JUMP_FORWARD', opcode=110, arg=30, argval=390, argrepr='to 390', offset=328, starts_line=None, is_jump_target=True, positions=None), + Instruction(opname='JUMP_FORWARD', opcode=110, arg=31, argval=392, argrepr='to 392', offset=328, starts_line=None, is_jump_target=True, positions=None), Instruction(opname='PUSH_EXC_INFO', opcode=35, arg=None, argval=None, argrepr='', offset=330, starts_line=None, is_jump_target=False, positions=None), Instruction(opname='LOAD_GLOBAL', opcode=116, arg=4, argval='ZeroDivisionError', argrepr='ZeroDivisionError', offset=332, starts_line=22, is_jump_target=False, positions=None), - Instruction(opname='JUMP_IF_NOT_EXC_MATCH', opcode=121, arg=191, argval=382, argrepr='to 382', offset=344, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=346, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=348, starts_line=23, is_jump_target=False, positions=None), - Instruction(opname='LOAD_CONST', opcode=100, arg=9, argval='Here we go, here we go, here we go...', argrepr="'Here we go, here we go, here we go...'", offset=360, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=362, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=366, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=376, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_EXCEPT', opcode=89, arg=None, argval=None, argrepr='', offset=378, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='JUMP_FORWARD', opcode=110, arg=21, argval=424, argrepr='to 424', offset=380, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='RERAISE', opcode=119, arg=0, argval=0, argrepr='', offset=382, starts_line=22, is_jump_target=True, positions=None), - Instruction(opname='COPY', opcode=120, arg=3, argval=3, argrepr='', offset=384, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_EXCEPT', opcode=89, arg=None, argval=None, argrepr='', offset=386, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='RERAISE', opcode=119, arg=1, argval=1, argrepr='', offset=388, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=390, starts_line=28, is_jump_target=True, positions=None), - Instruction(opname='LOAD_CONST', opcode=100, arg=10, argval="OK, now we're done", argrepr='"OK, now we\'re done"', offset=402, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=404, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=408, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=418, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='LOAD_CONST', opcode=100, arg=0, argval=None, argrepr='None', offset=420, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='RETURN_VALUE', opcode=83, arg=None, argval=None, argrepr='', offset=422, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='NOP', opcode=9, arg=None, argval=None, argrepr='', offset=424, starts_line=23, is_jump_target=True, positions=None), - Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=426, starts_line=28, is_jump_target=False, positions=None), - Instruction(opname='LOAD_CONST', opcode=100, arg=10, argval="OK, now we're done", argrepr='"OK, now we\'re done"', offset=438, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=440, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=444, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=454, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='LOAD_CONST', opcode=100, arg=0, argval=None, argrepr='None', offset=456, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='RETURN_VALUE', opcode=83, arg=None, argval=None, argrepr='', offset=458, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='PUSH_EXC_INFO', opcode=35, arg=None, argval=None, argrepr='', offset=460, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=462, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='LOAD_CONST', opcode=100, arg=10, argval="OK, now we're done", argrepr='"OK, now we\'re done"', offset=474, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=476, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=480, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=490, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='RERAISE', opcode=119, arg=0, argval=0, argrepr='', offset=492, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='COPY', opcode=120, arg=3, argval=3, argrepr='', offset=494, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='POP_EXCEPT', opcode=89, arg=None, argval=None, argrepr='', offset=496, starts_line=None, is_jump_target=False, positions=None), - Instruction(opname='RERAISE', opcode=119, arg=1, argval=1, argrepr='', offset=498, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='CHECK_EXC_MATCH', opcode=36, arg=None, argval=None, argrepr='', offset=344, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_JUMP_IF_FALSE', opcode=114, arg=192, argval=384, argrepr='to 384', offset=346, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=348, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=350, starts_line=23, is_jump_target=False, positions=None), + Instruction(opname='LOAD_CONST', opcode=100, arg=9, argval='Here we go, here we go, here we go...', argrepr="'Here we go, here we go, here we go...'", offset=362, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=364, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=368, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=378, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_EXCEPT', opcode=89, arg=None, argval=None, argrepr='', offset=380, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='JUMP_FORWARD', opcode=110, arg=21, argval=426, argrepr='to 426', offset=382, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='RERAISE', opcode=119, arg=0, argval=0, argrepr='', offset=384, starts_line=22, is_jump_target=True, positions=None), + Instruction(opname='COPY', opcode=120, arg=3, argval=3, argrepr='', offset=386, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_EXCEPT', opcode=89, arg=None, argval=None, argrepr='', offset=388, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='RERAISE', opcode=119, arg=1, argval=1, argrepr='', offset=390, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=392, starts_line=28, is_jump_target=True, positions=None), + Instruction(opname='LOAD_CONST', opcode=100, arg=10, argval="OK, now we're done", argrepr='"OK, now we\'re done"', offset=404, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=406, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=410, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=420, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='LOAD_CONST', opcode=100, arg=0, argval=None, argrepr='None', offset=422, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='RETURN_VALUE', opcode=83, arg=None, argval=None, argrepr='', offset=424, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='NOP', opcode=9, arg=None, argval=None, argrepr='', offset=426, starts_line=23, is_jump_target=True, positions=None), + Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=428, starts_line=28, is_jump_target=False, positions=None), + Instruction(opname='LOAD_CONST', opcode=100, arg=10, argval="OK, now we're done", argrepr='"OK, now we\'re done"', offset=440, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=442, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=446, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=456, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='LOAD_CONST', opcode=100, arg=0, argval=None, argrepr='None', offset=458, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='RETURN_VALUE', opcode=83, arg=None, argval=None, argrepr='', offset=460, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='PUSH_EXC_INFO', opcode=35, arg=None, argval=None, argrepr='', offset=462, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='LOAD_GLOBAL', opcode=116, arg=3, argval='print', argrepr='NULL + print', offset=464, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='LOAD_CONST', opcode=100, arg=10, argval="OK, now we're done", argrepr='"OK, now we\'re done"', offset=476, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='PRECALL', opcode=166, arg=1, argval=1, argrepr='', offset=478, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='CALL', opcode=171, arg=1, argval=1, argrepr='', offset=482, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_TOP', opcode=1, arg=None, argval=None, argrepr='', offset=492, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='RERAISE', opcode=119, arg=0, argval=0, argrepr='', offset=494, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='COPY', opcode=120, arg=3, argval=3, argrepr='', offset=496, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='POP_EXCEPT', opcode=89, arg=None, argval=None, argrepr='', offset=498, starts_line=None, is_jump_target=False, positions=None), + Instruction(opname='RERAISE', opcode=119, arg=1, argval=1, argrepr='', offset=500, starts_line=None, is_jump_target=False, positions=None), ] # One last piece of inspect fodder to check the default line number handling diff --git a/Misc/NEWS.d/next/Core and Builtins/2022-04-01-11-53-59.bpo-47186.RBCPk8.rst b/Misc/NEWS.d/next/Core and Builtins/2022-04-01-11-53-59.bpo-47186.RBCPk8.rst new file mode 100644 index 0000000..002da2b --- /dev/null +++ b/Misc/NEWS.d/next/Core and Builtins/2022-04-01-11-53-59.bpo-47186.RBCPk8.rst @@ -0,0 +1 @@ +Replace :opcode:`JUMP_IF_NOT_EXC_MATCH` by :opcode:`CHECK_EXC_MATCH` + jump. diff --git a/Objects/frameobject.c b/Objects/frameobject.c index 581de22..fe374bf 100644 --- a/Objects/frameobject.c +++ b/Objects/frameobject.c @@ -207,7 +207,6 @@ mark_stacks(PyCodeObject *code_obj, int len) case JUMP_IF_TRUE_OR_POP: case POP_JUMP_IF_FALSE: case POP_JUMP_IF_TRUE: - case JUMP_IF_NOT_EXC_MATCH: case JUMP_IF_NOT_EG_MATCH: { int64_t target_stack; @@ -216,8 +215,7 @@ mark_stacks(PyCodeObject *code_obj, int len) if (stacks[j] == UNINITIALIZED && j < i) { todo = 1; } - if (opcode == JUMP_IF_NOT_EXC_MATCH || - opcode == JUMP_IF_NOT_EG_MATCH) + if (opcode == JUMP_IF_NOT_EG_MATCH) { next_stack = pop_value(pop_value(next_stack)); target_stack = next_stack; diff --git a/Python/ceval.c b/Python/ceval.c index 8c1f21b..43080f8 100644 --- a/Python/ceval.c +++ b/Python/ceval.c @@ -3853,7 +3853,7 @@ handle_eval_breaker: DISPATCH(); } - TARGET(JUMP_IF_NOT_EXC_MATCH) { + TARGET(CHECK_EXC_MATCH) { PyObject *right = POP(); PyObject *left = TOP(); assert(PyExceptionInstance_Check(left)); @@ -3864,9 +3864,7 @@ handle_eval_breaker: int res = PyErr_GivenExceptionMatches(left, right); Py_DECREF(right); - if (res == 0) { - JUMPTO(oparg); - } + PUSH(Py_NewRef(res ? Py_True : Py_False)); DISPATCH(); } diff --git a/Python/compile.c b/Python/compile.c index 7a07377..bdf886b 100644 --- a/Python/compile.c +++ b/Python/compile.c @@ -977,8 +977,8 @@ stack_effect(int opcode, int oparg, int jump) case IS_OP: case CONTAINS_OP: return -1; - case JUMP_IF_NOT_EXC_MATCH: - return -1; + case CHECK_EXC_MATCH: + return 0; case JUMP_IF_NOT_EG_MATCH: return jump > 0 ? -1 : 0; case IMPORT_NAME: @@ -3352,7 +3352,8 @@ compiler_try_star_finally(struct compiler *c, stmt_ty s) [] JUMP L0 [exc] L1: ) - [exc, E1] JUMP_IF_NOT_EXC_MATCH L2 ) only if E1 + [exc, E1] CHECK_EXC_MATCH ) + [exc, bool] POP_JUMP_IF_FALSE L2 ) only if E1 [exc] (or POP if no V1) [] JUMP L0 @@ -3410,7 +3411,8 @@ compiler_try_except(struct compiler *c, stmt_ty s) return 0; if (handler->v.ExceptHandler.type) { VISIT(c, expr, handler->v.ExceptHandler.type); - ADDOP_JUMP(c, JUMP_IF_NOT_EXC_MATCH, except); + ADDOP(c, CHECK_EXC_MATCH); + ADDOP_JUMP(c, POP_JUMP_IF_FALSE, except); } if (handler->v.ExceptHandler.name) { basicblock *cleanup_end, *cleanup_body; diff --git a/Python/opcode_targets.h b/Python/opcode_targets.h index 3afaf0b..2eba553 100644 --- a/Python/opcode_targets.h +++ b/Python/opcode_targets.h @@ -35,6 +35,7 @@ static void *opcode_targets[256] = { &&TARGET_MATCH_KEYS, &&TARGET_JUMP_BACKWARD_QUICK, &&TARGET_PUSH_EXC_INFO, + &&TARGET_CHECK_EXC_MATCH, &&TARGET_LOAD_ATTR_ADAPTIVE, &&TARGET_LOAD_ATTR_INSTANCE_VALUE, &&TARGET_LOAD_ATTR_MODULE, @@ -47,40 +48,39 @@ static void *opcode_targets[256] = { &&TARGET_LOAD_GLOBAL_BUILTIN, &&TARGET_LOAD_GLOBAL_MODULE, &&TARGET_LOAD_METHOD_ADAPTIVE, - &&TARGET_LOAD_METHOD_CLASS, &&TARGET_WITH_EXCEPT_START, &&TARGET_GET_AITER, &&TARGET_GET_ANEXT, &&TARGET_BEFORE_ASYNC_WITH, &&TARGET_BEFORE_WITH, &&TARGET_END_ASYNC_FOR, + &&TARGET_LOAD_METHOD_CLASS, &&TARGET_LOAD_METHOD_MODULE, &&TARGET_LOAD_METHOD_NO_DICT, &&TARGET_LOAD_METHOD_WITH_DICT, &&TARGET_LOAD_METHOD_WITH_VALUES, - &&TARGET_PRECALL_ADAPTIVE, &&TARGET_STORE_SUBSCR, &&TARGET_DELETE_SUBSCR, + &&TARGET_PRECALL_ADAPTIVE, &&TARGET_PRECALL_BOUND_METHOD, &&TARGET_PRECALL_BUILTIN_CLASS, &&TARGET_PRECALL_BUILTIN_FAST_WITH_KEYWORDS, &&TARGET_PRECALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS, &&TARGET_PRECALL_NO_KW_BUILTIN_FAST, - &&TARGET_PRECALL_NO_KW_BUILTIN_O, &&TARGET_GET_ITER, &&TARGET_GET_YIELD_FROM_ITER, &&TARGET_PRINT_EXPR, &&TARGET_LOAD_BUILD_CLASS, + &&TARGET_PRECALL_NO_KW_BUILTIN_O, &&TARGET_PRECALL_NO_KW_ISINSTANCE, - &&TARGET_PRECALL_NO_KW_LEN, &&TARGET_LOAD_ASSERTION_ERROR, &&TARGET_RETURN_GENERATOR, + &&TARGET_PRECALL_NO_KW_LEN, &&TARGET_PRECALL_NO_KW_LIST_APPEND, &&TARGET_PRECALL_NO_KW_METHOD_DESCRIPTOR_FAST, &&TARGET_PRECALL_NO_KW_METHOD_DESCRIPTOR_NOARGS, &&TARGET_PRECALL_NO_KW_METHOD_DESCRIPTOR_O, &&TARGET_PRECALL_NO_KW_STR_1, - &&TARGET_PRECALL_NO_KW_TUPLE_1, &&TARGET_LIST_TO_TUPLE, &&TARGET_RETURN_VALUE, &&TARGET_IMPORT_STAR, @@ -112,7 +112,7 @@ static void *opcode_targets[256] = { &&TARGET_JUMP_FORWARD, &&TARGET_JUMP_IF_FALSE_OR_POP, &&TARGET_JUMP_IF_TRUE_OR_POP, - &&TARGET_PRECALL_NO_KW_TYPE_1, + &&TARGET_PRECALL_NO_KW_TUPLE_1, &&TARGET_POP_JUMP_IF_FALSE, &&TARGET_POP_JUMP_IF_TRUE, &&TARGET_LOAD_GLOBAL, @@ -120,7 +120,7 @@ static void *opcode_targets[256] = { &&TARGET_CONTAINS_OP, &&TARGET_RERAISE, &&TARGET_COPY, - &&TARGET_JUMP_IF_NOT_EXC_MATCH, + &&TARGET_PRECALL_NO_KW_TYPE_1, &&TARGET_BINARY_OP, &&TARGET_SEND, &&TARGET_LOAD_FAST, -- cgit v0.12