-
-
Notifications
You must be signed in to change notification settings - Fork 31.8k
GH-98831: Implement basic cache effects #99313
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
9f15c4b
6189043
f5e1aed
a8d608d
4ee85e7
873da31
e0ab5b8
882fdec
8226fb9
1aa0124
d094e42
d3d907a
0339a67
f3e7dd6
e3ff6ac
3db443a
c58a85a
756a41b
48400ac
433243a
3d51484
4d42a0a
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change | ||||
---|---|---|---|---|---|---|
|
@@ -76,13 +76,9 @@ do { \ | |||||
#define NAME_ERROR_MSG \ | ||||||
"name '%.200s' is not defined" | ||||||
|
||||||
typedef struct { | ||||||
PyObject *kwnames; | ||||||
} CallShape; | ||||||
|
||||||
// Dummy variables for stack effects. | ||||||
static PyObject *value, *value1, *value2, *left, *right, *res, *sum, *prod, *sub; | ||||||
static PyObject *container, *start, *stop, *v; | ||||||
static PyObject *container, *start, *stop, *v, *lhs, *rhs; | ||||||
|
||||||
static PyObject * | ||||||
dummy_func( | ||||||
|
@@ -101,6 +97,8 @@ dummy_func( | |||||
binaryfunc binary_ops[] | ||||||
) | ||||||
{ | ||||||
_PyInterpreterFrame entry_frame; | ||||||
|
||||||
switch (opcode) { | ||||||
|
||||||
// BEGIN BYTECODES // | ||||||
|
@@ -193,7 +191,21 @@ dummy_func( | |||||
ERROR_IF(res == NULL, error); | ||||||
} | ||||||
|
||||||
inst(BINARY_OP_MULTIPLY_INT, (left, right -- prod)) { | ||||||
family(binary_op, INLINE_CACHE_ENTRIES_BINARY_OP) = { | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Honestly, I don't think we really need the I feel like it sort of just complicates parsing and code generation for no real benefit... plus, we actually already have asserts to this effect in
Suggested change
|
||||||
BINARY_OP, | ||||||
BINARY_OP_ADD_FLOAT, | ||||||
BINARY_OP_ADD_INT, | ||||||
BINARY_OP_ADD_UNICODE, | ||||||
BINARY_OP_GENERIC, | ||||||
// BINARY_OP_INPLACE_ADD_UNICODE, // This is an odd duck. | ||||||
gvanrossum marked this conversation as resolved.
Show resolved
Hide resolved
|
||||||
BINARY_OP_MULTIPLY_FLOAT, | ||||||
BINARY_OP_MULTIPLY_INT, | ||||||
BINARY_OP_SUBTRACT_FLOAT, | ||||||
BINARY_OP_SUBTRACT_INT, | ||||||
}; | ||||||
|
||||||
|
||||||
inst(BINARY_OP_MULTIPLY_INT, (left, right, unused/1 -- prod)) { | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Just my preference, but I sort of prefer a name like
Suggested change
|
||||||
assert(cframe.use_tracing == 0); | ||||||
DEOPT_IF(!PyLong_CheckExact(left), BINARY_OP); | ||||||
DEOPT_IF(!PyLong_CheckExact(right), BINARY_OP); | ||||||
|
@@ -202,10 +214,9 @@ dummy_func( | |||||
_Py_DECREF_SPECIALIZED(right, (destructor)PyObject_Free); | ||||||
_Py_DECREF_SPECIALIZED(left, (destructor)PyObject_Free); | ||||||
ERROR_IF(prod == NULL, error); | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
} | ||||||
|
||||||
inst(BINARY_OP_MULTIPLY_FLOAT, (left, right -- prod)) { | ||||||
inst(BINARY_OP_MULTIPLY_FLOAT, (left, right, unused/1 -- prod)) { | ||||||
assert(cframe.use_tracing == 0); | ||||||
DEOPT_IF(!PyFloat_CheckExact(left), BINARY_OP); | ||||||
DEOPT_IF(!PyFloat_CheckExact(right), BINARY_OP); | ||||||
|
@@ -216,10 +227,9 @@ dummy_func( | |||||
_Py_DECREF_SPECIALIZED(right, _PyFloat_ExactDealloc); | ||||||
_Py_DECREF_SPECIALIZED(left, _PyFloat_ExactDealloc); | ||||||
ERROR_IF(prod == NULL, error); | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
} | ||||||
|
||||||
inst(BINARY_OP_SUBTRACT_INT, (left, right -- sub)) { | ||||||
inst(BINARY_OP_SUBTRACT_INT, (left, right, unused/1 -- sub)) { | ||||||
assert(cframe.use_tracing == 0); | ||||||
DEOPT_IF(!PyLong_CheckExact(left), BINARY_OP); | ||||||
DEOPT_IF(!PyLong_CheckExact(right), BINARY_OP); | ||||||
|
@@ -228,10 +238,9 @@ dummy_func( | |||||
_Py_DECREF_SPECIALIZED(right, (destructor)PyObject_Free); | ||||||
_Py_DECREF_SPECIALIZED(left, (destructor)PyObject_Free); | ||||||
ERROR_IF(sub == NULL, error); | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
} | ||||||
|
||||||
inst(BINARY_OP_SUBTRACT_FLOAT, (left, right -- sub)) { | ||||||
inst(BINARY_OP_SUBTRACT_FLOAT, (left, right, unused/1 -- sub)) { | ||||||
assert(cframe.use_tracing == 0); | ||||||
DEOPT_IF(!PyFloat_CheckExact(left), BINARY_OP); | ||||||
DEOPT_IF(!PyFloat_CheckExact(right), BINARY_OP); | ||||||
|
@@ -241,10 +250,9 @@ dummy_func( | |||||
_Py_DECREF_SPECIALIZED(right, _PyFloat_ExactDealloc); | ||||||
_Py_DECREF_SPECIALIZED(left, _PyFloat_ExactDealloc); | ||||||
ERROR_IF(sub == NULL, error); | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
} | ||||||
|
||||||
inst(BINARY_OP_ADD_UNICODE, (left, right -- res)) { | ||||||
inst(BINARY_OP_ADD_UNICODE, (left, right, unused/1 -- res)) { | ||||||
assert(cframe.use_tracing == 0); | ||||||
DEOPT_IF(!PyUnicode_CheckExact(left), BINARY_OP); | ||||||
DEOPT_IF(Py_TYPE(right) != Py_TYPE(left), BINARY_OP); | ||||||
|
@@ -253,7 +261,6 @@ dummy_func( | |||||
_Py_DECREF_SPECIALIZED(left, _PyUnicode_ExactDealloc); | ||||||
_Py_DECREF_SPECIALIZED(right, _PyUnicode_ExactDealloc); | ||||||
ERROR_IF(res == NULL, error); | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
} | ||||||
|
||||||
// This is a subtle one. It's a super-instruction for | ||||||
|
@@ -292,7 +299,7 @@ dummy_func( | |||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP + 1); | ||||||
} | ||||||
|
||||||
inst(BINARY_OP_ADD_FLOAT, (left, right -- sum)) { | ||||||
inst(BINARY_OP_ADD_FLOAT, (left, right, unused/1 -- sum)) { | ||||||
assert(cframe.use_tracing == 0); | ||||||
DEOPT_IF(!PyFloat_CheckExact(left), BINARY_OP); | ||||||
DEOPT_IF(Py_TYPE(right) != Py_TYPE(left), BINARY_OP); | ||||||
|
@@ -303,10 +310,9 @@ dummy_func( | |||||
_Py_DECREF_SPECIALIZED(right, _PyFloat_ExactDealloc); | ||||||
_Py_DECREF_SPECIALIZED(left, _PyFloat_ExactDealloc); | ||||||
ERROR_IF(sum == NULL, error); | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
} | ||||||
|
||||||
inst(BINARY_OP_ADD_INT, (left, right -- sum)) { | ||||||
inst(BINARY_OP_ADD_INT, (left, right, unused/1 -- sum)) { | ||||||
assert(cframe.use_tracing == 0); | ||||||
DEOPT_IF(!PyLong_CheckExact(left), BINARY_OP); | ||||||
DEOPT_IF(Py_TYPE(right) != Py_TYPE(left), BINARY_OP); | ||||||
|
@@ -315,7 +321,6 @@ dummy_func( | |||||
_Py_DECREF_SPECIALIZED(right, (destructor)PyObject_Free); | ||||||
_Py_DECREF_SPECIALIZED(left, (destructor)PyObject_Free); | ||||||
ERROR_IF(sum == NULL, error); | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
} | ||||||
|
||||||
inst(BINARY_SUBSCR, (container, sub -- res)) { | ||||||
|
@@ -3691,30 +3696,21 @@ dummy_func( | |||||
PUSH(Py_NewRef(peek)); | ||||||
} | ||||||
|
||||||
// stack effect: (__0 -- ) | ||||||
inst(BINARY_OP_GENERIC) { | ||||||
PyObject *rhs = POP(); | ||||||
PyObject *lhs = TOP(); | ||||||
inst(BINARY_OP_GENERIC, (lhs, rhs, unused/1 -- res)) { | ||||||
assert(0 <= oparg); | ||||||
assert((unsigned)oparg < Py_ARRAY_LENGTH(binary_ops)); | ||||||
assert(binary_ops[oparg]); | ||||||
PyObject *res = binary_ops[oparg](lhs, rhs); | ||||||
res = binary_ops[oparg](lhs, rhs); | ||||||
Py_DECREF(lhs); | ||||||
Py_DECREF(rhs); | ||||||
SET_TOP(res); | ||||||
if (res == NULL) { | ||||||
goto error; | ||||||
} | ||||||
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_OP); | ||||||
ERROR_IF(res == NULL, error); | ||||||
} | ||||||
|
||||||
// stack effect: (__0 -- ) | ||||||
inst(BINARY_OP) { | ||||||
// This always dispatches, so the result is unused. | ||||||
inst(BINARY_OP, (lhs, rhs, unused/1 -- unused)) { | ||||||
gvanrossum marked this conversation as resolved.
Show resolved
Hide resolved
|
||||||
_PyBinaryOpCache *cache = (_PyBinaryOpCache *)next_instr; | ||||||
if (ADAPTIVE_COUNTER_IS_ZERO(cache->counter)) { | ||||||
assert(cframe.use_tracing == 0); | ||||||
PyObject *lhs = SECOND(); | ||||||
PyObject *rhs = TOP(); | ||||||
next_instr--; | ||||||
_Py_Specialize_BinaryOp(lhs, rhs, next_instr, oparg, &GETLOCAL(0)); | ||||||
DISPATCH_SAME_OPARG(); | ||||||
|
@@ -3761,13 +3757,8 @@ dummy_func( | |||||
; | ||||||
} | ||||||
|
||||||
// Families go below this point // | ||||||
// Future families go below this point // | ||||||
gvanrossum marked this conversation as resolved.
Show resolved
Hide resolved
|
||||||
|
||||||
family(binary_op) = { | ||||||
BINARY_OP, BINARY_OP_ADD_FLOAT, | ||||||
BINARY_OP_ADD_INT, BINARY_OP_ADD_UNICODE, BINARY_OP_GENERIC, BINARY_OP_INPLACE_ADD_UNICODE, | ||||||
BINARY_OP_MULTIPLY_FLOAT, BINARY_OP_MULTIPLY_INT, BINARY_OP_SUBTRACT_FLOAT, | ||||||
BINARY_OP_SUBTRACT_INT }; | ||||||
family(binary_subscr) = { | ||||||
BINARY_SUBSCR, BINARY_SUBSCR_DICT, | ||||||
BINARY_SUBSCR_GETITEM, BINARY_SUBSCR_LIST_INT, BINARY_SUBSCR_TUPLE_INT }; | ||||||
|
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
:(