https://github.com/python/cpython/commit/f0f7b978be84c432139da1b107825aa2dc536854
commit: f0f7b978be84c432139da1b107825aa2dc536854
branch: main
author: Mark Shannon <[email protected]>
committer: markshannon <[email protected]>
date: 2025-01-20T15:49:15Z
summary:
GH-128939: Refactor JIT optimize structs (GH-128940)
files:
M Include/internal/pycore_optimizer.h
M Lib/test/test_capi/test_opt.py
M Lib/test/test_generated_cases.py
M Modules/_testinternalcapi.c
M Python/optimizer_analysis.c
M Python/optimizer_bytecodes.c
M Python/optimizer_cases.c.h
M Python/optimizer_symbols.c
M Tools/cases_generator/optimizer_generator.py
diff --git a/Include/internal/pycore_optimizer.h
b/Include/internal/pycore_optimizer.h
index a02b9ab4291bfc..03ce4d4491acd7 100644
--- a/Include/internal/pycore_optimizer.h
+++ b/Include/internal/pycore_optimizer.h
@@ -148,15 +148,6 @@ extern PyTypeObject _PyDefaultOptimizer_Type;
extern PyTypeObject _PyUOpExecutor_Type;
extern PyTypeObject _PyUOpOptimizer_Type;
-/* Symbols */
-/* See explanation in optimizer_symbols.c */
-
-struct _Py_UopsSymbol {
- int flags; // 0 bits: Top; 2 or more bits: Bottom
- PyTypeObject *typ; // Borrowed reference
- PyObject *const_val; // Owned reference (!)
- unsigned int type_version; // currently stores type version
-};
#define UOP_FORMAT_TARGET 0
#define UOP_FORMAT_JUMP 1
@@ -193,16 +184,63 @@ static inline uint16_t uop_get_error_target(const
_PyUOpInstruction *inst)
// handle before rejoining the rest of the program.
#define MAX_CHAIN_DEPTH 4
-typedef struct _Py_UopsSymbol _Py_UopsSymbol;
+/* Symbols */
+/* See explanation in optimizer_symbols.c */
+
+
+typedef enum _JitSymType {
+ JIT_SYM_UNKNOWN_TAG = 1,
+ JIT_SYM_NULL_TAG = 2,
+ JIT_SYM_NON_NULL_TAG = 3,
+ JIT_SYM_BOTTOM_TAG = 4,
+ JIT_SYM_TYPE_VERSION_TAG = 5,
+ JIT_SYM_KNOWN_CLASS_TAG = 6,
+ JIT_SYM_KNOWN_VALUE_TAG = 7,
+ JIT_SYM_TUPLE_TAG = 8,
+} JitSymType;
+
+typedef struct _jit_opt_known_class {
+ uint8_t tag;
+ uint32_t version;
+ PyTypeObject *type;
+} JitOptKnownClass;
+
+typedef struct _jit_opt_known_version {
+ uint8_t tag;
+ uint32_t version;
+} JitOptKnownVersion;
+
+typedef struct _jit_opt_known_value {
+ uint8_t tag;
+ PyObject *value;
+} JitOptKnownValue;
+
+#define MAX_SYMBOLIC_TUPLE_SIZE 7
+
+typedef struct _jit_opt_tuple {
+ uint8_t tag;
+ uint8_t length;
+ uint16_t items[MAX_SYMBOLIC_TUPLE_SIZE];
+} JitOptTuple;
+
+typedef union _jit_opt_symbol {
+ uint8_t tag;
+ JitOptKnownClass cls;
+ JitOptKnownValue value;
+ JitOptKnownVersion version;
+ JitOptTuple tuple;
+} JitOptSymbol;
+
+
struct _Py_UOpsAbstractFrame {
// Max stacklen
int stack_len;
int locals_len;
- _Py_UopsSymbol **stack_pointer;
- _Py_UopsSymbol **stack;
- _Py_UopsSymbol **locals;
+ JitOptSymbol **stack_pointer;
+ JitOptSymbol **stack;
+ JitOptSymbol **locals;
};
typedef struct _Py_UOpsAbstractFrame _Py_UOpsAbstractFrame;
@@ -210,10 +248,10 @@ typedef struct _Py_UOpsAbstractFrame
_Py_UOpsAbstractFrame;
typedef struct ty_arena {
int ty_curr_number;
int ty_max_number;
- _Py_UopsSymbol arena[TY_ARENA_SIZE];
+ JitOptSymbol arena[TY_ARENA_SIZE];
} ty_arena;
-struct _Py_UOpsContext {
+typedef struct _JitOptContext {
char done;
char out_of_space;
bool contradiction;
@@ -225,46 +263,47 @@ struct _Py_UOpsContext {
// Arena for the symbolic types.
ty_arena t_arena;
- _Py_UopsSymbol **n_consumed;
- _Py_UopsSymbol **limit;
- _Py_UopsSymbol *locals_and_stack[MAX_ABSTRACT_INTERP_SIZE];
-};
-
-typedef struct _Py_UOpsContext _Py_UOpsContext;
-
-extern bool _Py_uop_sym_is_null(_Py_UopsSymbol *sym);
-extern bool _Py_uop_sym_is_not_null(_Py_UopsSymbol *sym);
-extern bool _Py_uop_sym_is_const(_Py_UopsSymbol *sym);
-extern PyObject *_Py_uop_sym_get_const(_Py_UopsSymbol *sym);
-extern _Py_UopsSymbol *_Py_uop_sym_new_unknown(_Py_UOpsContext *ctx);
-extern _Py_UopsSymbol *_Py_uop_sym_new_not_null(_Py_UOpsContext *ctx);
-extern _Py_UopsSymbol *_Py_uop_sym_new_type(
- _Py_UOpsContext *ctx, PyTypeObject *typ);
-extern _Py_UopsSymbol *_Py_uop_sym_new_const(_Py_UOpsContext *ctx, PyObject
*const_val);
-extern _Py_UopsSymbol *_Py_uop_sym_new_null(_Py_UOpsContext *ctx);
-extern bool _Py_uop_sym_has_type(_Py_UopsSymbol *sym);
-extern bool _Py_uop_sym_matches_type(_Py_UopsSymbol *sym, PyTypeObject *typ);
-extern bool _Py_uop_sym_matches_type_version(_Py_UopsSymbol *sym, unsigned int
version);
-extern void _Py_uop_sym_set_null(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym);
-extern void _Py_uop_sym_set_non_null(_Py_UOpsContext *ctx, _Py_UopsSymbol
*sym);
-extern void _Py_uop_sym_set_type(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym,
PyTypeObject *typ);
-extern bool _Py_uop_sym_set_type_version(_Py_UOpsContext *ctx, _Py_UopsSymbol
*sym, unsigned int version);
-extern void _Py_uop_sym_set_const(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym,
PyObject *const_val);
-extern bool _Py_uop_sym_is_bottom(_Py_UopsSymbol *sym);
-extern int _Py_uop_sym_truthiness(_Py_UopsSymbol *sym);
-extern PyTypeObject *_Py_uop_sym_get_type(_Py_UopsSymbol *sym);
-
-
-extern void _Py_uop_abstractcontext_init(_Py_UOpsContext *ctx);
-extern void _Py_uop_abstractcontext_fini(_Py_UOpsContext *ctx);
+ JitOptSymbol **n_consumed;
+ JitOptSymbol **limit;
+ JitOptSymbol *locals_and_stack[MAX_ABSTRACT_INTERP_SIZE];
+} JitOptContext;
+
+extern bool _Py_uop_sym_is_null(JitOptSymbol *sym);
+extern bool _Py_uop_sym_is_not_null(JitOptSymbol *sym);
+extern bool _Py_uop_sym_is_const(JitOptSymbol *sym);
+extern PyObject *_Py_uop_sym_get_const(JitOptSymbol *sym);
+extern JitOptSymbol *_Py_uop_sym_new_unknown(JitOptContext *ctx);
+extern JitOptSymbol *_Py_uop_sym_new_not_null(JitOptContext *ctx);
+extern JitOptSymbol *_Py_uop_sym_new_type(
+ JitOptContext *ctx, PyTypeObject *typ);
+extern JitOptSymbol *_Py_uop_sym_new_const(JitOptContext *ctx, PyObject
*const_val);
+extern JitOptSymbol *_Py_uop_sym_new_null(JitOptContext *ctx);
+extern bool _Py_uop_sym_has_type(JitOptSymbol *sym);
+extern bool _Py_uop_sym_matches_type(JitOptSymbol *sym, PyTypeObject *typ);
+extern bool _Py_uop_sym_matches_type_version(JitOptSymbol *sym, unsigned int
version);
+extern void _Py_uop_sym_set_null(JitOptContext *ctx, JitOptSymbol *sym);
+extern void _Py_uop_sym_set_non_null(JitOptContext *ctx, JitOptSymbol *sym);
+extern void _Py_uop_sym_set_type(JitOptContext *ctx, JitOptSymbol *sym,
PyTypeObject *typ);
+extern bool _Py_uop_sym_set_type_version(JitOptContext *ctx, JitOptSymbol
*sym, unsigned int version);
+extern void _Py_uop_sym_set_const(JitOptContext *ctx, JitOptSymbol *sym,
PyObject *const_val);
+extern bool _Py_uop_sym_is_bottom(JitOptSymbol *sym);
+extern int _Py_uop_sym_truthiness(JitOptSymbol *sym);
+extern PyTypeObject *_Py_uop_sym_get_type(JitOptSymbol *sym);
+extern bool _Py_uop_sym_is_immortal(JitOptSymbol *sym);
+extern JitOptSymbol *_Py_uop_sym_new_tuple(JitOptContext *ctx, int size,
JitOptSymbol **args);
+extern JitOptSymbol *_Py_uop_sym_tuple_getitem(JitOptContext *ctx,
JitOptSymbol *sym, int item);
+extern int _Py_uop_sym_tuple_length(JitOptSymbol *sym);
+
+extern void _Py_uop_abstractcontext_init(JitOptContext *ctx);
+extern void _Py_uop_abstractcontext_fini(JitOptContext *ctx);
extern _Py_UOpsAbstractFrame *_Py_uop_frame_new(
- _Py_UOpsContext *ctx,
+ JitOptContext *ctx,
PyCodeObject *co,
int curr_stackentries,
- _Py_UopsSymbol **args,
+ JitOptSymbol **args,
int arg_len);
-extern int _Py_uop_frame_pop(_Py_UOpsContext *ctx);
+extern int _Py_uop_frame_pop(JitOptContext *ctx);
PyAPI_FUNC(PyObject *) _Py_uop_symbols_test(PyObject *self, PyObject *ignored);
diff --git a/Lib/test/test_capi/test_opt.py b/Lib/test/test_capi/test_opt.py
index a74b8fdd3923b7..9cfc6c142da6cd 100644
--- a/Lib/test/test_capi/test_opt.py
+++ b/Lib/test/test_capi/test_opt.py
@@ -1465,6 +1465,25 @@ def f(l: complex, r: complex) -> None:
with self.subTest(l=l, r=r, x=x, y=y):
script_helper.assert_python_ok("-c", s)
+ def test_symbols_flow_through_tuples(self):
+ def testfunc(n):
+ for _ in range(n):
+ a = 1
+ b = 2
+ t = a, b
+ x, y = t
+ r = x + y
+ return r
+
+ res, ex = self._run_with_optimizer(testfunc, TIER2_THRESHOLD)
+ self.assertEqual(res, 3)
+ self.assertIsNotNone(ex)
+ uops = get_opnames(ex)
+ self.assertIn("_BINARY_OP_ADD_INT", uops)
+ self.assertNotIn("_GUARD_BOTH_INT", uops)
+ self.assertNotIn("_GUARD_NOS_INT", uops)
+ self.assertNotIn("_GUARD_TOS_INT", uops)
+
def test_decref_escapes(self):
class Convert9999ToNone:
def __del__(self):
diff --git a/Lib/test/test_generated_cases.py b/Lib/test/test_generated_cases.py
index 7a50a29bb0126c..aa92145266961a 100644
--- a/Lib/test/test_generated_cases.py
+++ b/Lib/test/test_generated_cases.py
@@ -1842,8 +1842,8 @@ def test_overridden_abstract_args(self):
"""
output = """
case OP: {
- _Py_UopsSymbol *arg1;
- _Py_UopsSymbol *out;
+ JitOptSymbol *arg1;
+ JitOptSymbol *out;
arg1 = stack_pointer[-1];
out = EGGS(arg1);
stack_pointer[-1] = out;
@@ -1851,7 +1851,7 @@ def test_overridden_abstract_args(self):
}
case OP2: {
- _Py_UopsSymbol *out;
+ JitOptSymbol *out;
out = sym_new_not_null(ctx);
stack_pointer[-1] = out;
break;
@@ -1876,14 +1876,14 @@ def test_no_overridden_case(self):
"""
output = """
case OP: {
- _Py_UopsSymbol *out;
+ JitOptSymbol *out;
out = sym_new_not_null(ctx);
stack_pointer[-1] = out;
break;
}
case OP2: {
- _Py_UopsSymbol *out;
+ JitOptSymbol *out;
out = NULL;
stack_pointer[-1] = out;
break;
diff --git a/Modules/_testinternalcapi.c b/Modules/_testinternalcapi.c
index aae09f620b8898..e77df5b57b0504 100644
--- a/Modules/_testinternalcapi.c
+++ b/Modules/_testinternalcapi.c
@@ -27,7 +27,7 @@
#include "pycore_instruction_sequence.h" // _PyInstructionSequence_New()
#include "pycore_long.h" // _PyLong_Sign()
#include "pycore_object.h" // _PyObject_IsFreed()
-#include "pycore_optimizer.h" // _Py_UopsSymbol, etc.
+#include "pycore_optimizer.h" // JitOptSymbol, etc.
#include "pycore_pathconfig.h" // _PyPathConfig_ClearGlobal()
#include "pycore_pyerrors.h" // _PyErr_ChainExceptions1()
#include "pycore_pylifecycle.h" // _PyInterpreterConfig_AsDict()
diff --git a/Python/optimizer_analysis.c b/Python/optimizer_analysis.c
index 0ef15c630e91db..b9ac30ea04e4e8 100644
--- a/Python/optimizer_analysis.c
+++ b/Python/optimizer_analysis.c
@@ -368,13 +368,17 @@ remove_globals(_PyInterpreterFrame *frame,
_PyUOpInstruction *buffer,
#define sym_truthiness _Py_uop_sym_truthiness
#define frame_new _Py_uop_frame_new
#define frame_pop _Py_uop_frame_pop
+#define sym_new_tuple _Py_uop_sym_new_tuple
+#define sym_tuple_getitem _Py_uop_sym_tuple_getitem
+#define sym_tuple_length _Py_uop_sym_tuple_length
+#define sym_is_immortal _Py_uop_sym_is_immortal
static int
optimize_to_bool(
_PyUOpInstruction *this_instr,
- _Py_UOpsContext *ctx,
- _Py_UopsSymbol *value,
- _Py_UopsSymbol **result_ptr)
+ JitOptContext *ctx,
+ JitOptSymbol *value,
+ JitOptSymbol **result_ptr)
{
if (sym_matches_type(value, &PyBool_Type)) {
REPLACE_OP(this_instr, _NOP, 0, 0);
@@ -460,8 +464,8 @@ optimize_uops(
)
{
- _Py_UOpsContext context;
- _Py_UOpsContext *ctx = &context;
+ JitOptContext context;
+ JitOptContext *ctx = &context;
uint32_t opcode = UINT16_MAX;
int curr_space = 0;
int max_space = 0;
@@ -486,7 +490,7 @@ optimize_uops(
int oparg = this_instr->oparg;
opcode = this_instr->opcode;
- _Py_UopsSymbol **stack_pointer = ctx->frame->stack_pointer;
+ JitOptSymbol **stack_pointer = ctx->frame->stack_pointer;
#ifdef Py_DEBUG
if (get_lltrace() >= 3) {
diff --git a/Python/optimizer_bytecodes.c b/Python/optimizer_bytecodes.c
index 4d96ada5acf00f..881a607ca2aa29 100644
--- a/Python/optimizer_bytecodes.c
+++ b/Python/optimizer_bytecodes.c
@@ -6,8 +6,6 @@
#define op(name, ...) /* NAME is ignored */
-typedef struct _Py_UopsSymbol _Py_UopsSymbol;
-typedef struct _Py_UOpsContext _Py_UOpsContext;
typedef struct _Py_UOpsAbstractFrame _Py_UOpsAbstractFrame;
/* Shortened forms for convenience */
@@ -32,13 +30,17 @@ typedef struct _Py_UOpsAbstractFrame _Py_UOpsAbstractFrame;
#define sym_is_bottom _Py_uop_sym_is_bottom
#define frame_new _Py_uop_frame_new
#define frame_pop _Py_uop_frame_pop
+#define sym_new_tuple _Py_uop_sym_new_tuple
+#define sym_tuple_getitem _Py_uop_sym_tuple_getitem
+#define sym_tuple_length _Py_uop_sym_tuple_length
+#define sym_is_immortal _Py_uop_sym_is_immortal
extern int
optimize_to_bool(
_PyUOpInstruction *this_instr,
- _Py_UOpsContext *ctx,
- _Py_UopsSymbol *value,
- _Py_UopsSymbol **result_ptr);
+ JitOptContext *ctx,
+ JitOptSymbol *value,
+ JitOptSymbol **result_ptr);
extern void
eliminate_pop_guard(_PyUOpInstruction *this_instr, bool exit);
@@ -50,17 +52,17 @@ dummy_func(void) {
PyCodeObject *co;
int oparg;
- _Py_UopsSymbol *flag;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *res;
- _Py_UopsSymbol *iter;
- _Py_UopsSymbol *top;
- _Py_UopsSymbol *bottom;
+ JitOptSymbol *flag;
+ JitOptSymbol *left;
+ JitOptSymbol *right;
+ JitOptSymbol *value;
+ JitOptSymbol *res;
+ JitOptSymbol *iter;
+ JitOptSymbol *top;
+ JitOptSymbol *bottom;
_Py_UOpsAbstractFrame *frame;
_Py_UOpsAbstractFrame *new_frame;
- _Py_UOpsContext *ctx;
+ JitOptContext *ctx;
_PyUOpInstruction *this_instr;
_PyBloomFilter *dependencies;
int modified;
@@ -85,7 +87,7 @@ dummy_func(void) {
op(_LOAD_FAST_AND_CLEAR, (-- value)) {
value = GETLOCAL(oparg);
- _Py_UopsSymbol *temp = sym_new_null(ctx);
+ JitOptSymbol *temp = sym_new_null(ctx);
GETLOCAL(oparg) = temp;
}
@@ -365,7 +367,7 @@ dummy_func(void) {
}
op(_BINARY_OP_INPLACE_ADD_UNICODE, (left, right -- )) {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
if (sym_is_const(left) && sym_is_const(right) &&
sym_matches_type(left, &PyUnicode_Type) && sym_matches_type(right,
&PyUnicode_Type)) {
PyObject *temp = PyUnicode_Concat(sym_get_const(left),
sym_get_const(right));
@@ -949,6 +951,22 @@ dummy_func(void) {
res = sym_new_const(ctx, Py_True);
}
+ op(_BUILD_TUPLE, (values[oparg] -- tup)) {
+ tup = sym_new_tuple(ctx, oparg, values);
+ }
+
+ op(_UNPACK_SEQUENCE_TWO_TUPLE, (seq -- val1, val0)) {
+ val0 = sym_tuple_getitem(ctx, seq, 0);
+ val1 = sym_tuple_getitem(ctx, seq, 1);
+ }
+
+ op(_UNPACK_SEQUENCE_TUPLE, (seq -- values[oparg])) {
+ for (int i = 0; i < oparg; i++) {
+ values[i] = sym_tuple_getitem(ctx, seq, i);
+ }
+ }
+
+
// END BYTECODES //
}
diff --git a/Python/optimizer_cases.c.h b/Python/optimizer_cases.c.h
index 1f2b29c947434f..fa0b4ed4345320 100644
--- a/Python/optimizer_cases.c.h
+++ b/Python/optimizer_cases.c.h
@@ -26,7 +26,7 @@
/* _MONITOR_RESUME is not a viable micro-op for tier 2 */
case _LOAD_FAST_CHECK: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = GETLOCAL(oparg);
// We guarantee this will error - just bail and don't optimize it.
if (sym_is_null(value)) {
@@ -39,7 +39,7 @@
}
case _LOAD_FAST: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = GETLOCAL(oparg);
stack_pointer[0] = value;
stack_pointer += 1;
@@ -48,9 +48,9 @@
}
case _LOAD_FAST_AND_CLEAR: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = GETLOCAL(oparg);
- _Py_UopsSymbol *temp = sym_new_null(ctx);
+ JitOptSymbol *temp = sym_new_null(ctx);
GETLOCAL(oparg) = temp;
stack_pointer[0] = value;
stack_pointer += 1;
@@ -61,7 +61,7 @@
/* _LOAD_CONST is not a viable micro-op for tier 2 */
case _LOAD_CONST_MORTAL: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
PyObject *val = PyTuple_GET_ITEM(co->co_consts, this_instr->oparg);
int opcode = _Py_IsImmortal(val) ? _LOAD_CONST_INLINE_BORROW :
_LOAD_CONST_INLINE;
REPLACE_OP(this_instr, opcode, 0, (uintptr_t)val);
@@ -73,7 +73,7 @@
}
case _LOAD_CONST_IMMORTAL: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
PyObject *val = PyTuple_GET_ITEM(co->co_consts, this_instr->oparg);
REPLACE_OP(this_instr, _LOAD_CONST_INLINE_BORROW, 0,
(uintptr_t)val);
value = sym_new_const(ctx, val);
@@ -84,7 +84,7 @@
}
case _LOAD_SMALL_INT: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
PyObject *val = PyLong_FromLong(this_instr->oparg);
value = sym_new_const(ctx, val);
stack_pointer[0] = value;
@@ -94,7 +94,7 @@
}
case _STORE_FAST: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = stack_pointer[-1];
GETLOCAL(oparg) = value;
stack_pointer += -1;
@@ -109,7 +109,7 @@
}
case _PUSH_NULL: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_null(ctx);
stack_pointer[0] = res;
stack_pointer += 1;
@@ -124,7 +124,7 @@
}
case _END_SEND: {
- _Py_UopsSymbol *val;
+ JitOptSymbol *val;
val = sym_new_not_null(ctx);
stack_pointer[-2] = val;
stack_pointer += -1;
@@ -133,22 +133,22 @@
}
case _UNARY_NEGATIVE: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-1] = res;
break;
}
case _UNARY_NOT: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-1] = res;
break;
}
case _TO_BOOL: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *res;
+ JitOptSymbol *value;
+ JitOptSymbol *res;
value = stack_pointer[-1];
if (!optimize_to_bool(this_instr, ctx, value, &res)) {
res = sym_new_type(ctx, &PyBool_Type);
@@ -158,8 +158,8 @@
}
case _TO_BOOL_BOOL: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *res;
+ JitOptSymbol *value;
+ JitOptSymbol *res;
value = stack_pointer[-1];
if (!optimize_to_bool(this_instr, ctx, value, &res)) {
sym_set_type(value, &PyBool_Type);
@@ -170,8 +170,8 @@
}
case _TO_BOOL_INT: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *res;
+ JitOptSymbol *value;
+ JitOptSymbol *res;
value = stack_pointer[-1];
if (!optimize_to_bool(this_instr, ctx, value, &res)) {
sym_set_type(value, &PyLong_Type);
@@ -182,8 +182,8 @@
}
case _TO_BOOL_LIST: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *res;
+ JitOptSymbol *value;
+ JitOptSymbol *res;
value = stack_pointer[-1];
if (!optimize_to_bool(this_instr, ctx, value, &res)) {
sym_set_type(value, &PyList_Type);
@@ -194,8 +194,8 @@
}
case _TO_BOOL_NONE: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *res;
+ JitOptSymbol *value;
+ JitOptSymbol *res;
value = stack_pointer[-1];
if (!optimize_to_bool(this_instr, ctx, value, &res)) {
sym_set_const(value, Py_None);
@@ -206,8 +206,8 @@
}
case _TO_BOOL_STR: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *res;
+ JitOptSymbol *value;
+ JitOptSymbol *res;
value = stack_pointer[-1];
if (!optimize_to_bool(this_instr, ctx, value, &res)) {
res = sym_new_type(ctx, &PyBool_Type);
@@ -218,22 +218,22 @@
}
case _REPLACE_WITH_TRUE: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_const(ctx, Py_True);
stack_pointer[-1] = res;
break;
}
case _UNARY_INVERT: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-1] = res;
break;
}
case _GUARD_BOTH_INT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_matches_type(left, &PyLong_Type)) {
@@ -263,9 +263,9 @@
}
case _BINARY_OP_MULTIPLY_INT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_is_const(left) && sym_is_const(right) &&
@@ -296,9 +296,9 @@
}
case _BINARY_OP_ADD_INT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_is_const(left) && sym_is_const(right) &&
@@ -329,9 +329,9 @@
}
case _BINARY_OP_SUBTRACT_INT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_is_const(left) && sym_is_const(right) &&
@@ -362,8 +362,8 @@
}
case _GUARD_BOTH_FLOAT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_matches_type(left, &PyFloat_Type)) {
@@ -393,9 +393,9 @@
}
case _BINARY_OP_MULTIPLY_FLOAT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_is_const(left) && sym_is_const(right) &&
@@ -427,9 +427,9 @@
}
case _BINARY_OP_ADD_FLOAT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_is_const(left) && sym_is_const(right) &&
@@ -461,9 +461,9 @@
}
case _BINARY_OP_SUBTRACT_FLOAT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_is_const(left) && sym_is_const(right) &&
@@ -495,8 +495,8 @@
}
case _GUARD_BOTH_UNICODE: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_matches_type(left, &PyUnicode_Type) &&
@@ -509,9 +509,9 @@
}
case _BINARY_OP_ADD_UNICODE: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
if (sym_is_const(left) && sym_is_const(right) &&
@@ -536,11 +536,11 @@
}
case _BINARY_OP_INPLACE_ADD_UNICODE: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
right = stack_pointer[-1];
left = stack_pointer[-2];
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
if (sym_is_const(left) && sym_is_const(right) &&
sym_matches_type(left, &PyUnicode_Type) &&
sym_matches_type(right, &PyUnicode_Type)) {
PyObject *temp = PyUnicode_Concat(sym_get_const(left),
sym_get_const(right));
@@ -567,7 +567,7 @@
}
case _BINARY_OP_EXTEND: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -576,7 +576,7 @@
}
case _BINARY_SUBSCR: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -585,7 +585,7 @@
}
case _BINARY_SLICE: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-3] = res;
stack_pointer += -2;
@@ -600,7 +600,7 @@
}
case _BINARY_SUBSCR_LIST_INT: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -609,7 +609,7 @@
}
case _BINARY_SUBSCR_STR_INT: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -618,7 +618,7 @@
}
case _BINARY_SUBSCR_TUPLE_INT: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -627,7 +627,7 @@
}
case _BINARY_SUBSCR_DICT: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -636,7 +636,7 @@
}
case _BINARY_SUBSCR_CHECK_FUNC: {
- _Py_UopsSymbol *getitem;
+ JitOptSymbol *getitem;
getitem = sym_new_not_null(ctx);
stack_pointer[0] = getitem;
stack_pointer += 1;
@@ -645,9 +645,9 @@
}
case _BINARY_SUBSCR_INIT_CALL: {
- _Py_UopsSymbol *getitem;
- _Py_UopsSymbol *sub;
- _Py_UopsSymbol *container;
+ JitOptSymbol *getitem;
+ JitOptSymbol *sub;
+ JitOptSymbol *container;
_Py_UOpsAbstractFrame *new_frame;
getitem = stack_pointer[-1];
sub = stack_pointer[-2];
@@ -657,7 +657,7 @@
(void)getitem;
new_frame = NULL;
ctx->done = true;
- stack_pointer[-3] = (_Py_UopsSymbol *)new_frame;
+ stack_pointer[-3] = (JitOptSymbol *)new_frame;
stack_pointer += -2;
assert(WITHIN_STACK_BOUNDS());
break;
@@ -700,14 +700,14 @@
}
case _CALL_INTRINSIC_1: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-1] = res;
break;
}
case _CALL_INTRINSIC_2: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -716,8 +716,8 @@
}
case _RETURN_VALUE: {
- _Py_UopsSymbol *retval;
- _Py_UopsSymbol *res;
+ JitOptSymbol *retval;
+ JitOptSymbol *res;
retval = stack_pointer[-1];
stack_pointer += -1;
assert(WITHIN_STACK_BOUNDS());
@@ -744,14 +744,14 @@
}
case _GET_AITER: {
- _Py_UopsSymbol *iter;
+ JitOptSymbol *iter;
iter = sym_new_not_null(ctx);
stack_pointer[-1] = iter;
break;
}
case _GET_ANEXT: {
- _Py_UopsSymbol *awaitable;
+ JitOptSymbol *awaitable;
awaitable = sym_new_not_null(ctx);
stack_pointer[0] = awaitable;
stack_pointer += 1;
@@ -760,7 +760,7 @@
}
case _GET_AWAITABLE: {
- _Py_UopsSymbol *iter;
+ JitOptSymbol *iter;
iter = sym_new_not_null(ctx);
stack_pointer[-1] = iter;
break;
@@ -775,7 +775,7 @@
}
case _YIELD_VALUE: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_unknown(ctx);
stack_pointer[-1] = res;
break;
@@ -788,7 +788,7 @@
}
case _LOAD_COMMON_CONSTANT: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = sym_new_not_null(ctx);
stack_pointer[0] = value;
stack_pointer += 1;
@@ -797,7 +797,7 @@
}
case _LOAD_BUILD_CLASS: {
- _Py_UopsSymbol *bc;
+ JitOptSymbol *bc;
bc = sym_new_not_null(ctx);
stack_pointer[0] = bc;
stack_pointer += 1;
@@ -816,8 +816,8 @@
}
case _UNPACK_SEQUENCE: {
- _Py_UopsSymbol *seq;
- _Py_UopsSymbol **values;
+ JitOptSymbol *seq;
+ JitOptSymbol **values;
seq = stack_pointer[-1];
values = &stack_pointer[-1];
/* This has to be done manually */
@@ -831,10 +831,12 @@
}
case _UNPACK_SEQUENCE_TWO_TUPLE: {
- _Py_UopsSymbol *val1;
- _Py_UopsSymbol *val0;
- val1 = sym_new_not_null(ctx);
- val0 = sym_new_not_null(ctx);
+ JitOptSymbol *seq;
+ JitOptSymbol *val1;
+ JitOptSymbol *val0;
+ seq = stack_pointer[-1];
+ val0 = sym_tuple_getitem(ctx, seq, 0);
+ val1 = sym_tuple_getitem(ctx, seq, 1);
stack_pointer[-1] = val1;
stack_pointer[0] = val0;
stack_pointer += 1;
@@ -843,10 +845,12 @@
}
case _UNPACK_SEQUENCE_TUPLE: {
- _Py_UopsSymbol **values;
+ JitOptSymbol *seq;
+ JitOptSymbol **values;
+ seq = stack_pointer[-1];
values = &stack_pointer[-1];
- for (int _i = oparg; --_i >= 0;) {
- values[_i] = sym_new_not_null(ctx);
+ for (int i = 0; i < oparg; i++) {
+ values[i] = sym_tuple_getitem(ctx, seq, i);
}
stack_pointer += -1 + oparg;
assert(WITHIN_STACK_BOUNDS());
@@ -854,7 +858,7 @@
}
case _UNPACK_SEQUENCE_LIST: {
- _Py_UopsSymbol **values;
+ JitOptSymbol **values;
values = &stack_pointer[-1];
for (int _i = oparg; --_i >= 0;) {
values[_i] = sym_new_not_null(ctx);
@@ -865,8 +869,8 @@
}
case _UNPACK_EX: {
- _Py_UopsSymbol *seq;
- _Py_UopsSymbol **values;
+ JitOptSymbol *seq;
+ JitOptSymbol **values;
seq = stack_pointer[-1];
values = &stack_pointer[-1];
/* This has to be done manually */
@@ -903,7 +907,7 @@
}
case _LOAD_LOCALS: {
- _Py_UopsSymbol *locals;
+ JitOptSymbol *locals;
locals = sym_new_not_null(ctx);
stack_pointer[0] = locals;
stack_pointer += 1;
@@ -914,7 +918,7 @@
/* _LOAD_FROM_DICT_OR_GLOBALS is not a viable micro-op for tier 2 */
case _LOAD_NAME: {
- _Py_UopsSymbol *v;
+ JitOptSymbol *v;
v = sym_new_not_null(ctx);
stack_pointer[0] = v;
stack_pointer += 1;
@@ -923,8 +927,8 @@
}
case _LOAD_GLOBAL: {
- _Py_UopsSymbol **res;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol **res;
+ JitOptSymbol *null = NULL;
res = &stack_pointer[0];
res[0] = sym_new_not_null(ctx);
null = sym_new_null(ctx);
@@ -939,7 +943,7 @@
}
case _GUARD_GLOBALS_VERSION_PUSH_KEYS: {
- _Py_UopsSymbol *globals_keys;
+ JitOptSymbol *globals_keys;
uint16_t version = (uint16_t)this_instr->operand0;
globals_keys = sym_new_unknown(ctx);
(void)version;
@@ -950,7 +954,7 @@
}
case _GUARD_BUILTINS_VERSION_PUSH_KEYS: {
- _Py_UopsSymbol *builtins_keys;
+ JitOptSymbol *builtins_keys;
uint16_t version = (uint16_t)this_instr->operand0;
builtins_keys = sym_new_unknown(ctx);
(void)version;
@@ -961,8 +965,8 @@
}
case _LOAD_GLOBAL_MODULE_FROM_KEYS: {
- _Py_UopsSymbol *res;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *res;
+ JitOptSymbol *null = NULL;
res = sym_new_not_null(ctx);
null = sym_new_null(ctx);
stack_pointer[-1] = res;
@@ -973,8 +977,8 @@
}
case _LOAD_GLOBAL_BUILTINS_FROM_KEYS: {
- _Py_UopsSymbol *res;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *res;
+ JitOptSymbol *null = NULL;
res = sym_new_not_null(ctx);
null = sym_new_null(ctx);
stack_pointer[-1] = res;
@@ -997,14 +1001,14 @@
}
case _LOAD_FROM_DICT_OR_DEREF: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = sym_new_not_null(ctx);
stack_pointer[-1] = value;
break;
}
case _LOAD_DEREF: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = sym_new_not_null(ctx);
stack_pointer[0] = value;
stack_pointer += 1;
@@ -1023,7 +1027,7 @@
}
case _BUILD_STRING: {
- _Py_UopsSymbol *str;
+ JitOptSymbol *str;
str = sym_new_not_null(ctx);
stack_pointer[-oparg] = str;
stack_pointer += 1 - oparg;
@@ -1032,8 +1036,10 @@
}
case _BUILD_TUPLE: {
- _Py_UopsSymbol *tup;
- tup = sym_new_not_null(ctx);
+ JitOptSymbol **values;
+ JitOptSymbol *tup;
+ values = &stack_pointer[-oparg];
+ tup = sym_new_tuple(ctx, oparg, values);
stack_pointer[-oparg] = tup;
stack_pointer += 1 - oparg;
assert(WITHIN_STACK_BOUNDS());
@@ -1041,7 +1047,7 @@
}
case _BUILD_LIST: {
- _Py_UopsSymbol *list;
+ JitOptSymbol *list;
list = sym_new_not_null(ctx);
stack_pointer[-oparg] = list;
stack_pointer += 1 - oparg;
@@ -1062,7 +1068,7 @@
}
case _BUILD_SET: {
- _Py_UopsSymbol *set;
+ JitOptSymbol *set;
set = sym_new_not_null(ctx);
stack_pointer[-oparg] = set;
stack_pointer += 1 - oparg;
@@ -1071,7 +1077,7 @@
}
case _BUILD_MAP: {
- _Py_UopsSymbol *map;
+ JitOptSymbol *map;
map = sym_new_not_null(ctx);
stack_pointer[-oparg*2] = map;
stack_pointer += 1 - oparg*2;
@@ -1104,7 +1110,7 @@
/* _INSTRUMENTED_LOAD_SUPER_ATTR is not a viable micro-op for tier 2 */
case _LOAD_SUPER_ATTR_ATTR: {
- _Py_UopsSymbol *attr_st;
+ JitOptSymbol *attr_st;
attr_st = sym_new_not_null(ctx);
stack_pointer[-3] = attr_st;
stack_pointer += -2;
@@ -1113,8 +1119,8 @@
}
case _LOAD_SUPER_ATTR_METHOD: {
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *self_or_null;
+ JitOptSymbol *attr;
+ JitOptSymbol *self_or_null;
attr = sym_new_not_null(ctx);
self_or_null = sym_new_not_null(ctx);
stack_pointer[-3] = attr;
@@ -1125,9 +1131,9 @@
}
case _LOAD_ATTR: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *self_or_null = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *self_or_null = NULL;
owner = stack_pointer[-1];
(void)owner;
attr = sym_new_not_null(ctx);
@@ -1140,7 +1146,7 @@
}
case _GUARD_TYPE_VERSION: {
- _Py_UopsSymbol *owner;
+ JitOptSymbol *owner;
owner = stack_pointer[-1];
uint32_t type_version = (uint32_t)this_instr->operand0;
assert(type_version);
@@ -1174,9 +1180,9 @@
}
case _LOAD_ATTR_INSTANCE_VALUE: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *null = NULL;
owner = stack_pointer[-1];
uint16_t offset = (uint16_t)this_instr->operand0;
attr = sym_new_not_null(ctx);
@@ -1191,8 +1197,8 @@
}
case _CHECK_ATTR_MODULE_PUSH_KEYS: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *mod_keys;
+ JitOptSymbol *owner;
+ JitOptSymbol *mod_keys;
owner = stack_pointer[-1];
uint32_t dict_version = (uint32_t)this_instr->operand0;
(void)dict_version;
@@ -1222,9 +1228,9 @@
}
case _LOAD_ATTR_MODULE_FROM_KEYS: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *null = NULL;
owner = stack_pointer[-2];
uint16_t index = (uint16_t)this_instr->operand0;
(void)index;
@@ -1263,8 +1269,8 @@
}
case _CHECK_ATTR_WITH_HINT: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *dict;
+ JitOptSymbol *owner;
+ JitOptSymbol *dict;
owner = stack_pointer[-1];
dict = sym_new_not_null(ctx);
(void)owner;
@@ -1275,10 +1281,10 @@
}
case _LOAD_ATTR_WITH_HINT: {
- _Py_UopsSymbol *dict;
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *dict;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *null = NULL;
dict = stack_pointer[-1];
owner = stack_pointer[-2];
uint16_t hint = (uint16_t)this_instr->operand0;
@@ -1295,9 +1301,9 @@
}
case _LOAD_ATTR_SLOT: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *null = NULL;
owner = stack_pointer[-1];
uint16_t index = (uint16_t)this_instr->operand0;
attr = sym_new_not_null(ctx);
@@ -1316,9 +1322,9 @@
}
case _LOAD_ATTR_CLASS: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *null = NULL;
owner = stack_pointer[-1];
PyObject *descr = (PyObject *)this_instr->operand0;
attr = sym_new_not_null(ctx);
@@ -1333,7 +1339,7 @@
}
case _LOAD_ATTR_PROPERTY_FRAME: {
- _Py_UopsSymbol *owner;
+ JitOptSymbol *owner;
_Py_UOpsAbstractFrame *new_frame;
owner = stack_pointer[-1];
PyObject *fget = (PyObject *)this_instr->operand0;
@@ -1341,7 +1347,7 @@
(void)owner;
new_frame = NULL;
ctx->done = true;
- stack_pointer[-1] = (_Py_UopsSymbol *)new_frame;
+ stack_pointer[-1] = (JitOptSymbol *)new_frame;
break;
}
@@ -1370,9 +1376,9 @@
}
case _COMPARE_OP: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
(void)left;
@@ -1394,9 +1400,9 @@
}
case _COMPARE_OP_FLOAT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
(void)left;
@@ -1409,9 +1415,9 @@
}
case _COMPARE_OP_INT: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
(void)left;
@@ -1424,9 +1430,9 @@
}
case _COMPARE_OP_STR: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
(void)left;
@@ -1439,9 +1445,9 @@
}
case _IS_OP: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
(void)left;
@@ -1454,9 +1460,9 @@
}
case _CONTAINS_OP: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
(void)left;
@@ -1469,7 +1475,7 @@
}
case _CONTAINS_OP_SET: {
- _Py_UopsSymbol *b;
+ JitOptSymbol *b;
b = sym_new_not_null(ctx);
stack_pointer[-2] = b;
stack_pointer += -1;
@@ -1478,7 +1484,7 @@
}
case _CONTAINS_OP_DICT: {
- _Py_UopsSymbol *b;
+ JitOptSymbol *b;
b = sym_new_not_null(ctx);
stack_pointer[-2] = b;
stack_pointer += -1;
@@ -1487,8 +1493,8 @@
}
case _CHECK_EG_MATCH: {
- _Py_UopsSymbol *rest;
- _Py_UopsSymbol *match;
+ JitOptSymbol *rest;
+ JitOptSymbol *match;
rest = sym_new_not_null(ctx);
match = sym_new_not_null(ctx);
stack_pointer[-2] = rest;
@@ -1497,14 +1503,14 @@
}
case _CHECK_EXC_MATCH: {
- _Py_UopsSymbol *b;
+ JitOptSymbol *b;
b = sym_new_not_null(ctx);
stack_pointer[-1] = b;
break;
}
case _IMPORT_NAME: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -1513,7 +1519,7 @@
}
case _IMPORT_FROM: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[0] = res;
stack_pointer += 1;
@@ -1526,14 +1532,14 @@
/* _POP_JUMP_IF_TRUE is not a viable micro-op for tier 2 */
case _IS_NONE: {
- _Py_UopsSymbol *b;
+ JitOptSymbol *b;
b = sym_new_not_null(ctx);
stack_pointer[-1] = b;
break;
}
case _GET_LEN: {
- _Py_UopsSymbol *len;
+ JitOptSymbol *len;
len = sym_new_not_null(ctx);
stack_pointer[0] = len;
stack_pointer += 1;
@@ -1542,7 +1548,7 @@
}
case _MATCH_CLASS: {
- _Py_UopsSymbol *attrs;
+ JitOptSymbol *attrs;
attrs = sym_new_not_null(ctx);
stack_pointer[-3] = attrs;
stack_pointer += -2;
@@ -1551,7 +1557,7 @@
}
case _MATCH_MAPPING: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[0] = res;
stack_pointer += 1;
@@ -1560,7 +1566,7 @@
}
case _MATCH_SEQUENCE: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[0] = res;
stack_pointer += 1;
@@ -1569,7 +1575,7 @@
}
case _MATCH_KEYS: {
- _Py_UopsSymbol *values_or_none;
+ JitOptSymbol *values_or_none;
values_or_none = sym_new_not_null(ctx);
stack_pointer[0] = values_or_none;
stack_pointer += 1;
@@ -1578,14 +1584,14 @@
}
case _GET_ITER: {
- _Py_UopsSymbol *iter;
+ JitOptSymbol *iter;
iter = sym_new_not_null(ctx);
stack_pointer[-1] = iter;
break;
}
case _GET_YIELD_FROM_ITER: {
- _Py_UopsSymbol *iter;
+ JitOptSymbol *iter;
iter = sym_new_not_null(ctx);
stack_pointer[-1] = iter;
break;
@@ -1594,7 +1600,7 @@
/* _FOR_ITER is not a viable micro-op for tier 2 */
case _FOR_ITER_TIER_TWO: {
- _Py_UopsSymbol *next;
+ JitOptSymbol *next;
next = sym_new_not_null(ctx);
stack_pointer[0] = next;
stack_pointer += 1;
@@ -1615,7 +1621,7 @@
}
case _ITER_NEXT_LIST: {
- _Py_UopsSymbol *next;
+ JitOptSymbol *next;
next = sym_new_not_null(ctx);
stack_pointer[0] = next;
stack_pointer += 1;
@@ -1634,7 +1640,7 @@
}
case _ITER_NEXT_TUPLE: {
- _Py_UopsSymbol *next;
+ JitOptSymbol *next;
next = sym_new_not_null(ctx);
stack_pointer[0] = next;
stack_pointer += 1;
@@ -1653,8 +1659,8 @@
}
case _ITER_NEXT_RANGE: {
- _Py_UopsSymbol *iter;
- _Py_UopsSymbol *next;
+ JitOptSymbol *iter;
+ JitOptSymbol *next;
iter = stack_pointer[-1];
next = sym_new_type(ctx, &PyLong_Type);
(void)iter;
@@ -1671,9 +1677,9 @@
}
case _LOAD_SPECIAL: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *self_or_null;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *self_or_null;
owner = stack_pointer[-1];
(void)owner;
attr = sym_new_not_null(ctx);
@@ -1686,7 +1692,7 @@
}
case _WITH_EXCEPT_START: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[0] = res;
stack_pointer += 1;
@@ -1695,8 +1701,8 @@
}
case _PUSH_EXC_INFO: {
- _Py_UopsSymbol *prev_exc;
- _Py_UopsSymbol *new_exc;
+ JitOptSymbol *prev_exc;
+ JitOptSymbol *new_exc;
prev_exc = sym_new_not_null(ctx);
new_exc = sym_new_not_null(ctx);
stack_pointer[-1] = prev_exc;
@@ -1715,9 +1721,9 @@
}
case _LOAD_ATTR_METHOD_WITH_VALUES: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *self = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *self = NULL;
owner = stack_pointer[-1];
PyObject *descr = (PyObject *)this_instr->operand0;
(void)descr;
@@ -1731,9 +1737,9 @@
}
case _LOAD_ATTR_METHOD_NO_DICT: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *self = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *self = NULL;
owner = stack_pointer[-1];
PyObject *descr = (PyObject *)this_instr->operand0;
(void)descr;
@@ -1747,14 +1753,14 @@
}
case _LOAD_ATTR_NONDESCRIPTOR_WITH_VALUES: {
- _Py_UopsSymbol *attr;
+ JitOptSymbol *attr;
attr = sym_new_not_null(ctx);
stack_pointer[-1] = attr;
break;
}
case _LOAD_ATTR_NONDESCRIPTOR_NO_DICT: {
- _Py_UopsSymbol *attr;
+ JitOptSymbol *attr;
attr = sym_new_not_null(ctx);
stack_pointer[-1] = attr;
break;
@@ -1765,9 +1771,9 @@
}
case _LOAD_ATTR_METHOD_LAZY_DICT: {
- _Py_UopsSymbol *owner;
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *self = NULL;
+ JitOptSymbol *owner;
+ JitOptSymbol *attr;
+ JitOptSymbol *self = NULL;
owner = stack_pointer[-1];
PyObject *descr = (PyObject *)this_instr->operand0;
(void)descr;
@@ -1781,11 +1787,11 @@
}
case _MAYBE_EXPAND_METHOD: {
- _Py_UopsSymbol **args;
- _Py_UopsSymbol *self_or_null;
- _Py_UopsSymbol *callable;
- _Py_UopsSymbol *func;
- _Py_UopsSymbol *maybe_self;
+ JitOptSymbol **args;
+ JitOptSymbol *self_or_null;
+ JitOptSymbol *callable;
+ JitOptSymbol *func;
+ JitOptSymbol *maybe_self;
args = &stack_pointer[-oparg];
self_or_null = stack_pointer[-1 - oparg];
callable = stack_pointer[-2 - oparg];
@@ -1805,8 +1811,8 @@
/* _MONITOR_CALL is not a viable micro-op for tier 2 */
case _PY_FRAME_GENERAL: {
- _Py_UopsSymbol *self_or_null;
- _Py_UopsSymbol *callable;
+ JitOptSymbol *self_or_null;
+ JitOptSymbol *callable;
_Py_UOpsAbstractFrame *new_frame;
self_or_null = stack_pointer[-1 - oparg];
callable = stack_pointer[-2 - oparg];
@@ -1822,15 +1828,15 @@
break;
}
new_frame = frame_new(ctx, co, 0, NULL, 0);
- stack_pointer[0] = (_Py_UopsSymbol *)new_frame;
+ stack_pointer[0] = (JitOptSymbol *)new_frame;
stack_pointer += 1;
assert(WITHIN_STACK_BOUNDS());
break;
}
case _CHECK_FUNCTION_VERSION: {
- _Py_UopsSymbol *self_or_null;
- _Py_UopsSymbol *callable;
+ JitOptSymbol *self_or_null;
+ JitOptSymbol *callable;
self_or_null = stack_pointer[-1 - oparg];
callable = stack_pointer[-2 - oparg];
uint32_t func_version = (uint32_t)this_instr->operand0;
@@ -1853,8 +1859,8 @@
}
case _EXPAND_METHOD: {
- _Py_UopsSymbol **method;
- _Py_UopsSymbol **self;
+ JitOptSymbol **method;
+ JitOptSymbol **self;
method = &stack_pointer[-2 - oparg];
self = &stack_pointer[-1 - oparg];
method[0] = sym_new_not_null(ctx);
@@ -1867,7 +1873,7 @@
}
case _CALL_NON_PY_GENERAL: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -1876,8 +1882,8 @@
}
case _CHECK_CALL_BOUND_METHOD_EXACT_ARGS: {
- _Py_UopsSymbol *null;
- _Py_UopsSymbol *callable;
+ JitOptSymbol *null;
+ JitOptSymbol *callable;
null = stack_pointer[-1 - oparg];
callable = stack_pointer[-2 - oparg];
sym_set_null(null);
@@ -1886,9 +1892,9 @@
}
case _INIT_CALL_BOUND_METHOD_EXACT_ARGS: {
- _Py_UopsSymbol *callable;
- _Py_UopsSymbol *func;
- _Py_UopsSymbol *self;
+ JitOptSymbol *callable;
+ JitOptSymbol *func;
+ JitOptSymbol *self;
callable = stack_pointer[-2 - oparg];
(void)callable;
func = sym_new_not_null(ctx);
@@ -1908,8 +1914,8 @@
}
case _CHECK_FUNCTION_EXACT_ARGS: {
- _Py_UopsSymbol *self_or_null;
- _Py_UopsSymbol *callable;
+ JitOptSymbol *self_or_null;
+ JitOptSymbol *callable;
self_or_null = stack_pointer[-1 - oparg];
callable = stack_pointer[-2 - oparg];
assert(sym_matches_type(callable, &PyFunction_Type));
@@ -1933,9 +1939,9 @@
}
case _INIT_CALL_PY_EXACT_ARGS: {
- _Py_UopsSymbol **args;
- _Py_UopsSymbol *self_or_null;
- _Py_UopsSymbol *callable;
+ JitOptSymbol **args;
+ JitOptSymbol *self_or_null;
+ JitOptSymbol *callable;
_Py_UOpsAbstractFrame *new_frame;
args = &stack_pointer[-oparg];
self_or_null = stack_pointer[-1 - oparg];
@@ -1963,7 +1969,7 @@
} else {
new_frame = frame_new(ctx, co, 0, NULL, 0);
}
- stack_pointer[0] = (_Py_UopsSymbol *)new_frame;
+ stack_pointer[0] = (JitOptSymbol *)new_frame;
stack_pointer += 1;
assert(WITHIN_STACK_BOUNDS());
break;
@@ -2008,7 +2014,7 @@
}
case _CALL_TYPE_1: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-3] = res;
stack_pointer += -2;
@@ -2017,7 +2023,7 @@
}
case _CALL_STR_1: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-3] = res;
stack_pointer += -2;
@@ -2026,7 +2032,7 @@
}
case _CALL_TUPLE_1: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-3] = res;
stack_pointer += -2;
@@ -2035,11 +2041,11 @@
}
case _CHECK_AND_ALLOCATE_OBJECT: {
- _Py_UopsSymbol **args;
- _Py_UopsSymbol *null;
- _Py_UopsSymbol *callable;
- _Py_UopsSymbol *self;
- _Py_UopsSymbol *init;
+ JitOptSymbol **args;
+ JitOptSymbol *null;
+ JitOptSymbol *callable;
+ JitOptSymbol *self;
+ JitOptSymbol *init;
args = &stack_pointer[-oparg];
null = stack_pointer[-1 - oparg];
callable = stack_pointer[-2 - oparg];
@@ -2057,9 +2063,9 @@
}
case _CREATE_INIT_FRAME: {
- _Py_UopsSymbol **args;
- _Py_UopsSymbol *init;
- _Py_UopsSymbol *self;
+ JitOptSymbol **args;
+ JitOptSymbol *init;
+ JitOptSymbol *self;
_Py_UOpsAbstractFrame *init_frame;
args = &stack_pointer[-oparg];
init = stack_pointer[-1 - oparg];
@@ -2069,7 +2075,7 @@
(void)args;
init_frame = NULL;
ctx->done = true;
- stack_pointer[-2 - oparg] = (_Py_UopsSymbol *)init_frame;
+ stack_pointer[-2 - oparg] = (JitOptSymbol *)init_frame;
stack_pointer += -1 - oparg;
assert(WITHIN_STACK_BOUNDS());
break;
@@ -2082,7 +2088,7 @@
}
case _CALL_BUILTIN_CLASS: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2091,7 +2097,7 @@
}
case _CALL_BUILTIN_O: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2100,7 +2106,7 @@
}
case _CALL_BUILTIN_FAST: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2109,7 +2115,7 @@
}
case _CALL_BUILTIN_FAST_WITH_KEYWORDS: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2118,7 +2124,7 @@
}
case _CALL_LEN: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2127,7 +2133,7 @@
}
case _CALL_ISINSTANCE: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2142,7 +2148,7 @@
}
case _CALL_METHOD_DESCRIPTOR_O: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2151,7 +2157,7 @@
}
case _CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2160,7 +2166,7 @@
}
case _CALL_METHOD_DESCRIPTOR_NOARGS: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2169,7 +2175,7 @@
}
case _CALL_METHOD_DESCRIPTOR_FAST: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2 - oparg] = res;
stack_pointer += -1 - oparg;
@@ -2180,10 +2186,10 @@
/* _INSTRUMENTED_CALL_KW is not a viable micro-op for tier 2 */
case _MAYBE_EXPAND_METHOD_KW: {
- _Py_UopsSymbol **func;
- _Py_UopsSymbol **maybe_self;
- _Py_UopsSymbol **args;
- _Py_UopsSymbol *kwnames_out;
+ JitOptSymbol **func;
+ JitOptSymbol **maybe_self;
+ JitOptSymbol **args;
+ JitOptSymbol *kwnames_out;
func = &stack_pointer[-3 - oparg];
maybe_self = &stack_pointer[-2 - oparg];
args = &stack_pointer[-1 - oparg];
@@ -2200,10 +2206,10 @@
/* _DO_CALL_KW is not a viable micro-op for tier 2 */
case _PY_FRAME_KW: {
- _Py_UopsSymbol *kwnames;
- _Py_UopsSymbol **args;
- _Py_UopsSymbol *self_or_null;
- _Py_UopsSymbol *callable;
+ JitOptSymbol *kwnames;
+ JitOptSymbol **args;
+ JitOptSymbol *self_or_null;
+ JitOptSymbol *callable;
_Py_UOpsAbstractFrame *new_frame;
kwnames = stack_pointer[-1];
args = &stack_pointer[-1 - oparg];
@@ -2215,7 +2221,7 @@
(void)kwnames;
new_frame = NULL;
ctx->done = true;
- stack_pointer[-3 - oparg] = (_Py_UopsSymbol *)new_frame;
+ stack_pointer[-3 - oparg] = (JitOptSymbol *)new_frame;
stack_pointer += -2 - oparg;
assert(WITHIN_STACK_BOUNDS());
break;
@@ -2230,8 +2236,8 @@
}
case _EXPAND_METHOD_KW: {
- _Py_UopsSymbol **method;
- _Py_UopsSymbol **self;
+ JitOptSymbol **method;
+ JitOptSymbol **self;
method = &stack_pointer[-3 - oparg];
self = &stack_pointer[-2 - oparg];
method[0] = sym_new_not_null(ctx);
@@ -2244,7 +2250,7 @@
}
case _CALL_KW_NON_PY: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-3 - oparg] = res;
stack_pointer += -2 - oparg;
@@ -2255,8 +2261,8 @@
/* _INSTRUMENTED_CALL_FUNCTION_EX is not a viable micro-op for tier 2
*/
case _MAKE_CALLARGS_A_TUPLE: {
- _Py_UopsSymbol *tuple;
- _Py_UopsSymbol *kwargs_out = NULL;
+ JitOptSymbol *tuple;
+ JitOptSymbol *kwargs_out = NULL;
tuple = sym_new_not_null(ctx);
kwargs_out = sym_new_not_null(ctx);
stack_pointer[-1 - (oparg & 1)] = tuple;
@@ -2267,14 +2273,14 @@
/* _DO_CALL_FUNCTION_EX is not a viable micro-op for tier 2 */
case _MAKE_FUNCTION: {
- _Py_UopsSymbol *func;
+ JitOptSymbol *func;
func = sym_new_not_null(ctx);
stack_pointer[-1] = func;
break;
}
case _SET_FUNCTION_ATTRIBUTE: {
- _Py_UopsSymbol *func_out;
+ JitOptSymbol *func_out;
func_out = sym_new_not_null(ctx);
stack_pointer[-2] = func_out;
stack_pointer += -1;
@@ -2283,7 +2289,7 @@
}
case _RETURN_GENERATOR: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
ctx->frame->stack_pointer = stack_pointer;
frame_pop(ctx);
stack_pointer = ctx->frame->stack_pointer;
@@ -2307,7 +2313,7 @@
}
case _BUILD_SLICE: {
- _Py_UopsSymbol *slice;
+ JitOptSymbol *slice;
slice = sym_new_not_null(ctx);
stack_pointer[-2 - ((oparg == 3) ? 1 : 0)] = slice;
stack_pointer += -1 - ((oparg == 3) ? 1 : 0);
@@ -2316,21 +2322,21 @@
}
case _CONVERT_VALUE: {
- _Py_UopsSymbol *result;
+ JitOptSymbol *result;
result = sym_new_not_null(ctx);
stack_pointer[-1] = result;
break;
}
case _FORMAT_SIMPLE: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-1] = res;
break;
}
case _FORMAT_WITH_SPEC: {
- _Py_UopsSymbol *res;
+ JitOptSymbol *res;
res = sym_new_not_null(ctx);
stack_pointer[-2] = res;
stack_pointer += -1;
@@ -2339,8 +2345,8 @@
}
case _COPY: {
- _Py_UopsSymbol *bottom;
- _Py_UopsSymbol *top;
+ JitOptSymbol *bottom;
+ JitOptSymbol *top;
bottom = stack_pointer[-1 - (oparg-1)];
assert(oparg > 0);
top = bottom;
@@ -2351,9 +2357,9 @@
}
case _BINARY_OP: {
- _Py_UopsSymbol *right;
- _Py_UopsSymbol *left;
- _Py_UopsSymbol *res;
+ JitOptSymbol *right;
+ JitOptSymbol *left;
+ JitOptSymbol *res;
right = stack_pointer[-1];
left = stack_pointer[-2];
bool lhs_int = sym_matches_type(left, &PyLong_Type);
@@ -2426,10 +2432,10 @@
}
case _SWAP: {
- _Py_UopsSymbol *top_in;
- _Py_UopsSymbol *bottom_in;
- _Py_UopsSymbol *top_out;
- _Py_UopsSymbol *bottom_out;
+ JitOptSymbol *top_in;
+ JitOptSymbol *bottom_in;
+ JitOptSymbol *top_out;
+ JitOptSymbol *bottom_out;
top_in = stack_pointer[-1];
bottom_in = stack_pointer[-2 - (oparg-2)];
bottom_out = bottom_in;
@@ -2458,7 +2464,7 @@
/* _INSTRUMENTED_POP_JUMP_IF_NOT_NONE is not a viable micro-op for
tier 2 */
case _GUARD_IS_TRUE_POP: {
- _Py_UopsSymbol *flag;
+ JitOptSymbol *flag;
flag = stack_pointer[-1];
if (sym_is_const(flag)) {
PyObject *value = sym_get_const(flag);
@@ -2475,7 +2481,7 @@
}
case _GUARD_IS_FALSE_POP: {
- _Py_UopsSymbol *flag;
+ JitOptSymbol *flag;
flag = stack_pointer[-1];
if (sym_is_const(flag)) {
PyObject *value = sym_get_const(flag);
@@ -2492,7 +2498,7 @@
}
case _GUARD_IS_NONE_POP: {
- _Py_UopsSymbol *flag;
+ JitOptSymbol *flag;
flag = stack_pointer[-1];
if (sym_is_const(flag)) {
PyObject *value = sym_get_const(flag);
@@ -2517,7 +2523,7 @@
}
case _GUARD_IS_NOT_NONE_POP: {
- _Py_UopsSymbol *flag;
+ JitOptSymbol *flag;
flag = stack_pointer[-1];
if (sym_is_const(flag)) {
PyObject *value = sym_get_const(flag);
@@ -2575,7 +2581,7 @@
}
case _LOAD_CONST_INLINE: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
PyObject *ptr = (PyObject *)this_instr->operand0;
value = sym_new_const(ctx, ptr);
stack_pointer[0] = value;
@@ -2585,7 +2591,7 @@
}
case _LOAD_CONST_INLINE_BORROW: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
PyObject *ptr = (PyObject *)this_instr->operand0;
value = sym_new_const(ctx, ptr);
stack_pointer[0] = value;
@@ -2595,15 +2601,15 @@
}
case _POP_TOP_LOAD_CONST_INLINE_BORROW: {
- _Py_UopsSymbol *value;
+ JitOptSymbol *value;
value = sym_new_not_null(ctx);
stack_pointer[-1] = value;
break;
}
case _LOAD_CONST_INLINE_WITH_NULL: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *null;
+ JitOptSymbol *value;
+ JitOptSymbol *null;
PyObject *ptr = (PyObject *)this_instr->operand0;
value = sym_new_const(ctx, ptr);
null = sym_new_null(ctx);
@@ -2615,8 +2621,8 @@
}
case _LOAD_CONST_INLINE_BORROW_WITH_NULL: {
- _Py_UopsSymbol *value;
- _Py_UopsSymbol *null;
+ JitOptSymbol *value;
+ JitOptSymbol *null;
PyObject *ptr = (PyObject *)this_instr->operand0;
value = sym_new_const(ctx, ptr);
null = sym_new_null(ctx);
@@ -2632,8 +2638,8 @@
}
case _LOAD_GLOBAL_MODULE: {
- _Py_UopsSymbol *res;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *res;
+ JitOptSymbol *null = NULL;
res = sym_new_not_null(ctx);
null = sym_new_null(ctx);
stack_pointer[0] = res;
@@ -2644,8 +2650,8 @@
}
case _LOAD_GLOBAL_BUILTINS: {
- _Py_UopsSymbol *res;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *res;
+ JitOptSymbol *null = NULL;
res = sym_new_not_null(ctx);
null = sym_new_null(ctx);
stack_pointer[0] = res;
@@ -2656,8 +2662,8 @@
}
case _LOAD_ATTR_MODULE: {
- _Py_UopsSymbol *attr;
- _Py_UopsSymbol *null = NULL;
+ JitOptSymbol *attr;
+ JitOptSymbol *null = NULL;
attr = sym_new_not_null(ctx);
null = sym_new_null(ctx);
stack_pointer[-1] = attr;
diff --git a/Python/optimizer_symbols.c b/Python/optimizer_symbols.c
index 40cbf95e3d6d39..dcde8e7ce81577 100644
--- a/Python/optimizer_symbols.c
+++ b/Python/optimizer_symbols.c
@@ -28,11 +28,6 @@
- Bottom: IS_NULL and NOT_NULL flags set, type and const_val NULL.
*/
-// Flags for below.
-#define IS_NULL 1 << 0
-#define NOT_NULL 1 << 1
-#define NO_SPACE 1 << 2
-
#ifdef Py_DEBUG
static inline int get_lltrace(void) {
char *uop_debug = Py_GETENV("PYTHON_OPT_DEBUG");
@@ -48,187 +43,254 @@ static inline int get_lltrace(void) {
#define DPRINTF(level, ...)
#endif
-static _Py_UopsSymbol NO_SPACE_SYMBOL = {
- .flags = IS_NULL | NOT_NULL | NO_SPACE,
- .typ = NULL,
- .const_val = NULL,
- .type_version = 0,
+
+static JitOptSymbol NO_SPACE_SYMBOL = {
+ .tag = JIT_SYM_BOTTOM_TAG
};
-_Py_UopsSymbol *
-out_of_space(_Py_UOpsContext *ctx)
+JitOptSymbol *
+out_of_space(JitOptContext *ctx)
{
ctx->done = true;
ctx->out_of_space = true;
return &NO_SPACE_SYMBOL;
}
-static _Py_UopsSymbol *
-sym_new(_Py_UOpsContext *ctx)
+static JitOptSymbol *
+sym_new(JitOptContext *ctx)
{
- _Py_UopsSymbol *self = &ctx->t_arena.arena[ctx->t_arena.ty_curr_number];
+ JitOptSymbol *self = &ctx->t_arena.arena[ctx->t_arena.ty_curr_number];
if (ctx->t_arena.ty_curr_number >= ctx->t_arena.ty_max_number) {
OPT_STAT_INC(optimizer_failure_reason_no_memory);
DPRINTF(1, "out of space for symbolic expression type\n");
return NULL;
}
ctx->t_arena.ty_curr_number++;
- self->flags = 0;
- self->typ = NULL;
- self->const_val = NULL;
- self->type_version = 0;
-
+ self->tag = JIT_SYM_UNKNOWN_TAG;
return self;
}
static inline void
-sym_set_flag(_Py_UopsSymbol *sym, int flag)
-{
- sym->flags |= flag;
-}
-
-static inline void
-sym_set_bottom(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym)
+sym_set_bottom(JitOptContext *ctx, JitOptSymbol *sym)
{
- sym_set_flag(sym, IS_NULL | NOT_NULL);
- sym->typ = NULL;
- Py_CLEAR(sym->const_val);
+ sym->tag = JIT_SYM_BOTTOM_TAG;
ctx->done = true;
ctx->contradiction = true;
}
bool
-_Py_uop_sym_is_bottom(_Py_UopsSymbol *sym)
+_Py_uop_sym_is_bottom(JitOptSymbol *sym)
{
- if ((sym->flags & IS_NULL) && (sym->flags & NOT_NULL)) {
- assert(sym->flags == (IS_NULL | NOT_NULL));
- assert(sym->typ == NULL);
- assert(sym->const_val == NULL);
- return true;
- }
- return false;
+ return sym->tag == JIT_SYM_BOTTOM_TAG;
}
bool
-_Py_uop_sym_is_not_null(_Py_UopsSymbol *sym)
-{
- return sym->flags == NOT_NULL;
+_Py_uop_sym_is_not_null(JitOptSymbol *sym) {
+ return sym->tag == JIT_SYM_NON_NULL_TAG || sym->tag > JIT_SYM_BOTTOM_TAG;
}
bool
-_Py_uop_sym_is_null(_Py_UopsSymbol *sym)
+_Py_uop_sym_is_const(JitOptSymbol *sym)
{
- return sym->flags == IS_NULL;
+ return sym->tag == JIT_SYM_KNOWN_VALUE_TAG;
}
bool
-_Py_uop_sym_is_const(_Py_UopsSymbol *sym)
+_Py_uop_sym_is_null(JitOptSymbol *sym)
{
- return sym->const_val != NULL;
+ return sym->tag == JIT_SYM_NULL_TAG;
}
+
PyObject *
-_Py_uop_sym_get_const(_Py_UopsSymbol *sym)
+_Py_uop_sym_get_const(JitOptSymbol *sym)
{
- return sym->const_val;
+ if (sym->tag == JIT_SYM_KNOWN_VALUE_TAG) {
+ return sym->value.value;
+ }
+ return NULL;
}
void
-_Py_uop_sym_set_type(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym, PyTypeObject
*typ)
+_Py_uop_sym_set_type(JitOptContext *ctx, JitOptSymbol *sym, PyTypeObject *typ)
{
- assert(typ != NULL && PyType_Check(typ));
- if (sym->flags & IS_NULL) {
- sym_set_bottom(ctx, sym);
- return;
- }
- if (sym->typ != NULL) {
- if (sym->typ != typ) {
+ JitSymType tag = sym->tag;
+ switch(tag) {
+ case JIT_SYM_NULL_TAG:
sym_set_bottom(ctx, sym);
return;
- }
- }
- else {
- sym_set_flag(sym, NOT_NULL);
- sym->typ = typ;
+ case JIT_SYM_KNOWN_CLASS_TAG:
+ if (sym->cls.type != typ) {
+ sym_set_bottom(ctx, sym);
+ }
+ return;
+ case JIT_SYM_TYPE_VERSION_TAG:
+ if (sym->version.version == typ->tp_version_tag) {
+ sym->tag = JIT_SYM_KNOWN_CLASS_TAG;
+ sym->cls.type = typ;
+ sym->cls.version = typ->tp_version_tag;
+ }
+ else {
+ sym_set_bottom(ctx, sym);
+ }
+ return;
+ case JIT_SYM_KNOWN_VALUE_TAG:
+ if (Py_TYPE(sym->value.value) != typ) {
+ Py_CLEAR(sym->value.value);
+ sym_set_bottom(ctx, sym);
+ }
+ return;
+ case JIT_SYM_TUPLE_TAG:
+ if (typ != &PyTuple_Type) {
+ sym_set_bottom(ctx, sym);
+ }
+ return;
+ case JIT_SYM_BOTTOM_TAG:
+ return;
+ case JIT_SYM_NON_NULL_TAG:
+ case JIT_SYM_UNKNOWN_TAG:
+ sym->tag = JIT_SYM_KNOWN_CLASS_TAG;
+ sym->cls.version = 0;
+ sym->cls.type = typ;
+ return;
}
}
bool
-_Py_uop_sym_set_type_version(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym,
unsigned int version)
+_Py_uop_sym_set_type_version(JitOptContext *ctx, JitOptSymbol *sym, unsigned
int version)
{
- // if the type version was already set, then it must be different and we
should set it to bottom
- if (sym->type_version) {
- sym_set_bottom(ctx, sym);
- return false;
+ JitSymType tag = sym->tag;
+ switch(tag) {
+ case JIT_SYM_NULL_TAG:
+ sym_set_bottom(ctx, sym);
+ return false;
+ case JIT_SYM_KNOWN_CLASS_TAG:
+ if (sym->cls.type->tp_version_tag != version) {
+ sym_set_bottom(ctx, sym);
+ return false;
+ }
+ else {
+ sym->cls.version = version;
+ return true;
+ }
+ case JIT_SYM_KNOWN_VALUE_TAG:
+ Py_CLEAR(sym->value.value);
+ sym_set_bottom(ctx, sym);
+ return false;
+ case JIT_SYM_TUPLE_TAG:
+ sym_set_bottom(ctx, sym);
+ return false;
+ case JIT_SYM_TYPE_VERSION_TAG:
+ if (sym->version.version == version) {
+ return true;
+ }
+ sym_set_bottom(ctx, sym);
+ return false;
+ case JIT_SYM_BOTTOM_TAG:
+ return false;
+ case JIT_SYM_NON_NULL_TAG:
+ case JIT_SYM_UNKNOWN_TAG:
+ sym->tag = JIT_SYM_TYPE_VERSION_TAG;
+ sym->version.version = version;
+ return true;
}
- sym->type_version = version;
- return true;
+ Py_UNREACHABLE();
+}
+
+static void make_const(JitOptSymbol *sym, PyObject *val)
+{
+ sym->tag = JIT_SYM_KNOWN_VALUE_TAG;
+ sym->value.value = Py_NewRef(val);
}
void
-_Py_uop_sym_set_const(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym, PyObject
*const_val)
+_Py_uop_sym_set_const(JitOptContext *ctx, JitOptSymbol *sym, PyObject
*const_val)
{
- assert(const_val != NULL);
- if (sym->flags & IS_NULL) {
- sym_set_bottom(ctx, sym);
- }
- PyTypeObject *typ = Py_TYPE(const_val);
- if (sym->typ != NULL && sym->typ != typ) {
- sym_set_bottom(ctx, sym);
- }
- if (sym->const_val != NULL) {
- if (sym->const_val != const_val) {
- // TODO: What if they're equal?
+ JitSymType tag = sym->tag;
+ switch(tag) {
+ case JIT_SYM_NULL_TAG:
sym_set_bottom(ctx, sym);
- }
- }
- else {
- sym_set_flag(sym, NOT_NULL);
- sym->typ = typ;
- sym->const_val = Py_NewRef(const_val);
+ return;
+ case JIT_SYM_KNOWN_CLASS_TAG:
+ if (sym->cls.type != Py_TYPE(const_val)) {
+ sym_set_bottom(ctx, sym);
+ return;
+ }
+ make_const(sym, const_val);
+ return;
+ case JIT_SYM_KNOWN_VALUE_TAG:
+ if (sym->value.value != const_val) {
+ Py_CLEAR(sym->value.value);
+ sym_set_bottom(ctx, sym);
+ }
+ return;
+ case JIT_SYM_TUPLE_TAG:
+ sym_set_bottom(ctx, sym);
+ return;
+ case JIT_SYM_TYPE_VERSION_TAG:
+ if (sym->version.version != Py_TYPE(const_val)->tp_version_tag) {
+ sym_set_bottom(ctx, sym);
+ return;
+ }
+ make_const(sym, const_val);
+ return;
+ case JIT_SYM_BOTTOM_TAG:
+ return;
+ case JIT_SYM_NON_NULL_TAG:
+ case JIT_SYM_UNKNOWN_TAG:
+ make_const(sym, const_val);
+ return;
}
}
void
-_Py_uop_sym_set_null(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym)
+_Py_uop_sym_set_null(JitOptContext *ctx, JitOptSymbol *sym)
{
- if (_Py_uop_sym_is_not_null(sym)) {
+ if (sym->tag == JIT_SYM_UNKNOWN_TAG) {
+ sym->tag = JIT_SYM_NULL_TAG;
+ }
+ else if (sym->tag > JIT_SYM_NULL_TAG) {
sym_set_bottom(ctx, sym);
}
- sym_set_flag(sym, IS_NULL);
}
void
-_Py_uop_sym_set_non_null(_Py_UOpsContext *ctx, _Py_UopsSymbol *sym)
+_Py_uop_sym_set_non_null(JitOptContext *ctx, JitOptSymbol *sym)
{
- if (_Py_uop_sym_is_null(sym)) {
+ if (sym->tag == JIT_SYM_UNKNOWN_TAG) {
+ sym->tag = JIT_SYM_NON_NULL_TAG;
+ }
+ else if (sym->tag == JIT_SYM_NULL_TAG) {
sym_set_bottom(ctx, sym);
}
- sym_set_flag(sym, NOT_NULL);
}
-_Py_UopsSymbol *
-_Py_uop_sym_new_unknown(_Py_UOpsContext *ctx)
+JitOptSymbol *
+_Py_uop_sym_new_unknown(JitOptContext *ctx)
{
- return sym_new(ctx);
+ JitOptSymbol *res = sym_new(ctx);
+ if (res == NULL) {
+ return out_of_space(ctx);
+ }
+ return res;
}
-_Py_UopsSymbol *
-_Py_uop_sym_new_not_null(_Py_UOpsContext *ctx)
+JitOptSymbol *
+_Py_uop_sym_new_not_null(JitOptContext *ctx)
{
- _Py_UopsSymbol *res = _Py_uop_sym_new_unknown(ctx);
+ JitOptSymbol *res = sym_new(ctx);
if (res == NULL) {
return out_of_space(ctx);
}
- sym_set_flag(res, NOT_NULL);
+ res->tag = JIT_SYM_NON_NULL_TAG;
return res;
}
-_Py_UopsSymbol *
-_Py_uop_sym_new_type(_Py_UOpsContext *ctx, PyTypeObject *typ)
+JitOptSymbol *
+_Py_uop_sym_new_type(JitOptContext *ctx, PyTypeObject *typ)
{
- _Py_UopsSymbol *res = sym_new(ctx);
+ JitOptSymbol *res = sym_new(ctx);
if (res == NULL) {
return out_of_space(ctx);
}
@@ -237,11 +299,11 @@ _Py_uop_sym_new_type(_Py_UOpsContext *ctx, PyTypeObject
*typ)
}
// Adds a new reference to const_val, owned by the symbol.
-_Py_UopsSymbol *
-_Py_uop_sym_new_const(_Py_UOpsContext *ctx, PyObject *const_val)
+JitOptSymbol *
+_Py_uop_sym_new_const(JitOptContext *ctx, PyObject *const_val)
{
assert(const_val != NULL);
- _Py_UopsSymbol *res = sym_new(ctx);
+ JitOptSymbol *res = sym_new(ctx);
if (res == NULL) {
return out_of_space(ctx);
}
@@ -249,10 +311,10 @@ _Py_uop_sym_new_const(_Py_UOpsContext *ctx, PyObject
*const_val)
return res;
}
-_Py_UopsSymbol *
-_Py_uop_sym_new_null(_Py_UOpsContext *ctx)
+JitOptSymbol *
+_Py_uop_sym_new_null(JitOptContext *ctx)
{
- _Py_UopsSymbol *null_sym = _Py_uop_sym_new_unknown(ctx);
+ JitOptSymbol *null_sym = sym_new(ctx);
if (null_sym == NULL) {
return out_of_space(ctx);
}
@@ -261,64 +323,105 @@ _Py_uop_sym_new_null(_Py_UOpsContext *ctx)
}
PyTypeObject *
-_Py_uop_sym_get_type(_Py_UopsSymbol *sym)
+_Py_uop_sym_get_type(JitOptSymbol *sym)
{
- if (_Py_uop_sym_is_bottom(sym)) {
- return NULL;
- }
- return sym->typ;
+ JitSymType tag = sym->tag;
+ switch(tag) {
+ case JIT_SYM_NULL_TAG:
+ case JIT_SYM_TYPE_VERSION_TAG:
+ case JIT_SYM_BOTTOM_TAG:
+ case JIT_SYM_NON_NULL_TAG:
+ case JIT_SYM_UNKNOWN_TAG:
+ return NULL;
+ case JIT_SYM_KNOWN_CLASS_TAG:
+ return sym->cls.type;
+ case JIT_SYM_KNOWN_VALUE_TAG:
+ return Py_TYPE(sym->value.value);
+ case JIT_SYM_TUPLE_TAG:
+ return &PyTuple_Type;
+ }
+ Py_UNREACHABLE();
}
unsigned int
-_Py_uop_sym_get_type_version(_Py_UopsSymbol *sym)
+_Py_uop_sym_get_type_version(JitOptSymbol *sym)
{
- return sym->type_version;
+ JitSymType tag = sym->tag;
+ switch(tag) {
+ case JIT_SYM_NULL_TAG:
+ case JIT_SYM_BOTTOM_TAG:
+ case JIT_SYM_NON_NULL_TAG:
+ case JIT_SYM_UNKNOWN_TAG:
+ return 0;
+ case JIT_SYM_TYPE_VERSION_TAG:
+ return sym->version.version;
+ case JIT_SYM_KNOWN_CLASS_TAG:
+ return sym->cls.version;
+ case JIT_SYM_KNOWN_VALUE_TAG:
+ return Py_TYPE(sym->value.value)->tp_version_tag;
+ case JIT_SYM_TUPLE_TAG:
+ return PyTuple_Type.tp_version_tag;
+ }
+ Py_UNREACHABLE();
}
bool
-_Py_uop_sym_has_type(_Py_UopsSymbol *sym)
+_Py_uop_sym_has_type(JitOptSymbol *sym)
{
- if (_Py_uop_sym_is_bottom(sym)) {
- return false;
- }
- return sym->typ != NULL;
+ JitSymType tag = sym->tag;
+ switch(tag) {
+ case JIT_SYM_NULL_TAG:
+ case JIT_SYM_TYPE_VERSION_TAG:
+ case JIT_SYM_BOTTOM_TAG:
+ case JIT_SYM_NON_NULL_TAG:
+ case JIT_SYM_UNKNOWN_TAG:
+ return false;
+ case JIT_SYM_KNOWN_CLASS_TAG:
+ case JIT_SYM_KNOWN_VALUE_TAG:
+ case JIT_SYM_TUPLE_TAG:
+ return true;
+ }
+ Py_UNREACHABLE();
}
bool
-_Py_uop_sym_matches_type(_Py_UopsSymbol *sym, PyTypeObject *typ)
+_Py_uop_sym_matches_type(JitOptSymbol *sym, PyTypeObject *typ)
{
assert(typ != NULL && PyType_Check(typ));
return _Py_uop_sym_get_type(sym) == typ;
}
bool
-_Py_uop_sym_matches_type_version(_Py_UopsSymbol *sym, unsigned int version)
+_Py_uop_sym_matches_type_version(JitOptSymbol *sym, unsigned int version)
{
return _Py_uop_sym_get_type_version(sym) == version;
}
-
int
-_Py_uop_sym_truthiness(_Py_UopsSymbol *sym)
-{
- /* There are some non-constant values for
- * which `bool(val)` always evaluates to
- * True or False, such as tuples with known
- * length, but unknown contents, or bound-methods.
- * This function will need updating
- * should we support those values.
- */
- if (_Py_uop_sym_is_bottom(sym)) {
- return -1;
- }
- if (!_Py_uop_sym_is_const(sym)) {
- return -1;
- }
- PyObject *value = _Py_uop_sym_get_const(sym);
+_Py_uop_sym_truthiness(JitOptSymbol *sym)
+{
+ switch(sym->tag) {
+ case JIT_SYM_NULL_TAG:
+ case JIT_SYM_TYPE_VERSION_TAG:
+ case JIT_SYM_BOTTOM_TAG:
+ case JIT_SYM_NON_NULL_TAG:
+ case JIT_SYM_UNKNOWN_TAG:
+ return -1;
+ case JIT_SYM_KNOWN_CLASS_TAG:
+ /* TODO :
+ * Instances of some classes are always
+ * true. We should return 1 in those cases */
+ return -1;
+ case JIT_SYM_KNOWN_VALUE_TAG:
+ break;
+ case JIT_SYM_TUPLE_TAG:
+ return sym->tuple.length != 0;
+ }
+ PyObject *value = sym->value.value;
+ /* Only handle a few known safe types */
if (value == Py_None) {
return 0;
}
- /* Only handle a few known safe types */
PyTypeObject *tp = Py_TYPE(value);
if (tp == &PyLong_Type) {
return !_PyLong_IsZero((PyLongObject *)value);
@@ -332,13 +435,84 @@ _Py_uop_sym_truthiness(_Py_UopsSymbol *sym)
return -1;
}
+static JitOptSymbol *
+allocation_base(JitOptContext *ctx)
+{
+ return ctx->t_arena.arena;
+}
+
+JitOptSymbol *
+_Py_uop_sym_new_tuple(JitOptContext *ctx, int size, JitOptSymbol **args)
+{
+ JitOptSymbol *res = sym_new(ctx);
+ if (res == NULL) {
+ return out_of_space(ctx);
+ }
+ if (size > MAX_SYMBOLIC_TUPLE_SIZE) {
+ res->tag = JIT_SYM_KNOWN_CLASS_TAG;
+ res->cls.type = &PyTuple_Type;
+ }
+ else {
+ res->tag = JIT_SYM_TUPLE_TAG;
+ res->tuple.length = size;
+ for (int i = 0; i < size; i++) {
+ res->tuple.items[i] = (uint16_t)(args[i] - allocation_base(ctx));
+ }
+ }
+ return res;
+}
+
+JitOptSymbol *
+_Py_uop_sym_tuple_getitem(JitOptContext *ctx, JitOptSymbol *sym, int item)
+{
+ assert(item >= 0);
+ if (sym->tag == JIT_SYM_KNOWN_VALUE_TAG) {
+ PyObject *tuple = sym->value.value;
+ if (PyTuple_CheckExact(tuple) && item < PyTuple_GET_SIZE(tuple)) {
+ return _Py_uop_sym_new_const(ctx, PyTuple_GET_ITEM(tuple, item));
+ }
+ }
+ else if (sym->tag == JIT_SYM_TUPLE_TAG && item < sym->tuple.length) {
+ return allocation_base(ctx) + sym->tuple.items[item];
+ }
+ return _Py_uop_sym_new_unknown(ctx);
+}
+
+int
+_Py_uop_sym_tuple_length(JitOptSymbol *sym)
+{
+ if (sym->tag == JIT_SYM_KNOWN_VALUE_TAG) {
+ PyObject *tuple = sym->value.value;
+ if (PyTuple_CheckExact(tuple)) {
+ return PyTuple_GET_SIZE(tuple);
+ }
+ }
+ else if (sym->tag == JIT_SYM_TUPLE_TAG) {
+ return sym->tuple.length;
+ }
+ return -1;
+}
+
+// Return true if known to be immortal.
+bool
+_Py_uop_sym_is_immortal(JitOptSymbol *sym)
+{
+ if (sym->tag == JIT_SYM_KNOWN_VALUE_TAG) {
+ return _Py_IsImmortal(sym->value.value);
+ }
+ if (sym->tag == JIT_SYM_KNOWN_CLASS_TAG) {
+ return sym->cls.type == &PyBool_Type;
+ }
+ return false;
+}
+
// 0 on success, -1 on error.
_Py_UOpsAbstractFrame *
_Py_uop_frame_new(
- _Py_UOpsContext *ctx,
+ JitOptContext *ctx,
PyCodeObject *co,
int curr_stackentries,
- _Py_UopsSymbol **args,
+ JitOptSymbol **args,
int arg_len)
{
assert(ctx->curr_frame_depth < MAX_ABSTRACT_FRAME_DEPTH);
@@ -363,14 +537,14 @@ _Py_uop_frame_new(
}
for (int i = arg_len; i < co->co_nlocalsplus; i++) {
- _Py_UopsSymbol *local = _Py_uop_sym_new_unknown(ctx);
+ JitOptSymbol *local = _Py_uop_sym_new_unknown(ctx);
frame->locals[i] = local;
}
// Initialize the stack as well
for (int i = 0; i < curr_stackentries; i++) {
- _Py_UopsSymbol *stackvar = _Py_uop_sym_new_unknown(ctx);
+ JitOptSymbol *stackvar = _Py_uop_sym_new_unknown(ctx);
frame->stack[i] = stackvar;
}
@@ -378,7 +552,7 @@ _Py_uop_frame_new(
}
void
-_Py_uop_abstractcontext_fini(_Py_UOpsContext *ctx)
+_Py_uop_abstractcontext_fini(JitOptContext *ctx)
{
if (ctx == NULL) {
return;
@@ -386,13 +560,17 @@ _Py_uop_abstractcontext_fini(_Py_UOpsContext *ctx)
ctx->curr_frame_depth = 0;
int tys = ctx->t_arena.ty_curr_number;
for (int i = 0; i < tys; i++) {
- Py_CLEAR(ctx->t_arena.arena[i].const_val);
+ JitOptSymbol *sym = &ctx->t_arena.arena[i];
+ if (sym->tag == JIT_SYM_KNOWN_VALUE_TAG) {
+ Py_CLEAR(sym->value.value);
+ }
}
}
void
-_Py_uop_abstractcontext_init(_Py_UOpsContext *ctx)
+_Py_uop_abstractcontext_init(JitOptContext *ctx)
{
+ static_assert(sizeof(JitOptSymbol) <= 2*sizeof(uint64_t));
ctx->limit = ctx->locals_and_stack + MAX_ABSTRACT_INTERP_SIZE;
ctx->n_consumed = ctx->locals_and_stack;
#ifdef Py_DEBUG // Aids debugging a little. There should never be NULL in the
abstract interpreter.
@@ -410,7 +588,7 @@ _Py_uop_abstractcontext_init(_Py_UOpsContext *ctx)
}
int
-_Py_uop_frame_pop(_Py_UOpsContext *ctx)
+_Py_uop_frame_pop(JitOptContext *ctx)
{
_Py_UOpsAbstractFrame *frame = ctx->frame;
ctx->n_consumed = frame->locals;
@@ -431,26 +609,25 @@ do { \
} \
} while (0)
-static _Py_UopsSymbol *
-make_bottom(_Py_UOpsContext *ctx)
+static JitOptSymbol *
+make_bottom(JitOptContext *ctx)
{
- _Py_UopsSymbol *sym = _Py_uop_sym_new_unknown(ctx);
- _Py_uop_sym_set_null(ctx, sym);
- _Py_uop_sym_set_non_null(ctx, sym);
+ JitOptSymbol *sym = sym_new(ctx);
+ sym->tag = JIT_SYM_BOTTOM_TAG;
return sym;
}
PyObject *
_Py_uop_symbols_test(PyObject *Py_UNUSED(self), PyObject *Py_UNUSED(ignored))
{
- _Py_UOpsContext context;
- _Py_UOpsContext *ctx = &context;
+ JitOptContext context;
+ JitOptContext *ctx = &context;
_Py_uop_abstractcontext_init(ctx);
PyObject *val_42 = NULL;
PyObject *val_43 = NULL;
// Use a single 'sym' variable so copy-pasting tests is easier.
- _Py_UopsSymbol *sym = _Py_uop_sym_new_unknown(ctx);
+ JitOptSymbol *sym = _Py_uop_sym_new_unknown(ctx);
if (sym == NULL) {
goto fail;
}
@@ -510,6 +687,7 @@ _Py_uop_symbols_test(PyObject *Py_UNUSED(self), PyObject
*Py_UNUSED(ignored))
TEST_PREDICATE(_Py_uop_sym_is_const(sym), "42 is not a constant");
TEST_PREDICATE(_Py_uop_sym_get_const(sym) != NULL, "42 as constant is
NULL");
TEST_PREDICATE(_Py_uop_sym_get_const(sym) == val_42, "42 as constant isn't
42");
+ TEST_PREDICATE(_Py_uop_sym_is_immortal(sym), "42 is not immortal");
_Py_uop_sym_set_type(ctx, sym, &PyLong_Type); // Should be a no-op
TEST_PREDICATE(_Py_uop_sym_matches_type(sym, &PyLong_Type), "(42 and 42)
isn't an int");
@@ -518,6 +696,9 @@ _Py_uop_symbols_test(PyObject *Py_UNUSED(self), PyObject
*Py_UNUSED(ignored))
_Py_uop_sym_set_type(ctx, sym, &PyFloat_Type); // Should make it bottom
TEST_PREDICATE(_Py_uop_sym_is_bottom(sym), "(42 and float) isn't bottom");
+ sym = _Py_uop_sym_new_type(ctx, &PyBool_Type);
+ TEST_PREDICATE(_Py_uop_sym_is_immortal(sym), "a bool is not immortal");
+
sym = _Py_uop_sym_new_type(ctx, &PyLong_Type);
if (sym == NULL) {
goto fail;
@@ -534,15 +715,37 @@ _Py_uop_symbols_test(PyObject *Py_UNUSED(self), PyObject
*Py_UNUSED(ignored))
sym = _Py_uop_sym_new_const(ctx, PyLong_FromLong(0));
TEST_PREDICATE(_Py_uop_sym_truthiness(sym) == 0, "bool(0) is not False");
+ JitOptSymbol *i1 = _Py_uop_sym_new_type(ctx, &PyFloat_Type);
+ JitOptSymbol *i2 = _Py_uop_sym_new_const(ctx, val_43);
+ JitOptSymbol *array[2] = { i1, i2 };
+ sym = _Py_uop_sym_new_tuple(ctx, 2, array);
+ TEST_PREDICATE(
+ _Py_uop_sym_matches_type(_Py_uop_sym_tuple_getitem(ctx, sym, 0),
&PyFloat_Type),
+ "tuple item does not match value used to create tuple"
+ );
+ TEST_PREDICATE(
+ _Py_uop_sym_get_const(_Py_uop_sym_tuple_getitem(ctx, sym, 1)) ==
val_43,
+ "tuple item does not match value used to create tuple"
+ );
+ PyObject *pair[2] = { val_42, val_43 };
+ PyObject *tuple = _PyTuple_FromArray(pair, 2);
+ sym = _Py_uop_sym_new_const(ctx, tuple);
+ TEST_PREDICATE(
+ _Py_uop_sym_get_const(_Py_uop_sym_tuple_getitem(ctx, sym, 1)) ==
val_43,
+ "tuple item does not match value used to create tuple"
+ );
+
_Py_uop_abstractcontext_fini(ctx);
Py_DECREF(val_42);
Py_DECREF(val_43);
+ Py_DECREF(tuple);
Py_RETURN_NONE;
fail:
_Py_uop_abstractcontext_fini(ctx);
Py_XDECREF(val_42);
Py_XDECREF(val_43);
+ Py_DECREF(tuple);
return NULL;
}
diff --git a/Tools/cases_generator/optimizer_generator.py
b/Tools/cases_generator/optimizer_generator.py
index 2928440fecca0c..5cfec4bfecbf07 100644
--- a/Tools/cases_generator/optimizer_generator.py
+++ b/Tools/cases_generator/optimizer_generator.py
@@ -36,10 +36,10 @@ def validate_uop(override: Uop, uop: Uop) -> None:
def type_name(var: StackItem) -> str:
if var.is_array():
- return f"_Py_UopsSymbol **"
+ return f"JitOptSymbol **"
if var.type:
return var.type
- return f"_Py_UopsSymbol *"
+ return f"JitOptSymbol *"
def declare_variables(uop: Uop, out: CWriter, skip_inputs: bool) -> None:
@@ -151,11 +151,11 @@ def write_uop(
var.defined = False
storage = emitter.emit_tokens(override, storage, None)
out.start_line()
- storage.flush(out, cast_type="_Py_UopsSymbol *")
+ storage.flush(out, cast_type="JitOptSymbol *")
else:
emit_default(out, uop, stack)
out.start_line()
- stack.flush(out, cast_type="_Py_UopsSymbol *")
+ stack.flush(out, cast_type="JitOptSymbol *")
except StackError as ex:
raise analysis_error(ex.args[0], prototype.body[0]) # from None
_______________________________________________
Python-checkins mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3/lists/python-checkins.python.org/
Member address: [email protected]