From d20fbb8d16cba39e41b457b340f0ad2c2ffa1858 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Wed, 2 Aug 2023 17:52:29 +0800 Subject: [PATCH 01/14] gh-107557: Tier 2 abstract interpreter barebones --- .gitattributes | 1 + Include/internal/pycore_optimizer.h | 16 + Makefile.pre.in | 9 +- PCbuild/_freeze_module.vcxproj | 1 + PCbuild/_freeze_module.vcxproj.filters | 3 + PCbuild/pythoncore.vcxproj | 3 + PCbuild/pythoncore.vcxproj.filters | 9 + Python/abstract_interp_cases.c.h | 1085 +++++++++++++++++++++++ Python/optimizer.c | 8 +- Python/optimizer_analysis.c | 21 + Tools/cases_generator/generate_cases.py | 47 +- Tools/cases_generator/instructions.py | 31 + 12 files changed, 1229 insertions(+), 5 deletions(-) create mode 100644 Include/internal/pycore_optimizer.h create mode 100644 Python/abstract_interp_cases.c.h create mode 100644 Python/optimizer_analysis.c diff --git a/.gitattributes b/.gitattributes index 5d5558da711b17..e8b6b5bd7fa54f 100644 --- a/.gitattributes +++ b/.gitattributes @@ -87,6 +87,7 @@ Programs/test_frozenmain.h generated Python/Python-ast.c generated Python/executor_cases.c.h generated Python/generated_cases.c.h generated +Python/abstract_interp_cases.c.h generated Python/opcode_targets.h generated Python/stdlib_module_names.h generated Tools/peg_generator/pegen/grammar_parser.py generated diff --git a/Include/internal/pycore_optimizer.h b/Include/internal/pycore_optimizer.h new file mode 100644 index 00000000000000..3b5fa634e13972 --- /dev/null +++ b/Include/internal/pycore_optimizer.h @@ -0,0 +1,16 @@ +#ifndef Py_INTERNAL_OPTIMIZER_H +#define Py_INTERNAL_OPTIMIZER_H +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef Py_BUILD_CORE +# error "this header requires Py_BUILD_CORE define" +#endif + +extern int uop_analyze_and_optimize(struct _PyUOpInstruction *trace, int trace_len); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_INTERNAL_OPTIMIZER_H */ diff --git a/Makefile.pre.in b/Makefile.pre.in index 12409774746a30..a334aae9dec4fc 100644 --- a/Makefile.pre.in +++ b/Makefile.pre.in @@ -405,6 +405,7 @@ PYTHON_OBJS= \ Python/mysnprintf.o \ Python/mystrtoul.o \ Python/optimizer.o \ + Python/optimizer_analysis.o \ Python/pathconfig.o \ Python/preconfig.o \ Python/pyarena.o \ @@ -1562,6 +1563,7 @@ Python/ceval.o: \ Python/executor.o: \ $(srcdir)/Include/internal/pycore_opcode_metadata.h \ + $(srcdir)/Include/internal/pycore_optimizer.h \ $(srcdir)/Python/ceval_macros.h \ $(srcdir)/Python/executor_cases.c.h @@ -1570,7 +1572,12 @@ Python/flowgraph.o: \ Python/optimizer.o: \ $(srcdir)/Python/executor_cases.c.h \ - $(srcdir)/Include/internal/pycore_opcode_metadata.h + $(srcdir)/Include/internal/pycore_opcode_metadata.h \ + $(srcdir)/Include/internal/pycore_optimizer.h + +Python/optimizer_analysis.o: \ + $(srcdir)/Include/internal/pycore_opcode_metadata.h \ + $(srcdir)/Include/internal/pycore_optimizer.h Python/frozen.o: $(FROZEN_FILES_OUT) diff --git a/PCbuild/_freeze_module.vcxproj b/PCbuild/_freeze_module.vcxproj index e247637a0dfe5c..bdcf29ba44dab5 100644 --- a/PCbuild/_freeze_module.vcxproj +++ b/PCbuild/_freeze_module.vcxproj @@ -218,6 +218,7 @@ + diff --git a/PCbuild/_freeze_module.vcxproj.filters b/PCbuild/_freeze_module.vcxproj.filters index 2a0e009308022b..45333fa97f1c64 100644 --- a/PCbuild/_freeze_module.vcxproj.filters +++ b/PCbuild/_freeze_module.vcxproj.filters @@ -283,6 +283,9 @@ Source Files + + Source Files + Source Files diff --git a/PCbuild/pythoncore.vcxproj b/PCbuild/pythoncore.vcxproj index bfe59acf12a69d..b0e62864421e17 100644 --- a/PCbuild/pythoncore.vcxproj +++ b/PCbuild/pythoncore.vcxproj @@ -248,6 +248,7 @@ + @@ -279,6 +280,7 @@ + @@ -548,6 +550,7 @@ + diff --git a/PCbuild/pythoncore.vcxproj.filters b/PCbuild/pythoncore.vcxproj.filters index 0a8b0c3faf51e1..d5f61e9c5d7c89 100644 --- a/PCbuild/pythoncore.vcxproj.filters +++ b/PCbuild/pythoncore.vcxproj.filters @@ -648,6 +648,9 @@ Include\internal + + Include\internal + Include\internal @@ -732,6 +735,9 @@ Include\internal + + Include\internal + Modules\zlib @@ -1223,6 +1229,9 @@ Python + + Python + Python diff --git a/Python/abstract_interp_cases.c.h b/Python/abstract_interp_cases.c.h new file mode 100644 index 00000000000000..4b05477da45e3a --- /dev/null +++ b/Python/abstract_interp_cases.c.h @@ -0,0 +1,1085 @@ +// This file is generated by Tools/cases_generator/generate_cases.py +// from: +// Python\bytecodes.c +// Do not edit! + + case NOP: { + break; + } + + case RESUME: { + break; + } + + case INSTRUMENTED_RESUME: { + break; + } + + case LOAD_FAST_CHECK: { + STACK_GROW(1); + break; + } + + case LOAD_FAST: { + STACK_GROW(1); + break; + } + + case LOAD_FAST_AND_CLEAR: { + STACK_GROW(1); + break; + } + + case LOAD_FAST_LOAD_FAST: { + STACK_GROW(2); + break; + } + + case LOAD_CONST: { + STACK_GROW(1); + break; + } + + case STORE_FAST: { + STACK_SHRINK(1); + break; + } + + case STORE_FAST_LOAD_FAST: { + break; + } + + case STORE_FAST_STORE_FAST: { + STACK_SHRINK(2); + break; + } + + case POP_TOP: { + STACK_SHRINK(1); + break; + } + + case PUSH_NULL: { + STACK_GROW(1); + break; + } + + case INSTRUMENTED_END_FOR: { + STACK_SHRINK(2); + break; + } + + case END_SEND: { + STACK_SHRINK(1); + break; + } + + case INSTRUMENTED_END_SEND: { + STACK_SHRINK(1); + break; + } + + case UNARY_NEGATIVE: { + break; + } + + case UNARY_NOT: { + break; + } + + case TO_BOOL: { + break; + } + + case TO_BOOL_BOOL: { + break; + } + + case TO_BOOL_INT: { + break; + } + + case TO_BOOL_LIST: { + break; + } + + case TO_BOOL_NONE: { + break; + } + + case TO_BOOL_STR: { + break; + } + + case TO_BOOL_ALWAYS_TRUE: { + break; + } + + case UNARY_INVERT: { + break; + } + + case _GUARD_BOTH_INT: { + break; + } + + case _BINARY_OP_MULTIPLY_INT: { + STACK_SHRINK(1); + break; + } + + case _BINARY_OP_ADD_INT: { + STACK_SHRINK(1); + break; + } + + case _BINARY_OP_SUBTRACT_INT: { + STACK_SHRINK(1); + break; + } + + case _GUARD_BOTH_FLOAT: { + break; + } + + case _BINARY_OP_MULTIPLY_FLOAT: { + STACK_SHRINK(1); + break; + } + + case _BINARY_OP_ADD_FLOAT: { + STACK_SHRINK(1); + break; + } + + case _BINARY_OP_SUBTRACT_FLOAT: { + STACK_SHRINK(1); + break; + } + + case _GUARD_BOTH_UNICODE: { + break; + } + + case _BINARY_OP_ADD_UNICODE: { + STACK_SHRINK(1); + break; + } + + case _BINARY_OP_INPLACE_ADD_UNICODE: { + STACK_SHRINK(2); + break; + } + + case BINARY_SUBSCR: { + STACK_SHRINK(1); + break; + } + + case BINARY_SLICE: { + STACK_SHRINK(2); + break; + } + + case STORE_SLICE: { + STACK_SHRINK(4); + break; + } + + case BINARY_SUBSCR_LIST_INT: { + STACK_SHRINK(1); + break; + } + + case BINARY_SUBSCR_TUPLE_INT: { + STACK_SHRINK(1); + break; + } + + case BINARY_SUBSCR_DICT: { + STACK_SHRINK(1); + break; + } + + case BINARY_SUBSCR_GETITEM: { + STACK_SHRINK(1); + break; + } + + case LIST_APPEND: { + STACK_SHRINK(1); + break; + } + + case SET_ADD: { + STACK_SHRINK(1); + break; + } + + case STORE_SUBSCR: { + STACK_SHRINK(3); + break; + } + + case STORE_SUBSCR_LIST_INT: { + STACK_SHRINK(3); + break; + } + + case STORE_SUBSCR_DICT: { + STACK_SHRINK(3); + break; + } + + case DELETE_SUBSCR: { + STACK_SHRINK(2); + break; + } + + case CALL_INTRINSIC_1: { + break; + } + + case CALL_INTRINSIC_2: { + STACK_SHRINK(1); + break; + } + + case RAISE_VARARGS: { + STACK_SHRINK(oparg); + break; + } + + case INTERPRETER_EXIT: { + STACK_SHRINK(1); + break; + } + + case RETURN_VALUE: { + STACK_SHRINK(1); + break; + } + + case INSTRUMENTED_RETURN_VALUE: { + STACK_SHRINK(1); + break; + } + + case RETURN_CONST: { + break; + } + + case INSTRUMENTED_RETURN_CONST: { + break; + } + + case GET_AITER: { + break; + } + + case GET_ANEXT: { + STACK_GROW(1); + break; + } + + case GET_AWAITABLE: { + break; + } + + case SEND: { + break; + } + + case SEND_GEN: { + break; + } + + case INSTRUMENTED_YIELD_VALUE: { + break; + } + + case YIELD_VALUE: { + break; + } + + case POP_EXCEPT: { + STACK_SHRINK(1); + break; + } + + case RERAISE: { + STACK_SHRINK(1); + break; + } + + case END_ASYNC_FOR: { + STACK_SHRINK(2); + break; + } + + case CLEANUP_THROW: { + STACK_SHRINK(1); + break; + } + + case LOAD_ASSERTION_ERROR: { + STACK_GROW(1); + break; + } + + case LOAD_BUILD_CLASS: { + STACK_GROW(1); + break; + } + + case STORE_NAME: { + STACK_SHRINK(1); + break; + } + + case DELETE_NAME: { + break; + } + + case UNPACK_SEQUENCE: { + STACK_SHRINK(1); + STACK_GROW(oparg); + break; + } + + case UNPACK_SEQUENCE_TWO_TUPLE: { + STACK_SHRINK(1); + STACK_GROW(oparg); + break; + } + + case UNPACK_SEQUENCE_TUPLE: { + STACK_SHRINK(1); + STACK_GROW(oparg); + break; + } + + case UNPACK_SEQUENCE_LIST: { + STACK_SHRINK(1); + STACK_GROW(oparg); + break; + } + + case UNPACK_EX: { + STACK_GROW((oparg & 0xFF) + (oparg >> 8)); + break; + } + + case STORE_ATTR: { + STACK_SHRINK(2); + break; + } + + case DELETE_ATTR: { + STACK_SHRINK(1); + break; + } + + case STORE_GLOBAL: { + STACK_SHRINK(1); + break; + } + + case DELETE_GLOBAL: { + break; + } + + case _LOAD_LOCALS: { + STACK_GROW(1); + break; + } + + case _LOAD_FROM_DICT_OR_GLOBALS: { + break; + } + + case LOAD_GLOBAL: { + STACK_GROW(1); + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case _GUARD_GLOBALS_VERSION: { + break; + } + + case _GUARD_BUILTINS_VERSION: { + break; + } + + case _LOAD_GLOBAL_MODULE: { + STACK_GROW(1); + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case _LOAD_GLOBAL_BUILTINS: { + STACK_GROW(1); + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case DELETE_FAST: { + break; + } + + case MAKE_CELL: { + break; + } + + case DELETE_DEREF: { + break; + } + + case LOAD_FROM_DICT_OR_DEREF: { + break; + } + + case LOAD_DEREF: { + STACK_GROW(1); + break; + } + + case STORE_DEREF: { + STACK_SHRINK(1); + break; + } + + case COPY_FREE_VARS: { + break; + } + + case BUILD_STRING: { + STACK_SHRINK(oparg); + STACK_GROW(1); + break; + } + + case BUILD_TUPLE: { + STACK_SHRINK(oparg); + STACK_GROW(1); + break; + } + + case BUILD_LIST: { + STACK_SHRINK(oparg); + STACK_GROW(1); + break; + } + + case LIST_EXTEND: { + STACK_SHRINK(1); + break; + } + + case SET_UPDATE: { + STACK_SHRINK(1); + break; + } + + case BUILD_SET: { + STACK_SHRINK(oparg); + STACK_GROW(1); + break; + } + + case BUILD_MAP: { + STACK_SHRINK(oparg*2); + STACK_GROW(1); + break; + } + + case SETUP_ANNOTATIONS: { + break; + } + + case BUILD_CONST_KEY_MAP: { + STACK_SHRINK(oparg); + break; + } + + case DICT_UPDATE: { + STACK_SHRINK(1); + break; + } + + case DICT_MERGE: { + STACK_SHRINK(1); + break; + } + + case MAP_ADD: { + STACK_SHRINK(2); + break; + } + + case INSTRUMENTED_LOAD_SUPER_ATTR: { + STACK_SHRINK(2); + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_SUPER_ATTR: { + STACK_SHRINK(2); + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_SUPER_ATTR_ATTR: { + STACK_SHRINK(2); + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_SUPER_ATTR_METHOD: { + STACK_SHRINK(1); + break; + } + + case LOAD_ATTR: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case _GUARD_TYPE_VERSION: { + break; + } + + case _CHECK_MANAGED_OBJECT_HAS_VALUES: { + break; + } + + case _LOAD_ATTR_INSTANCE_VALUE: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_ATTR_MODULE: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_ATTR_WITH_HINT: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_ATTR_SLOT: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_ATTR_CLASS: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_ATTR_PROPERTY: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN: { + STACK_GROW(((oparg & 1) ? 1 : 0)); + break; + } + + case STORE_ATTR_INSTANCE_VALUE: { + STACK_SHRINK(2); + break; + } + + case STORE_ATTR_WITH_HINT: { + STACK_SHRINK(2); + break; + } + + case STORE_ATTR_SLOT: { + STACK_SHRINK(2); + break; + } + + case COMPARE_OP: { + STACK_SHRINK(1); + break; + } + + case COMPARE_OP_FLOAT: { + STACK_SHRINK(1); + break; + } + + case COMPARE_OP_INT: { + STACK_SHRINK(1); + break; + } + + case COMPARE_OP_STR: { + STACK_SHRINK(1); + break; + } + + case IS_OP: { + STACK_SHRINK(1); + break; + } + + case CONTAINS_OP: { + STACK_SHRINK(1); + break; + } + + case CHECK_EG_MATCH: { + break; + } + + case CHECK_EXC_MATCH: { + break; + } + + case IMPORT_NAME: { + STACK_SHRINK(1); + break; + } + + case IMPORT_FROM: { + STACK_GROW(1); + break; + } + + case JUMP_FORWARD: { + break; + } + + case JUMP_BACKWARD: { + break; + } + + case ENTER_EXECUTOR: { + break; + } + + case POP_JUMP_IF_FALSE: { + STACK_SHRINK(1); + break; + } + + case POP_JUMP_IF_TRUE: { + STACK_SHRINK(1); + break; + } + + case IS_NONE: { + break; + } + + case JUMP_BACKWARD_NO_INTERRUPT: { + break; + } + + case GET_LEN: { + STACK_GROW(1); + break; + } + + case MATCH_CLASS: { + STACK_SHRINK(2); + break; + } + + case MATCH_MAPPING: { + STACK_GROW(1); + break; + } + + case MATCH_SEQUENCE: { + STACK_GROW(1); + break; + } + + case MATCH_KEYS: { + STACK_GROW(1); + break; + } + + case GET_ITER: { + break; + } + + case GET_YIELD_FROM_ITER: { + break; + } + + case FOR_ITER: { + STACK_GROW(1); + break; + } + + case INSTRUMENTED_FOR_ITER: { + break; + } + + case _ITER_CHECK_LIST: { + break; + } + + case _ITER_JUMP_LIST: { + break; + } + + case _IS_ITER_EXHAUSTED_LIST: { + STACK_GROW(1); + break; + } + + case _ITER_NEXT_LIST: { + STACK_GROW(1); + break; + } + + case _ITER_CHECK_TUPLE: { + break; + } + + case _ITER_JUMP_TUPLE: { + break; + } + + case _IS_ITER_EXHAUSTED_TUPLE: { + STACK_GROW(1); + break; + } + + case _ITER_NEXT_TUPLE: { + STACK_GROW(1); + break; + } + + case _ITER_CHECK_RANGE: { + break; + } + + case _ITER_JUMP_RANGE: { + break; + } + + case _IS_ITER_EXHAUSTED_RANGE: { + STACK_GROW(1); + break; + } + + case _ITER_NEXT_RANGE: { + STACK_GROW(1); + break; + } + + case FOR_ITER_GEN: { + STACK_GROW(1); + break; + } + + case BEFORE_ASYNC_WITH: { + STACK_GROW(1); + break; + } + + case BEFORE_WITH: { + STACK_GROW(1); + break; + } + + case WITH_EXCEPT_START: { + STACK_GROW(1); + break; + } + + case PUSH_EXC_INFO: { + STACK_GROW(1); + break; + } + + case LOAD_ATTR_METHOD_WITH_VALUES: { + STACK_GROW(1); + break; + } + + case LOAD_ATTR_METHOD_NO_DICT: { + STACK_GROW(1); + break; + } + + case LOAD_ATTR_NONDESCRIPTOR_WITH_VALUES: { + break; + } + + case LOAD_ATTR_NONDESCRIPTOR_NO_DICT: { + break; + } + + case LOAD_ATTR_METHOD_LAZY_DICT: { + STACK_GROW(1); + break; + } + + case KW_NAMES: { + break; + } + + case INSTRUMENTED_CALL: { + break; + } + + case CALL: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_BOUND_METHOD_EXACT_ARGS: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case CALL_PY_EXACT_ARGS: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case CALL_PY_WITH_DEFAULTS: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case CALL_NO_KW_TYPE_1: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case CALL_NO_KW_STR_1: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_NO_KW_TUPLE_1: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_NO_KW_ALLOC_AND_ENTER_INIT: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case EXIT_INIT_CHECK: { + STACK_SHRINK(1); + break; + } + + case CALL_BUILTIN_CLASS: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_NO_KW_BUILTIN_O: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_NO_KW_BUILTIN_FAST: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_BUILTIN_FAST_WITH_KEYWORDS: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_NO_KW_LEN: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case CALL_NO_KW_ISINSTANCE: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case CALL_NO_KW_LIST_APPEND: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + break; + } + + case CALL_NO_KW_METHOD_DESCRIPTOR_O: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_NO_KW_METHOD_DESCRIPTOR_NOARGS: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case CALL_NO_KW_METHOD_DESCRIPTOR_FAST: { + STACK_SHRINK(oparg); + STACK_SHRINK(1); + CHECK_EVAL_BREAKER(); + break; + } + + case INSTRUMENTED_CALL_FUNCTION_EX: { + break; + } + + case CALL_FUNCTION_EX: { + STACK_SHRINK(((oparg & 1) ? 1 : 0)); + STACK_SHRINK(2); + CHECK_EVAL_BREAKER(); + break; + } + + case MAKE_FUNCTION: { + break; + } + + case SET_FUNCTION_ATTRIBUTE: { + STACK_SHRINK(1); + break; + } + + case RETURN_GENERATOR: { + break; + } + + case BUILD_SLICE: { + STACK_SHRINK(((oparg == 3) ? 1 : 0)); + STACK_SHRINK(1); + break; + } + + case CONVERT_VALUE: { + break; + } + + case FORMAT_SIMPLE: { + break; + } + + case FORMAT_WITH_SPEC: { + STACK_SHRINK(1); + break; + } + + case COPY: { + STACK_GROW(1); + break; + } + + case BINARY_OP: { + STACK_SHRINK(1); + break; + } + + case SWAP: { + break; + } + + case INSTRUMENTED_INSTRUCTION: { + break; + } + + case INSTRUMENTED_JUMP_FORWARD: { + break; + } + + case INSTRUMENTED_JUMP_BACKWARD: { + break; + } + + case INSTRUMENTED_POP_JUMP_IF_TRUE: { + break; + } + + case INSTRUMENTED_POP_JUMP_IF_FALSE: { + break; + } + + case INSTRUMENTED_POP_JUMP_IF_NONE: { + break; + } + + case INSTRUMENTED_POP_JUMP_IF_NOT_NONE: { + break; + } + + case EXTENDED_ARG: { + break; + } + + case CACHE: { + break; + } + + case RESERVED: { + break; + } + + case _POP_JUMP_IF_FALSE: { + STACK_SHRINK(1); + break; + } + + case _POP_JUMP_IF_TRUE: { + STACK_SHRINK(1); + break; + } + + case JUMP_TO_TOP: { + CHECK_EVAL_BREAKER(); + break; + } + + case SAVE_IP: { + break; + } + + case EXIT_TRACE: { + break; + } diff --git a/Python/optimizer.c b/Python/optimizer.c index 238ab02d09faa7..79280bb18448ff 100644 --- a/Python/optimizer.c +++ b/Python/optimizer.c @@ -4,6 +4,7 @@ #include "pycore_opcode.h" #include "pycore_opcode_metadata.h" #include "pycore_opcode_utils.h" +#include "pycore_optimizer.h" #include "pycore_pystate.h" // _PyInterpreterState_GET() #include "pycore_uops.h" #include "cpython/optimizer.h" @@ -704,10 +705,11 @@ uop_optimize( return -1; } executor->base.execute = _PyUopExecute; + trace_length = uop_analyze_and_optimize(trace, trace_length); memcpy(executor->trace, trace, trace_length * sizeof(_PyUOpInstruction)); - if (trace_length < _Py_UOP_MAX_TRACE_LENGTH) { - executor->trace[trace_length].opcode = 0; // Sentinel - } + if (trace_length < _Py_UOP_MAX_TRACE_LENGTH) { + executor->trace[trace_length].opcode = 0; // Sentinel + } *exec_ptr = (_PyExecutorObject *)executor; return 1; } diff --git a/Python/optimizer_analysis.c b/Python/optimizer_analysis.c new file mode 100644 index 00000000000000..d489fb802fca33 --- /dev/null +++ b/Python/optimizer_analysis.c @@ -0,0 +1,21 @@ +#include "Python.h" +#include "opcode.h" +#include "pycore_interp.h" +#include "pycore_opcode.h" +#include "pycore_opcode_metadata.h" +#include "pycore_opcode_utils.h" +#include "pycore_pystate.h" // _PyInterpreterState_GET() +#include "pycore_uops.h" +#include "cpython/optimizer.h" +#include +#include +#include +#include "pycore_optimizer.h" + +int +uop_analyze_and_optimize( + _PyUOpInstruction *trace, + int trace_len) +{ + return trace_len; +} diff --git a/Tools/cases_generator/generate_cases.py b/Tools/cases_generator/generate_cases.py index 967e1e2f5b63bb..4407410664c104 100644 --- a/Tools/cases_generator/generate_cases.py +++ b/Tools/cases_generator/generate_cases.py @@ -15,6 +15,7 @@ from flags import InstructionFlags, variable_used from instructions import ( AnyInstruction, + AbstractInstruction, Component, Instruction, MacroInstruction, @@ -43,6 +44,9 @@ DEFAULT_EXECUTOR_OUTPUT = os.path.relpath( os.path.join(ROOT, "Python/executor_cases.c.h") ) +DEFAULT_ABSTRACT_INTERPRETER_OUTPUT = os.path.relpath( + os.path.join(ROOT, "Python/abstract_interp_cases.c.h") +) # Constants used instead of size for macro expansions. # Note: 1, 2, 4 must match actual cache entry sizes. @@ -91,7 +95,13 @@ help="Write executor cases to this file", default=DEFAULT_EXECUTOR_OUTPUT, ) - +arg_parser.add_argument( + "-a", + "--abstract-interpreter-cases", + type=str, + help="Write abstract interpreter cases to this file", + default=DEFAULT_ABSTRACT_INTERPRETER_OUTPUT, +) class Generator(Analyzer): def get_stack_effect_info( @@ -620,6 +630,39 @@ def write_executor_instructions( file=sys.stderr, ) + def write_abstract_interpreter_instructions( + self, abstract_interpreter_filename: str, emit_line_directives: bool + ) -> None: + """Generate cases for the Tier 2 abstract interpreter/analzyer.""" + with open(abstract_interpreter_filename, "w") as f: + self.out = Formatter(f, 8, emit_line_directives) + self.write_provenance_header() + for thing in self.everything: + match thing: + case OverriddenInstructionPlaceHolder(): + # TODO: Is this helpful? + self.write_overridden_instr_place_holder(thing) + case parsing.InstDef(): + instr = AbstractInstruction(self.instrs[thing.name].inst) + self.out.emit("") + with self.out.block(f"case {thing.name}:"): + instr.write(self.out, tier=TIER_TWO) + if instr.check_eval_breaker: + self.out.emit("CHECK_EVAL_BREAKER();") + self.out.emit("break;") + # elif instr.kind != "op": + # print(f"NOTE: {thing.name} is not a viable uop") + case parsing.Macro(): + pass + case parsing.Pseudo(): + pass + case _: + typing.assert_never(thing) + print( + f"Wrote some stuff to {abstract_interpreter_filename}", + file=sys.stderr, + ) + def write_overridden_instr_place_holder( self, place_holder: OverriddenInstructionPlaceHolder ) -> None: @@ -724,6 +767,8 @@ def main(): a.write_instructions(args.output, args.emit_line_directives) a.write_metadata(args.metadata, args.pymetadata) a.write_executor_instructions(args.executor_cases, args.emit_line_directives) + a.write_abstract_interpreter_instructions(args.abstract_interpreter_cases, + args.emit_line_directives) if __name__ == "__main__": diff --git a/Tools/cases_generator/instructions.py b/Tools/cases_generator/instructions.py index 6f42699d900b46..6184bea9850dc7 100644 --- a/Tools/cases_generator/instructions.py +++ b/Tools/cases_generator/instructions.py @@ -310,6 +310,37 @@ def write_body( StackEffectMapping = list[tuple[StackEffect, StackEffect]] +# Instruction used for abstract interpretation. +class AbstractInstruction(Instruction): + def __init__(self, inst: parsing.InstDef): + super().__init__(inst) + + def write(self, out: Formatter, tier: Tiers = TIER_ONE) -> None: + """Write one abstract instruction, sans prologue and epilogue.""" + # Write a static assertion that a family's cache size is correct + if family := self.family: + if self.name == family.name: + if cache_size := family.size: + out.emit( + f"static_assert({cache_size} == " + f'{self.cache_offset}, "incorrect cache size");' + ) + # Write net stack growth/shrinkage + out.stack_adjust( + [ieff for ieff in self.input_effects], + [oeff for oeff in self.output_effects], + ) + + def write_body( + self, + out: Formatter, + dedent: int, + active_caches: list[ActiveCacheEffect], + tier: Tiers = TIER_ONE, + ) -> None: + pass + + @dataclasses.dataclass class Component: instr: Instruction From 2aeea51c4e94e44767d87869723a05f1c5fd15fb Mon Sep 17 00:00:00 2001 From: "blurb-it[bot]" <43283697+blurb-it[bot]@users.noreply.github.com> Date: Wed, 2 Aug 2023 09:55:27 +0000 Subject: [PATCH 02/14] =?UTF-8?q?=F0=9F=93=9C=F0=9F=A4=96=20Added=20by=20b?= =?UTF-8?q?lurb=5Fit.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../2023-08-02-09-55-21.gh-issue-107557.P1z-in.rst | 1 + 1 file changed, 1 insertion(+) create mode 100644 Misc/NEWS.d/next/Core and Builtins/2023-08-02-09-55-21.gh-issue-107557.P1z-in.rst diff --git a/Misc/NEWS.d/next/Core and Builtins/2023-08-02-09-55-21.gh-issue-107557.P1z-in.rst b/Misc/NEWS.d/next/Core and Builtins/2023-08-02-09-55-21.gh-issue-107557.P1z-in.rst new file mode 100644 index 00000000000000..392f59c79e8de9 --- /dev/null +++ b/Misc/NEWS.d/next/Core and Builtins/2023-08-02-09-55-21.gh-issue-107557.P1z-in.rst @@ -0,0 +1 @@ +Generate the cases needed for the barebones tier 2 abstract interpreter for optimization passes in CPython. From 1a728ab6ce121e30d8f475c9499b2a84eb134ebf Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Wed, 2 Aug 2023 19:50:24 +0800 Subject: [PATCH 03/14] Copy Guido's input and output code, and fix build Co-Authored-By: Guido van Rossum --- Include/internal/pycore_optimizer.h | 4 +- Python/abstract_interp_cases.c.h | 412 ++++++++++++++++++++++++++ Tools/cases_generator/instructions.py | 38 +++ 3 files changed, 453 insertions(+), 1 deletion(-) diff --git a/Include/internal/pycore_optimizer.h b/Include/internal/pycore_optimizer.h index 3b5fa634e13972..06d05cf00babd3 100644 --- a/Include/internal/pycore_optimizer.h +++ b/Include/internal/pycore_optimizer.h @@ -8,7 +8,9 @@ extern "C" { # error "this header requires Py_BUILD_CORE define" #endif -extern int uop_analyze_and_optimize(struct _PyUOpInstruction *trace, int trace_len); +#include "pycore_uops.h" + +int uop_analyze_and_optimize(_PyUOpInstruction *trace, int trace_len); #ifdef __cplusplus } diff --git a/Python/abstract_interp_cases.c.h b/Python/abstract_interp_cases.c.h index 4b05477da45e3a..2adf4deccea4bd 100644 --- a/Python/abstract_interp_cases.c.h +++ b/Python/abstract_interp_cases.c.h @@ -17,77 +17,104 @@ case LOAD_FAST_CHECK: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case LOAD_FAST: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case LOAD_FAST_AND_CLEAR: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case LOAD_FAST_LOAD_FAST: { STACK_GROW(2); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case LOAD_CONST: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case STORE_FAST: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case STORE_FAST_LOAD_FAST: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case STORE_FAST_STORE_FAST: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case POP_TOP: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case PUSH_NULL: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case INSTRUMENTED_END_FOR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case END_SEND: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case INSTRUMENTED_END_SEND: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case UNARY_NEGATIVE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case UNARY_NOT: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case TO_BOOL: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } @@ -96,26 +123,38 @@ } case TO_BOOL_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case TO_BOOL_LIST: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case TO_BOOL_NONE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case TO_BOOL_STR: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case TO_BOOL_ALWAYS_TRUE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case UNARY_INVERT: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } @@ -124,17 +163,26 @@ } case _BINARY_OP_MULTIPLY_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case _BINARY_OP_ADD_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case _BINARY_OP_SUBTRACT_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } @@ -143,17 +191,26 @@ } case _BINARY_OP_MULTIPLY_FLOAT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case _BINARY_OP_ADD_FLOAT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case _BINARY_OP_SUBTRACT_FLOAT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } @@ -162,105 +219,155 @@ } case _BINARY_OP_ADD_UNICODE: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case _BINARY_OP_INPLACE_ADD_UNICODE: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case BINARY_SUBSCR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case BINARY_SLICE: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(2); + stack_pointer[-1] = NULL; break; } case STORE_SLICE: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; + stack_pointer[-4] = NULL; STACK_SHRINK(4); break; } case BINARY_SUBSCR_LIST_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case BINARY_SUBSCR_TUPLE_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case BINARY_SUBSCR_DICT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case BINARY_SUBSCR_GETITEM: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case LIST_APPEND: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case SET_ADD: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case STORE_SUBSCR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(3); break; } case STORE_SUBSCR_LIST_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(3); break; } case STORE_SUBSCR_DICT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(3); break; } case DELETE_SUBSCR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case CALL_INTRINSIC_1: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case CALL_INTRINSIC_2: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case RAISE_VARARGS: { + (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); break; } case INTERPRETER_EXIT: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case RETURN_VALUE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case INSTRUMENTED_RETURN_VALUE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -274,65 +381,90 @@ } case GET_AITER: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case GET_ANEXT: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case GET_AWAITABLE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case SEND: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case SEND_GEN: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case INSTRUMENTED_YIELD_VALUE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case YIELD_VALUE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case POP_EXCEPT: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case RERAISE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case END_ASYNC_FOR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case CLEANUP_THROW: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case LOAD_ASSERTION_ERROR: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case LOAD_BUILD_CLASS: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case STORE_NAME: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -342,45 +474,61 @@ } case UNPACK_SEQUENCE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); + stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_SEQUENCE_TWO_TUPLE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); + stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_SEQUENCE_TUPLE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); + stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_SEQUENCE_LIST: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); + stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_EX: { + stack_pointer[-1] = NULL; STACK_GROW((oparg & 0xFF) + (oparg >> 8)); + stack_pointer - ((oparg >> 8)) = (PyObject **)NULL; + stack_pointer[-(1 + (oparg >> 8))] = NULL; + stack_pointer - (1 + (oparg >> 8) + (oparg & 0xFF)) = (PyObject **)NULL; break; } case STORE_ATTR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case DELETE_ATTR: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case STORE_GLOBAL: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -391,16 +539,21 @@ case _LOAD_LOCALS: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case _LOAD_FROM_DICT_OR_GLOBALS: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_GLOBAL: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } @@ -415,12 +568,16 @@ case _LOAD_GLOBAL_MODULE: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case _LOAD_GLOBAL_BUILTINS: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } @@ -437,15 +594,19 @@ } case LOAD_FROM_DICT_OR_DEREF: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_DEREF: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case STORE_DEREF: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -455,42 +616,54 @@ } case BUILD_STRING: { + (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case BUILD_TUPLE: { + (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case BUILD_LIST: { + (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case LIST_EXTEND: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case SET_UPDATE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case BUILD_SET: { + (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case BUILD_MAP: { + (stack_pointer - oparg*2) = (PyObject **)NULL; STACK_SHRINK(oparg*2); STACK_GROW(1); + stack_pointer[-1] = NULL; break; } @@ -499,21 +672,28 @@ } case BUILD_CONST_KEY_MAP: { + stack_pointer[-1] = NULL; + (stack_pointer - (1 + oparg)) = (PyObject **)NULL; STACK_SHRINK(oparg); + stack_pointer[-1] = NULL; break; } case DICT_UPDATE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case DICT_MERGE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case MAP_ADD: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } @@ -525,24 +705,42 @@ } case LOAD_SUPER_ATTR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(2); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_SUPER_ATTR_ATTR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(2); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_SUPER_ATTR_METHOD: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case LOAD_ATTR: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } @@ -555,100 +753,155 @@ } case _LOAD_ATTR_INSTANCE_VALUE: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_MODULE: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_WITH_HINT: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_SLOT: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_CLASS: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_PROPERTY: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN: { + stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1] = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case STORE_ATTR_INSTANCE_VALUE: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case STORE_ATTR_WITH_HINT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case STORE_ATTR_SLOT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case COMPARE_OP: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case COMPARE_OP_FLOAT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case COMPARE_OP_INT: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case COMPARE_OP_STR: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case IS_OP: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CONTAINS_OP: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CHECK_EG_MATCH: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case CHECK_EXC_MATCH: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case IMPORT_NAME: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case IMPORT_FROM: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } @@ -665,16 +918,20 @@ } case POP_JUMP_IF_FALSE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case POP_JUMP_IF_TRUE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case IS_NONE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } @@ -684,39 +941,52 @@ case GET_LEN: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case MATCH_CLASS: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; + stack_pointer[-3] = NULL; STACK_SHRINK(2); + stack_pointer[-1] = NULL; break; } case MATCH_MAPPING: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case MATCH_SEQUENCE: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case MATCH_KEYS: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case GET_ITER: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case GET_YIELD_FROM_ITER: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case FOR_ITER: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } @@ -734,11 +1004,13 @@ case _IS_ITER_EXHAUSTED_LIST: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case _ITER_NEXT_LIST: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } @@ -752,11 +1024,13 @@ case _IS_ITER_EXHAUSTED_TUPLE: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case _ITER_NEXT_TUPLE: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } @@ -770,59 +1044,87 @@ case _IS_ITER_EXHAUSTED_RANGE: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case _ITER_NEXT_RANGE: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case FOR_ITER_GEN: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case BEFORE_ASYNC_WITH: { + stack_pointer[-1] = NULL; STACK_GROW(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case BEFORE_WITH: { + stack_pointer[-1] = NULL; STACK_GROW(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case WITH_EXCEPT_START: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case PUSH_EXC_INFO: { + stack_pointer[-1] = NULL; STACK_GROW(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case LOAD_ATTR_METHOD_WITH_VALUES: { + stack_pointer[-1] = NULL; STACK_GROW(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case LOAD_ATTR_METHOD_NO_DICT: { + stack_pointer[-1] = NULL; STACK_GROW(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } case LOAD_ATTR_NONDESCRIPTOR_WITH_VALUES: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_ATTR_NONDESCRIPTOR_NO_DICT: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_ATTR_METHOD_LAZY_DICT: { + stack_pointer[-1] = NULL; STACK_GROW(1); + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; break; } @@ -835,131 +1137,208 @@ } case CALL: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_BOUND_METHOD_EXACT_ARGS: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CALL_PY_EXACT_ARGS: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CALL_PY_WITH_DEFAULTS: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CALL_NO_KW_TYPE_1: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CALL_NO_KW_STR_1: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_NO_KW_TUPLE_1: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_NO_KW_ALLOC_AND_ENTER_INIT: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case EXIT_INIT_CHECK: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case CALL_BUILTIN_CLASS: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_NO_KW_BUILTIN_O: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_NO_KW_BUILTIN_FAST: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_BUILTIN_FAST_WITH_KEYWORDS: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_NO_KW_LEN: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CALL_NO_KW_ISINSTANCE: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CALL_NO_KW_LIST_APPEND: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CALL_NO_KW_METHOD_DESCRIPTOR_O: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_NO_KW_METHOD_DESCRIPTOR_NOARGS: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case CALL_NO_KW_METHOD_DESCRIPTOR_FAST: { + (stack_pointer - oparg) = (PyObject **)NULL; + stack_pointer[-(1 + oparg)] = NULL; + stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } @@ -969,18 +1348,28 @@ } case CALL_FUNCTION_EX: { + (oparg & 1) ? stack_pointer[-(((oparg & 1) ? 1 : 0))] : NULL = NULL; + stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; + stack_pointer[-(2 + ((oparg & 1) ? 1 : 0))] = NULL; + stack_pointer[-(3 + ((oparg & 1) ? 1 : 0))] = NULL; STACK_SHRINK(((oparg & 1) ? 1 : 0)); STACK_SHRINK(2); + stack_pointer[-1] = NULL; CHECK_EVAL_BREAKER(); break; } case MAKE_FUNCTION: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case SET_FUNCTION_ATTRIBUTE: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } @@ -989,35 +1378,56 @@ } case BUILD_SLICE: { + (oparg == 3) ? stack_pointer[-(((oparg == 3) ? 1 : 0))] : NULL = NULL; + stack_pointer[-(1 + ((oparg == 3) ? 1 : 0))] = NULL; + stack_pointer[-(2 + ((oparg == 3) ? 1 : 0))] = NULL; STACK_SHRINK(((oparg == 3) ? 1 : 0)); STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case CONVERT_VALUE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case FORMAT_SIMPLE: { + stack_pointer[-1] = NULL; + stack_pointer[-1] = NULL; break; } case FORMAT_WITH_SPEC: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case COPY: { STACK_GROW(1); + stack_pointer[-1] = NULL; break; } case BINARY_OP: { + stack_pointer[-1] = NULL; + stack_pointer[-2] = NULL; STACK_SHRINK(1); + stack_pointer[-1] = NULL; break; } case SWAP: { + stack_pointer[-1] = NULL; + (stack_pointer - (1 + (oparg-2))) = (PyObject **)NULL; + stack_pointer[-(2 + (oparg-2))] = NULL; + stack_pointer[-1] = NULL; + stack_pointer - (1 + (oparg-2)) = (PyObject **)NULL; + stack_pointer[-(2 + (oparg-2))] = NULL; break; } @@ -1062,11 +1472,13 @@ } case _POP_JUMP_IF_FALSE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case _POP_JUMP_IF_TRUE: { + stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } diff --git a/Tools/cases_generator/instructions.py b/Tools/cases_generator/instructions.py index 6184bea9850dc7..f3f3093219b65a 100644 --- a/Tools/cases_generator/instructions.py +++ b/Tools/cases_generator/instructions.py @@ -325,12 +325,50 @@ def write(self, out: Formatter, tier: Tiers = TIER_ONE) -> None: f"static_assert({cache_size} == " f'{self.cache_offset}, "incorrect cache size");' ) + # NULL out inputs, unless it's the same as in the output, + # Write input stack effect variable declarations and initializations + ieffects = list(reversed(self.input_effects)) + for i, ieffect in enumerate(ieffects): + if ieffect.name in self.unmoved_names: + continue + isize = string_effect_size( + list_effect_size([ieff for ieff in ieffects[: i + 1]]) + ) + if ieffect.size: + src = StackEffect( + f"(stack_pointer - {maybe_parenthesize(isize)})", "PyObject **" + ) + elif ieffect.cond: + src = StackEffect( + f"({ieffect.cond}) ? stack_pointer[-{maybe_parenthesize(isize)}] : NULL", + "", + ) + else: + src = StackEffect(f"stack_pointer[-{maybe_parenthesize(isize)}]", "") + out.assign(src, parsing.StackEffect("NULL")) + # Write net stack growth/shrinkage out.stack_adjust( [ieff for ieff in self.input_effects], [oeff for oeff in self.output_effects], ) + # NULL out outputs, unless it's same as input. + oeffects = list(reversed(self.output_effects)) + for i, oeffect in enumerate(oeffects): + if oeffect.name in self.unmoved_names: + continue + osize = string_effect_size( + list_effect_size([oeff for oeff in oeffects[: i + 1]]) + ) + if oeffect.size: + dst = StackEffect( + f"stack_pointer - {maybe_parenthesize(osize)}", "PyObject **" + ) + else: + dst = StackEffect(f"stack_pointer[-{maybe_parenthesize(osize)}]", "") + out.assign(dst, parsing.StackEffect("NULL")) + def write_body( self, out: Formatter, From 17fccbca34ae7bc433e1ba1fff4b6e9d617c16d6 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Wed, 2 Aug 2023 19:54:50 +0800 Subject: [PATCH 04/14] fix separator --- Python/abstract_interp_cases.c.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Python/abstract_interp_cases.c.h b/Python/abstract_interp_cases.c.h index 2adf4deccea4bd..ac8c3a367da49f 100644 --- a/Python/abstract_interp_cases.c.h +++ b/Python/abstract_interp_cases.c.h @@ -1,6 +1,6 @@ // This file is generated by Tools/cases_generator/generate_cases.py // from: -// Python\bytecodes.c +// Python/bytecodes.c // Do not edit! case NOP: { From a1da69db9529d988d6dc5ff6688105d9d235b6bd Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Wed, 2 Aug 2023 19:59:17 +0800 Subject: [PATCH 05/14] credit Jules --- Tools/cases_generator/instructions.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Tools/cases_generator/instructions.py b/Tools/cases_generator/instructions.py index f3f3093219b65a..197a79f539d5e7 100644 --- a/Tools/cases_generator/instructions.py +++ b/Tools/cases_generator/instructions.py @@ -326,7 +326,7 @@ def write(self, out: Formatter, tier: Tiers = TIER_ONE) -> None: f'{self.cache_offset}, "incorrect cache size");' ) # NULL out inputs, unless it's the same as in the output, - # Write input stack effect variable declarations and initializations + # Write input stack effect variable declarations and initializations. ieffects = list(reversed(self.input_effects)) for i, ieffect in enumerate(ieffects): if ieffect.name in self.unmoved_names: From b458e171cbe24a71cb721da0606b07ff3e3f8ba1 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Wed, 2 Aug 2023 20:00:18 +0800 Subject: [PATCH 06/14] add jules to co-authors Co-Authored-By: Jules <57632293+juliapoo@users.noreply.github.com> --- Python/optimizer_analysis.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Python/optimizer_analysis.c b/Python/optimizer_analysis.c index d489fb802fca33..13d2b8c48637b1 100644 --- a/Python/optimizer_analysis.c +++ b/Python/optimizer_analysis.c @@ -15,7 +15,8 @@ int uop_analyze_and_optimize( _PyUOpInstruction *trace, - int trace_len) + int trace_len +) { return trace_len; } From f81f8889d2cfa1160e106c3cdd0e592adb2d742f Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Wed, 2 Aug 2023 23:46:58 +0800 Subject: [PATCH 07/14] add pycore_optimizer.h to headers in makefile --- Makefile.pre.in | 1 + 1 file changed, 1 insertion(+) diff --git a/Makefile.pre.in b/Makefile.pre.in index a334aae9dec4fc..ce6e38bacc81ae 100644 --- a/Makefile.pre.in +++ b/Makefile.pre.in @@ -1787,6 +1787,7 @@ PYTHON_HEADERS= \ $(srcdir)/Include/internal/pycore_obmalloc_init.h \ $(srcdir)/Include/internal/pycore_opcode.h \ $(srcdir)/Include/internal/pycore_opcode_utils.h \ + $(srcdir)/Include/internal/pycore_optimizer.h \ $(srcdir)/Include/internal/pycore_pathconfig.h \ $(srcdir)/Include/internal/pycore_pyarena.h \ $(srcdir)/Include/internal/pycore_pyerrors.h \ From 0020320d0f5aa58f6aa2a36b8f025396f5b7ba55 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Thu, 3 Aug 2023 00:03:59 +0800 Subject: [PATCH 08/14] fix: remove whitespace --- Makefile.pre.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile.pre.in b/Makefile.pre.in index ce6e38bacc81ae..94beadabce18cc 100644 --- a/Makefile.pre.in +++ b/Makefile.pre.in @@ -1787,7 +1787,7 @@ PYTHON_HEADERS= \ $(srcdir)/Include/internal/pycore_obmalloc_init.h \ $(srcdir)/Include/internal/pycore_opcode.h \ $(srcdir)/Include/internal/pycore_opcode_utils.h \ - $(srcdir)/Include/internal/pycore_optimizer.h \ + $(srcdir)/Include/internal/pycore_optimizer.h \ $(srcdir)/Include/internal/pycore_pathconfig.h \ $(srcdir)/Include/internal/pycore_pyarena.h \ $(srcdir)/Include/internal/pycore_pyerrors.h \ From 1f93072c596e48f11ca715ac54091e885bebbbf9 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Thu, 3 Aug 2023 01:09:26 +0800 Subject: [PATCH 09/14] fix make smelly --- Include/internal/pycore_optimizer.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Include/internal/pycore_optimizer.h b/Include/internal/pycore_optimizer.h index 06d05cf00babd3..ccbe7e52af289a 100644 --- a/Include/internal/pycore_optimizer.h +++ b/Include/internal/pycore_optimizer.h @@ -10,7 +10,7 @@ extern "C" { #include "pycore_uops.h" -int uop_analyze_and_optimize(_PyUOpInstruction *trace, int trace_len); +int _Py_uop_analyze_and_optimize(_PyUOpInstruction *trace, int trace_len); #ifdef __cplusplus } From dac63e348441a99ba2844a22abdc214aad3402f1 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Thu, 3 Aug 2023 01:11:34 +0800 Subject: [PATCH 10/14] fix: build --- Python/optimizer_analysis.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Python/optimizer_analysis.c b/Python/optimizer_analysis.c index 13d2b8c48637b1..cb399b0beb9129 100644 --- a/Python/optimizer_analysis.c +++ b/Python/optimizer_analysis.c @@ -13,7 +13,7 @@ #include "pycore_optimizer.h" int -uop_analyze_and_optimize( +_Py_uop_analyze_and_optimize( _PyUOpInstruction *trace, int trace_len ) From e62e0153cd765bea9786407b32272dcb0e5dc234 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Thu, 3 Aug 2023 01:35:01 +0800 Subject: [PATCH 11/14] fix wrong symbol --- Python/optimizer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Python/optimizer.c b/Python/optimizer.c index 79280bb18448ff..3f9a82cf1daa13 100644 --- a/Python/optimizer.c +++ b/Python/optimizer.c @@ -705,7 +705,7 @@ uop_optimize( return -1; } executor->base.execute = _PyUopExecute; - trace_length = uop_analyze_and_optimize(trace, trace_length); + trace_length = _Py_uop_analyze_and_optimize(trace, trace_length); memcpy(executor->trace, trace, trace_length * sizeof(_PyUOpInstruction)); if (trace_length < _Py_UOP_MAX_TRACE_LENGTH) { executor->trace[trace_length].opcode = 0; // Sentinel From a7f654cafe24b9dc65188e8514be5fd1c472ab36 Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Thu, 3 Aug 2023 02:10:11 +0800 Subject: [PATCH 12/14] ignore static globals check for abstract interpreter --- Tools/c-analyzer/cpython/_parser.py | 1 + 1 file changed, 1 insertion(+) diff --git a/Tools/c-analyzer/cpython/_parser.py b/Tools/c-analyzer/cpython/_parser.py index 9bc7285e18b2fb..90334d0e79da80 100644 --- a/Tools/c-analyzer/cpython/_parser.py +++ b/Tools/c-analyzer/cpython/_parser.py @@ -84,6 +84,7 @@ def clean_lines(text): Python/frozen_modules/*.h Python/generated_cases.c.h Python/executor_cases.c.h +Python/abstract_interp_cases.c.h # not actually source Python/bytecodes.c From ec58145acf047f75ce9b34418327a97a158c262e Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Sat, 5 Aug 2023 01:23:56 +0800 Subject: [PATCH 13/14] merge Guido's changes --- Python/abstract_interp_cases.c.h | 308 +++----------------------- Tools/cases_generator/instructions.py | 43 +--- Tools/cases_generator/stacking.py | 36 +++ 3 files changed, 65 insertions(+), 322 deletions(-) diff --git a/Python/abstract_interp_cases.c.h b/Python/abstract_interp_cases.c.h index ac8c3a367da49f..8356ad15299f8e 100644 --- a/Python/abstract_interp_cases.c.h +++ b/Python/abstract_interp_cases.c.h @@ -35,8 +35,8 @@ case LOAD_FAST_LOAD_FAST: { STACK_GROW(2); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } @@ -47,26 +47,21 @@ } case STORE_FAST: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case STORE_FAST_LOAD_FAST: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case STORE_FAST_STORE_FAST: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case POP_TOP: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -78,42 +73,33 @@ } case INSTRUMENTED_END_FOR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case END_SEND: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case INSTRUMENTED_END_SEND: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case UNARY_NEGATIVE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case UNARY_NOT: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case TO_BOOL: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } @@ -123,37 +109,31 @@ } case TO_BOOL_INT: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case TO_BOOL_LIST: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case TO_BOOL_NONE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case TO_BOOL_STR: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case TO_BOOL_ALWAYS_TRUE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case UNARY_INVERT: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } @@ -163,24 +143,18 @@ } case _BINARY_OP_MULTIPLY_INT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case _BINARY_OP_ADD_INT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case _BINARY_OP_SUBTRACT_INT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; @@ -191,24 +165,18 @@ } case _BINARY_OP_MULTIPLY_FLOAT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case _BINARY_OP_ADD_FLOAT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case _BINARY_OP_SUBTRACT_FLOAT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; @@ -219,155 +187,114 @@ } case _BINARY_OP_ADD_UNICODE: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case _BINARY_OP_INPLACE_ADD_UNICODE: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case BINARY_SUBSCR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case BINARY_SLICE: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(2); stack_pointer[-1] = NULL; break; } case STORE_SLICE: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; - stack_pointer[-4] = NULL; STACK_SHRINK(4); break; } case BINARY_SUBSCR_LIST_INT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case BINARY_SUBSCR_TUPLE_INT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case BINARY_SUBSCR_DICT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case BINARY_SUBSCR_GETITEM: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case LIST_APPEND: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case SET_ADD: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case STORE_SUBSCR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(3); break; } case STORE_SUBSCR_LIST_INT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(3); break; } case STORE_SUBSCR_DICT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(3); break; } case DELETE_SUBSCR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case CALL_INTRINSIC_1: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case CALL_INTRINSIC_2: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case RAISE_VARARGS: { - (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); break; } case INTERPRETER_EXIT: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case RETURN_VALUE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case INSTRUMENTED_RETURN_VALUE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -381,7 +308,6 @@ } case GET_AITER: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } @@ -393,61 +319,49 @@ } case GET_AWAITABLE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case SEND: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case SEND_GEN: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case INSTRUMENTED_YIELD_VALUE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case YIELD_VALUE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case POP_EXCEPT: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case RERAISE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case END_ASYNC_FOR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case CLEANUP_THROW: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } @@ -464,7 +378,6 @@ } case STORE_NAME: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -474,61 +387,46 @@ } case UNPACK_SEQUENCE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); - stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_SEQUENCE_TWO_TUPLE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); - stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_SEQUENCE_TUPLE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); - stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_SEQUENCE_LIST: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); STACK_GROW(oparg); - stack_pointer - oparg = (PyObject **)NULL; break; } case UNPACK_EX: { - stack_pointer[-1] = NULL; STACK_GROW((oparg & 0xFF) + (oparg >> 8)); - stack_pointer - ((oparg >> 8)) = (PyObject **)NULL; - stack_pointer[-(1 + (oparg >> 8))] = NULL; - stack_pointer - (1 + (oparg >> 8) + (oparg & 0xFF)) = (PyObject **)NULL; + stack_pointer[-1 - (oparg >> 8)] = NULL; break; } case STORE_ATTR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case DELETE_ATTR: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case STORE_GLOBAL: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -544,7 +442,6 @@ } case _LOAD_FROM_DICT_OR_GLOBALS: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } @@ -552,8 +449,8 @@ case LOAD_GLOBAL: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } @@ -568,16 +465,16 @@ case _LOAD_GLOBAL_MODULE: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case _LOAD_GLOBAL_BUILTINS: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } @@ -594,7 +491,6 @@ } case LOAD_FROM_DICT_OR_DEREF: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } @@ -606,7 +502,6 @@ } case STORE_DEREF: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } @@ -616,7 +511,6 @@ } case BUILD_STRING: { - (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); stack_pointer[-1] = NULL; @@ -624,7 +518,6 @@ } case BUILD_TUPLE: { - (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); stack_pointer[-1] = NULL; @@ -632,7 +525,6 @@ } case BUILD_LIST: { - (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); stack_pointer[-1] = NULL; @@ -640,19 +532,16 @@ } case LIST_EXTEND: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case SET_UPDATE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case BUILD_SET: { - (stack_pointer - oparg) = (PyObject **)NULL; STACK_SHRINK(oparg); STACK_GROW(1); stack_pointer[-1] = NULL; @@ -660,7 +549,6 @@ } case BUILD_MAP: { - (stack_pointer - oparg*2) = (PyObject **)NULL; STACK_SHRINK(oparg*2); STACK_GROW(1); stack_pointer[-1] = NULL; @@ -672,28 +560,22 @@ } case BUILD_CONST_KEY_MAP: { - stack_pointer[-1] = NULL; - (stack_pointer - (1 + oparg)) = (PyObject **)NULL; STACK_SHRINK(oparg); stack_pointer[-1] = NULL; break; } case DICT_UPDATE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case DICT_MERGE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case MAP_ADD: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } @@ -701,46 +583,38 @@ case INSTRUMENTED_LOAD_SUPER_ATTR: { STACK_SHRINK(2); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_SUPER_ATTR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(2); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_SUPER_ATTR_ATTR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(2); STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_SUPER_ATTR_METHOD: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_ATTR: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } @@ -753,147 +627,117 @@ } case _LOAD_ATTR_INSTANCE_VALUE: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_MODULE: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_WITH_HINT: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_SLOT: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_CLASS: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_PROPERTY: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN: { - stack_pointer[-1] = NULL; STACK_GROW(((oparg & 1) ? 1 : 0)); + stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; break; } case STORE_ATTR_INSTANCE_VALUE: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case STORE_ATTR_WITH_HINT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case STORE_ATTR_SLOT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(2); break; } case COMPARE_OP: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case COMPARE_OP_FLOAT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case COMPARE_OP_INT: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case COMPARE_OP_STR: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case IS_OP: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case CONTAINS_OP: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case CHECK_EG_MATCH: { - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; break; } case CHECK_EXC_MATCH: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case IMPORT_NAME: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; @@ -918,19 +762,16 @@ } case POP_JUMP_IF_FALSE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case POP_JUMP_IF_TRUE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case IS_NONE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } @@ -946,9 +787,6 @@ } case MATCH_CLASS: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; - stack_pointer[-3] = NULL; STACK_SHRINK(2); stack_pointer[-1] = NULL; break; @@ -973,13 +811,11 @@ } case GET_ITER: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case GET_YIELD_FROM_ITER: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } @@ -1061,18 +897,16 @@ } case BEFORE_ASYNC_WITH: { - stack_pointer[-1] = NULL; STACK_GROW(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } case BEFORE_WITH: { - stack_pointer[-1] = NULL; STACK_GROW(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } @@ -1083,48 +917,42 @@ } case PUSH_EXC_INFO: { - stack_pointer[-1] = NULL; STACK_GROW(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_ATTR_METHOD_WITH_VALUES: { - stack_pointer[-1] = NULL; STACK_GROW(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_ATTR_METHOD_NO_DICT: { - stack_pointer[-1] = NULL; STACK_GROW(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } case LOAD_ATTR_NONDESCRIPTOR_WITH_VALUES: { - stack_pointer[-1] = NULL; - stack_pointer[-1] = NULL; + stack_pointer[-1 - (0 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; break; } case LOAD_ATTR_NONDESCRIPTOR_NO_DICT: { - stack_pointer[-1] = NULL; - stack_pointer[-1] = NULL; + stack_pointer[-1 - (0 ? 1 : 0)] = NULL; stack_pointer[-1] = NULL; break; } case LOAD_ATTR_METHOD_LAZY_DICT: { - stack_pointer[-1] = NULL; STACK_GROW(1); - stack_pointer[-1] = NULL; stack_pointer[-2] = NULL; + stack_pointer[-1] = NULL; break; } @@ -1137,9 +965,6 @@ } case CALL: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1148,9 +973,6 @@ } case CALL_BOUND_METHOD_EXACT_ARGS: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1158,9 +980,6 @@ } case CALL_PY_EXACT_ARGS: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1168,9 +987,6 @@ } case CALL_PY_WITH_DEFAULTS: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1178,9 +994,6 @@ } case CALL_NO_KW_TYPE_1: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1188,9 +1001,6 @@ } case CALL_NO_KW_STR_1: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1199,9 +1009,6 @@ } case CALL_NO_KW_TUPLE_1: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1210,9 +1017,6 @@ } case CALL_NO_KW_ALLOC_AND_ENTER_INIT: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1220,15 +1024,11 @@ } case EXIT_INIT_CHECK: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case CALL_BUILTIN_CLASS: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1237,9 +1037,6 @@ } case CALL_NO_KW_BUILTIN_O: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1248,9 +1045,6 @@ } case CALL_NO_KW_BUILTIN_FAST: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1259,9 +1053,6 @@ } case CALL_BUILTIN_FAST_WITH_KEYWORDS: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1270,9 +1061,6 @@ } case CALL_NO_KW_LEN: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1280,9 +1068,6 @@ } case CALL_NO_KW_ISINSTANCE: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1290,9 +1075,6 @@ } case CALL_NO_KW_LIST_APPEND: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1300,9 +1082,6 @@ } case CALL_NO_KW_METHOD_DESCRIPTOR_O: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1311,9 +1090,6 @@ } case CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1322,9 +1098,6 @@ } case CALL_NO_KW_METHOD_DESCRIPTOR_NOARGS: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1333,9 +1106,6 @@ } case CALL_NO_KW_METHOD_DESCRIPTOR_FAST: { - (stack_pointer - oparg) = (PyObject **)NULL; - stack_pointer[-(1 + oparg)] = NULL; - stack_pointer[-(2 + oparg)] = NULL; STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1348,10 +1118,6 @@ } case CALL_FUNCTION_EX: { - (oparg & 1) ? stack_pointer[-(((oparg & 1) ? 1 : 0))] : NULL = NULL; - stack_pointer[-(1 + ((oparg & 1) ? 1 : 0))] = NULL; - stack_pointer[-(2 + ((oparg & 1) ? 1 : 0))] = NULL; - stack_pointer[-(3 + ((oparg & 1) ? 1 : 0))] = NULL; STACK_SHRINK(((oparg & 1) ? 1 : 0)); STACK_SHRINK(2); stack_pointer[-1] = NULL; @@ -1360,14 +1126,11 @@ } case MAKE_FUNCTION: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case SET_FUNCTION_ATTRIBUTE: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; @@ -1378,9 +1141,6 @@ } case BUILD_SLICE: { - (oparg == 3) ? stack_pointer[-(((oparg == 3) ? 1 : 0))] : NULL = NULL; - stack_pointer[-(1 + ((oparg == 3) ? 1 : 0))] = NULL; - stack_pointer[-(2 + ((oparg == 3) ? 1 : 0))] = NULL; STACK_SHRINK(((oparg == 3) ? 1 : 0)); STACK_SHRINK(1); stack_pointer[-1] = NULL; @@ -1388,20 +1148,16 @@ } case CONVERT_VALUE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case FORMAT_SIMPLE: { - stack_pointer[-1] = NULL; stack_pointer[-1] = NULL; break; } case FORMAT_WITH_SPEC: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; @@ -1414,20 +1170,14 @@ } case BINARY_OP: { - stack_pointer[-1] = NULL; - stack_pointer[-2] = NULL; STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } case SWAP: { + stack_pointer[-2 - (oparg-2)] = NULL; stack_pointer[-1] = NULL; - (stack_pointer - (1 + (oparg-2))) = (PyObject **)NULL; - stack_pointer[-(2 + (oparg-2))] = NULL; - stack_pointer[-1] = NULL; - stack_pointer - (1 + (oparg-2)) = (PyObject **)NULL; - stack_pointer[-(2 + (oparg-2))] = NULL; break; } @@ -1472,13 +1222,11 @@ } case _POP_JUMP_IF_FALSE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } case _POP_JUMP_IF_TRUE: { - stack_pointer[-1] = NULL; STACK_SHRINK(1); break; } diff --git a/Tools/cases_generator/instructions.py b/Tools/cases_generator/instructions.py index c10dfd241684f5..a10e8f41ab67db 100644 --- a/Tools/cases_generator/instructions.py +++ b/Tools/cases_generator/instructions.py @@ -263,49 +263,8 @@ def write(self, out: Formatter, tier: Tiers = TIER_ONE) -> None: f"static_assert({cache_size} == " f'{self.cache_offset}, "incorrect cache size");' ) - # NULL out inputs, unless it's the same as in the output, - # Write input stack effect variable declarations and initializations. - ieffects = list(reversed(self.input_effects)) - for i, ieffect in enumerate(ieffects): - if ieffect.name in self.unmoved_names: - continue - isize = string_effect_size( - list_effect_size([ieff for ieff in ieffects[: i + 1]]) - ) - if ieffect.size: - src = StackEffect( - f"(stack_pointer - {maybe_parenthesize(isize)})", "PyObject **" - ) - elif ieffect.cond: - src = StackEffect( - f"({ieffect.cond}) ? stack_pointer[-{maybe_parenthesize(isize)}] : NULL", - "", - ) - else: - src = StackEffect(f"stack_pointer[-{maybe_parenthesize(isize)}]", "") - out.assign(src, parsing.StackEffect("NULL")) - # Write net stack growth/shrinkage - out.stack_adjust( - [ieff for ieff in self.input_effects], - [oeff for oeff in self.output_effects], - ) - - # NULL out outputs, unless it's same as input. - oeffects = list(reversed(self.output_effects)) - for i, oeffect in enumerate(oeffects): - if oeffect.name in self.unmoved_names: - continue - osize = string_effect_size( - list_effect_size([oeff for oeff in oeffects[: i + 1]]) - ) - if oeffect.size: - dst = StackEffect( - f"stack_pointer - {maybe_parenthesize(osize)}", "PyObject **" - ) - else: - dst = StackEffect(f"stack_pointer[-{maybe_parenthesize(osize)}]", "") - out.assign(dst, parsing.StackEffect("NULL")) + stacking.write_single_instr_for_abstract_interp(self, out) def write_body( self, diff --git a/Tools/cases_generator/stacking.py b/Tools/cases_generator/stacking.py index 23eca3037f896d..8ae08f70904305 100644 --- a/Tools/cases_generator/stacking.py +++ b/Tools/cases_generator/stacking.py @@ -398,3 +398,39 @@ def write_components( ), poke.effect, ) + + +def write_single_instr_for_abstract_interp( + instr: Instruction, out: Formatter +): + try: + _write_components_for_abstract_interp( + [Component(instr, instr.active_caches)], + out, + ) + except AssertionError as err: + raise AssertionError(f"Error writing abstract instruction {instr.name}") from err + + +def _write_components_for_abstract_interp( + parts: list[Component], + out: Formatter, +): + managers = get_managers(parts) + for mgr in managers: + if mgr is managers[-1]: + out.stack_adjust(mgr.final_offset.deep, mgr.final_offset.high) + # Use clone() since adjust_inverse() mutates final_offset + mgr.adjust_inverse(mgr.final_offset.clone()) + # NULL out the output stack effects + for poke in mgr.pokes: + if not poke.effect.size and poke.effect.name not in mgr.instr.unmoved_names: + out.assign( + StackEffect( + poke.as_variable(), + poke.effect.type, + poke.effect.cond, + poke.effect.size, + ), + StackEffect("NULL"), + ) From 429276733ff98850eee575c7faf5bcee0b69ae2c Mon Sep 17 00:00:00 2001 From: Ken Jin <28750310+Fidget-Spinner@users.noreply.github.com> Date: Sat, 5 Aug 2023 01:31:21 +0800 Subject: [PATCH 14/14] remove unused stuff --- Python/abstract_interp_cases.c.h | 505 +++++++----------------- Tools/cases_generator/generate_cases.py | 14 +- 2 files changed, 150 insertions(+), 369 deletions(-) diff --git a/Python/abstract_interp_cases.c.h b/Python/abstract_interp_cases.c.h index 8356ad15299f8e..33e726cc78e17d 100644 --- a/Python/abstract_interp_cases.c.h +++ b/Python/abstract_interp_cases.c.h @@ -3,17 +3,13 @@ // Python/bytecodes.c // Do not edit! + case NOP: { break; } - case RESUME: { - break; - } - case INSTRUMENTED_RESUME: { - break; - } + case LOAD_FAST_CHECK: { STACK_GROW(1); @@ -21,24 +17,21 @@ break; } + case LOAD_FAST: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case LOAD_FAST_AND_CLEAR: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } - case LOAD_FAST_LOAD_FAST: { - STACK_GROW(2); - stack_pointer[-2] = NULL; - stack_pointer[-1] = NULL; - break; - } + case LOAD_CONST: { STACK_GROW(1); @@ -46,36 +39,28 @@ break; } + case STORE_FAST: { STACK_SHRINK(1); break; } - case STORE_FAST_LOAD_FAST: { - stack_pointer[-1] = NULL; - break; - } - case STORE_FAST_STORE_FAST: { - STACK_SHRINK(2); - break; - } + case POP_TOP: { STACK_SHRINK(1); break; } + case PUSH_NULL: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } - case INSTRUMENTED_END_FOR: { - STACK_SHRINK(2); - break; - } + case END_SEND: { STACK_SHRINK(1); @@ -83,119 +68,131 @@ break; } - case INSTRUMENTED_END_SEND: { - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } + case UNARY_NEGATIVE: { stack_pointer[-1] = NULL; break; } + case UNARY_NOT: { stack_pointer[-1] = NULL; break; } + case TO_BOOL: { stack_pointer[-1] = NULL; break; } + case TO_BOOL_BOOL: { break; } + case TO_BOOL_INT: { stack_pointer[-1] = NULL; break; } + case TO_BOOL_LIST: { stack_pointer[-1] = NULL; break; } + case TO_BOOL_NONE: { stack_pointer[-1] = NULL; break; } + case TO_BOOL_STR: { stack_pointer[-1] = NULL; break; } + case TO_BOOL_ALWAYS_TRUE: { stack_pointer[-1] = NULL; break; } + case UNARY_INVERT: { stack_pointer[-1] = NULL; break; } + case _GUARD_BOTH_INT: { break; } + case _BINARY_OP_MULTIPLY_INT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case _BINARY_OP_ADD_INT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case _BINARY_OP_SUBTRACT_INT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case _GUARD_BOTH_FLOAT: { break; } + case _BINARY_OP_MULTIPLY_FLOAT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case _BINARY_OP_ADD_FLOAT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case _BINARY_OP_SUBTRACT_FLOAT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case _GUARD_BOTH_UNICODE: { break; } + case _BINARY_OP_ADD_UNICODE: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } - case _BINARY_OP_INPLACE_ADD_UNICODE: { - STACK_SHRINK(2); - break; - } + case BINARY_SUBSCR: { STACK_SHRINK(1); @@ -203,167 +200,128 @@ break; } + case BINARY_SLICE: { STACK_SHRINK(2); stack_pointer[-1] = NULL; break; } + case STORE_SLICE: { STACK_SHRINK(4); break; } + case BINARY_SUBSCR_LIST_INT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case BINARY_SUBSCR_TUPLE_INT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case BINARY_SUBSCR_DICT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } - case BINARY_SUBSCR_GETITEM: { - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } + case LIST_APPEND: { STACK_SHRINK(1); break; } + case SET_ADD: { STACK_SHRINK(1); break; } + case STORE_SUBSCR: { STACK_SHRINK(3); break; } + case STORE_SUBSCR_LIST_INT: { STACK_SHRINK(3); break; } + case STORE_SUBSCR_DICT: { STACK_SHRINK(3); break; } + case DELETE_SUBSCR: { STACK_SHRINK(2); break; } + case CALL_INTRINSIC_1: { stack_pointer[-1] = NULL; break; } + case CALL_INTRINSIC_2: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } - case RAISE_VARARGS: { - STACK_SHRINK(oparg); - break; - } - case INTERPRETER_EXIT: { - STACK_SHRINK(1); - break; - } - case RETURN_VALUE: { - STACK_SHRINK(1); - break; - } - case INSTRUMENTED_RETURN_VALUE: { - STACK_SHRINK(1); - break; - } - case RETURN_CONST: { - break; - } - case INSTRUMENTED_RETURN_CONST: { - break; - } + case GET_AITER: { stack_pointer[-1] = NULL; break; } + case GET_ANEXT: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case GET_AWAITABLE: { stack_pointer[-1] = NULL; break; } - case SEND: { - stack_pointer[-1] = NULL; - break; - } - case SEND_GEN: { - stack_pointer[-1] = NULL; - break; - } - case INSTRUMENTED_YIELD_VALUE: { - stack_pointer[-1] = NULL; - break; - } - case YIELD_VALUE: { - stack_pointer[-1] = NULL; - break; - } + case POP_EXCEPT: { STACK_SHRINK(1); break; } - case RERAISE: { - STACK_SHRINK(1); - break; - } - case END_ASYNC_FOR: { - STACK_SHRINK(2); - break; - } - case CLEANUP_THROW: { - STACK_SHRINK(1); - stack_pointer[-2] = NULL; - stack_pointer[-1] = NULL; - break; - } + case LOAD_ASSERTION_ERROR: { STACK_GROW(1); @@ -371,81 +329,96 @@ break; } + case LOAD_BUILD_CLASS: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case STORE_NAME: { STACK_SHRINK(1); break; } + case DELETE_NAME: { break; } + case UNPACK_SEQUENCE: { STACK_SHRINK(1); STACK_GROW(oparg); break; } + case UNPACK_SEQUENCE_TWO_TUPLE: { STACK_SHRINK(1); STACK_GROW(oparg); break; } + case UNPACK_SEQUENCE_TUPLE: { STACK_SHRINK(1); STACK_GROW(oparg); break; } + case UNPACK_SEQUENCE_LIST: { STACK_SHRINK(1); STACK_GROW(oparg); break; } + case UNPACK_EX: { STACK_GROW((oparg & 0xFF) + (oparg >> 8)); stack_pointer[-1 - (oparg >> 8)] = NULL; break; } + case STORE_ATTR: { STACK_SHRINK(2); break; } + case DELETE_ATTR: { STACK_SHRINK(1); break; } + case STORE_GLOBAL: { STACK_SHRINK(1); break; } + case DELETE_GLOBAL: { break; } + case _LOAD_LOCALS: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case _LOAD_FROM_DICT_OR_GLOBALS: { stack_pointer[-1] = NULL; break; } + case LOAD_GLOBAL: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); @@ -454,14 +427,17 @@ break; } + case _GUARD_GLOBALS_VERSION: { break; } + case _GUARD_BUILTINS_VERSION: { break; } + case _LOAD_GLOBAL_MODULE: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); @@ -470,6 +446,7 @@ break; } + case _LOAD_GLOBAL_BUILTINS: { STACK_GROW(1); STACK_GROW(((oparg & 1) ? 1 : 0)); @@ -478,38 +455,42 @@ break; } + case DELETE_FAST: { break; } - case MAKE_CELL: { - break; - } + case DELETE_DEREF: { break; } + case LOAD_FROM_DICT_OR_DEREF: { stack_pointer[-1] = NULL; break; } + case LOAD_DEREF: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case STORE_DEREF: { STACK_SHRINK(1); break; } + case COPY_FREE_VARS: { break; } + case BUILD_STRING: { STACK_SHRINK(oparg); STACK_GROW(1); @@ -517,6 +498,7 @@ break; } + case BUILD_TUPLE: { STACK_SHRINK(oparg); STACK_GROW(1); @@ -524,6 +506,7 @@ break; } + case BUILD_LIST: { STACK_SHRINK(oparg); STACK_GROW(1); @@ -531,16 +514,19 @@ break; } + case LIST_EXTEND: { STACK_SHRINK(1); break; } + case SET_UPDATE: { STACK_SHRINK(1); break; } + case BUILD_SET: { STACK_SHRINK(oparg); STACK_GROW(1); @@ -548,6 +534,7 @@ break; } + case BUILD_MAP: { STACK_SHRINK(oparg*2); STACK_GROW(1); @@ -555,46 +542,38 @@ break; } + case SETUP_ANNOTATIONS: { break; } + case BUILD_CONST_KEY_MAP: { STACK_SHRINK(oparg); stack_pointer[-1] = NULL; break; } + case DICT_UPDATE: { STACK_SHRINK(1); break; } + case DICT_MERGE: { STACK_SHRINK(1); break; } + case MAP_ADD: { STACK_SHRINK(2); break; } - case INSTRUMENTED_LOAD_SUPER_ATTR: { - STACK_SHRINK(2); - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_SUPER_ATTR: { - STACK_SHRINK(2); - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } + case LOAD_SUPER_ATTR_ATTR: { STACK_SHRINK(2); @@ -604,6 +583,7 @@ break; } + case LOAD_SUPER_ATTR_METHOD: { STACK_SHRINK(1); stack_pointer[-2] = NULL; @@ -611,6 +591,7 @@ break; } + case LOAD_ATTR: { STACK_GROW(((oparg & 1) ? 1 : 0)); stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; @@ -618,14 +599,17 @@ break; } + case _GUARD_TYPE_VERSION: { break; } + case _CHECK_MANAGED_OBJECT_HAS_VALUES: { break; } + case _LOAD_ATTR_INSTANCE_VALUE: { STACK_GROW(((oparg & 1) ? 1 : 0)); stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; @@ -633,62 +617,15 @@ break; } - case LOAD_ATTR_MODULE: { - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_WITH_HINT: { - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_SLOT: { - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_CLASS: { - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_PROPERTY: { - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN: { - STACK_GROW(((oparg & 1) ? 1 : 0)); - stack_pointer[-1 - (oparg & 1 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case STORE_ATTR_INSTANCE_VALUE: { - STACK_SHRINK(2); - break; - } - case STORE_ATTR_WITH_HINT: { - STACK_SHRINK(2); - break; - } - case STORE_ATTR_SLOT: { - STACK_SHRINK(2); - break; - } + case COMPARE_OP: { STACK_SHRINK(1); @@ -696,89 +633,68 @@ break; } + case COMPARE_OP_FLOAT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case COMPARE_OP_INT: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case COMPARE_OP_STR: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case IS_OP: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case CONTAINS_OP: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case CHECK_EG_MATCH: { stack_pointer[-2] = NULL; stack_pointer[-1] = NULL; break; } + case CHECK_EXC_MATCH: { stack_pointer[-1] = NULL; break; } - case IMPORT_NAME: { - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } - case IMPORT_FROM: { - STACK_GROW(1); - stack_pointer[-1] = NULL; - break; - } - case JUMP_FORWARD: { - break; - } - case JUMP_BACKWARD: { - break; - } - case ENTER_EXECUTOR: { - break; - } - case POP_JUMP_IF_FALSE: { - STACK_SHRINK(1); - break; - } - case POP_JUMP_IF_TRUE: { - STACK_SHRINK(1); - break; - } + case IS_NONE: { stack_pointer[-1] = NULL; break; } - case JUMP_BACKWARD_NO_INTERRUPT: { - break; - } + case GET_LEN: { STACK_GROW(1); @@ -786,57 +702,54 @@ break; } + case MATCH_CLASS: { STACK_SHRINK(2); stack_pointer[-1] = NULL; break; } + case MATCH_MAPPING: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case MATCH_SEQUENCE: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case MATCH_KEYS: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case GET_ITER: { stack_pointer[-1] = NULL; break; } + case GET_YIELD_FROM_ITER: { stack_pointer[-1] = NULL; break; } - case FOR_ITER: { - STACK_GROW(1); - stack_pointer[-1] = NULL; - break; - } - case INSTRUMENTED_FOR_ITER: { - break; - } + case _ITER_CHECK_LIST: { break; } - case _ITER_JUMP_LIST: { - break; - } + case _IS_ITER_EXHAUSTED_LIST: { STACK_GROW(1); @@ -844,19 +757,19 @@ break; } + case _ITER_NEXT_LIST: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case _ITER_CHECK_TUPLE: { break; } - case _ITER_JUMP_TUPLE: { - break; - } + case _IS_ITER_EXHAUSTED_TUPLE: { STACK_GROW(1); @@ -864,19 +777,19 @@ break; } + case _ITER_NEXT_TUPLE: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case _ITER_CHECK_RANGE: { break; } - case _ITER_JUMP_RANGE: { - break; - } + case _IS_ITER_EXHAUSTED_RANGE: { STACK_GROW(1); @@ -884,31 +797,16 @@ break; } + case _ITER_NEXT_RANGE: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } - case FOR_ITER_GEN: { - STACK_GROW(1); - stack_pointer[-1] = NULL; - break; - } - case BEFORE_ASYNC_WITH: { - STACK_GROW(1); - stack_pointer[-2] = NULL; - stack_pointer[-1] = NULL; - break; - } - case BEFORE_WITH: { - STACK_GROW(1); - stack_pointer[-2] = NULL; - stack_pointer[-1] = NULL; - break; - } + case WITH_EXCEPT_START: { STACK_GROW(1); @@ -916,6 +814,7 @@ break; } + case PUSH_EXC_INFO: { STACK_GROW(1); stack_pointer[-2] = NULL; @@ -923,75 +822,17 @@ break; } - case LOAD_ATTR_METHOD_WITH_VALUES: { - STACK_GROW(1); - stack_pointer[-2] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_METHOD_NO_DICT: { - STACK_GROW(1); - stack_pointer[-2] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_NONDESCRIPTOR_WITH_VALUES: { - stack_pointer[-1 - (0 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_NONDESCRIPTOR_NO_DICT: { - stack_pointer[-1 - (0 ? 1 : 0)] = NULL; - stack_pointer[-1] = NULL; - break; - } - case LOAD_ATTR_METHOD_LAZY_DICT: { - STACK_GROW(1); - stack_pointer[-2] = NULL; - stack_pointer[-1] = NULL; - break; - } - case KW_NAMES: { - break; - } - case INSTRUMENTED_CALL: { - break; - } - case CALL: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); - break; - } - case CALL_BOUND_METHOD_EXACT_ARGS: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } - case CALL_PY_EXACT_ARGS: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } - case CALL_PY_WITH_DEFAULTS: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } + case CALL_NO_KW_TYPE_1: { STACK_SHRINK(oparg); @@ -1000,65 +841,47 @@ break; } + case CALL_NO_KW_STR_1: { STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); break; } + case CALL_NO_KW_TUPLE_1: { STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); break; } - case CALL_NO_KW_ALLOC_AND_ENTER_INIT: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } + case EXIT_INIT_CHECK: { STACK_SHRINK(1); break; } - case CALL_BUILTIN_CLASS: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); - break; - } + case CALL_NO_KW_BUILTIN_O: { STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); break; } + case CALL_NO_KW_BUILTIN_FAST: { STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); break; } - case CALL_BUILTIN_FAST_WITH_KEYWORDS: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); - break; - } + case CALL_NO_KW_LEN: { STACK_SHRINK(oparg); @@ -1067,6 +890,7 @@ break; } + case CALL_NO_KW_ISINSTANCE: { STACK_SHRINK(oparg); STACK_SHRINK(1); @@ -1074,71 +898,48 @@ break; } - case CALL_NO_KW_LIST_APPEND: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - break; - } + case CALL_NO_KW_METHOD_DESCRIPTOR_O: { STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); break; } - case CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS: { - STACK_SHRINK(oparg); - STACK_SHRINK(1); - stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); - break; - } + case CALL_NO_KW_METHOD_DESCRIPTOR_NOARGS: { STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); break; } + case CALL_NO_KW_METHOD_DESCRIPTOR_FAST: { STACK_SHRINK(oparg); STACK_SHRINK(1); stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); break; } - case INSTRUMENTED_CALL_FUNCTION_EX: { - break; - } - case CALL_FUNCTION_EX: { - STACK_SHRINK(((oparg & 1) ? 1 : 0)); - STACK_SHRINK(2); - stack_pointer[-1] = NULL; - CHECK_EVAL_BREAKER(); - break; - } + case MAKE_FUNCTION: { stack_pointer[-1] = NULL; break; } + case SET_FUNCTION_ATTRIBUTE: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } - case RETURN_GENERATOR: { - break; - } + case BUILD_SLICE: { STACK_SHRINK(((oparg == 3) ? 1 : 0)); @@ -1147,99 +948,79 @@ break; } + case CONVERT_VALUE: { stack_pointer[-1] = NULL; break; } + case FORMAT_SIMPLE: { stack_pointer[-1] = NULL; break; } + case FORMAT_WITH_SPEC: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case COPY: { STACK_GROW(1); stack_pointer[-1] = NULL; break; } + case BINARY_OP: { STACK_SHRINK(1); stack_pointer[-1] = NULL; break; } + case SWAP: { stack_pointer[-2 - (oparg-2)] = NULL; stack_pointer[-1] = NULL; break; } - case INSTRUMENTED_INSTRUCTION: { - break; - } - case INSTRUMENTED_JUMP_FORWARD: { - break; - } - case INSTRUMENTED_JUMP_BACKWARD: { - break; - } - case INSTRUMENTED_POP_JUMP_IF_TRUE: { - break; - } - case INSTRUMENTED_POP_JUMP_IF_FALSE: { - break; - } - case INSTRUMENTED_POP_JUMP_IF_NONE: { - break; - } - case INSTRUMENTED_POP_JUMP_IF_NOT_NONE: { - break; - } - case EXTENDED_ARG: { - break; - } - case CACHE: { - break; - } - case RESERVED: { - break; - } + case _POP_JUMP_IF_FALSE: { STACK_SHRINK(1); break; } + case _POP_JUMP_IF_TRUE: { STACK_SHRINK(1); break; } + case JUMP_TO_TOP: { - CHECK_EVAL_BREAKER(); break; } + case SAVE_IP: { break; } + case EXIT_TRACE: { break; } diff --git a/Tools/cases_generator/generate_cases.py b/Tools/cases_generator/generate_cases.py index 832beedec05460..10351e7a768a56 100644 --- a/Tools/cases_generator/generate_cases.py +++ b/Tools/cases_generator/generate_cases.py @@ -629,13 +629,13 @@ def write_abstract_interpreter_instructions( case parsing.InstDef(): instr = AbstractInstruction(self.instrs[thing.name].inst) self.out.emit("") - with self.out.block(f"case {thing.name}:"): - instr.write(self.out, tier=TIER_TWO) - if instr.check_eval_breaker: - self.out.emit("CHECK_EVAL_BREAKER();") - self.out.emit("break;") - # elif instr.kind != "op": - # print(f"NOTE: {thing.name} is not a viable uop") + if instr.is_viable_uop(): + self.out.emit("") + with self.out.block(f"case {thing.name}:"): + instr.write(self.out, tier=TIER_TWO) + self.out.emit("break;") + # elif instr.kind != "op": + # print(f"NOTE: {thing.name} is not a viable uop") case parsing.Macro(): pass case parsing.Pseudo():