diff --git a/Include/internal/pycore_opcode_metadata.h b/Include/internal/pycore_opcode_metadata.h index dd1bf2d1d2b51a..8d1d1f8a4c223c 100644 --- a/Include/internal/pycore_opcode_metadata.h +++ b/Include/internal/pycore_opcode_metadata.h @@ -1357,7 +1357,7 @@ _PyOpcode_macro_expansion[256] = { [CALL_KW_BOUND_METHOD] = { .nuops = 6, .uops = { { _CHECK_PEP_523, OPARG_SIMPLE, 1 }, { _CHECK_METHOD_VERSION_KW, 2, 1 }, { _EXPAND_METHOD_KW, OPARG_SIMPLE, 3 }, { _PY_FRAME_KW, OPARG_SIMPLE, 3 }, { _SAVE_RETURN_OFFSET, OPARG_SAVE_RETURN_OFFSET, 3 }, { _PUSH_FRAME, OPARG_SIMPLE, 3 } } }, [CALL_KW_NON_PY] = { .nuops = 3, .uops = { { _CHECK_IS_NOT_PY_CALLABLE_KW, OPARG_SIMPLE, 3 }, { _CALL_KW_NON_PY, OPARG_SIMPLE, 3 }, { _CHECK_PERIODIC, OPARG_SIMPLE, 3 } } }, [CALL_KW_PY] = { .nuops = 5, .uops = { { _CHECK_PEP_523, OPARG_SIMPLE, 1 }, { _CHECK_FUNCTION_VERSION_KW, 2, 1 }, { _PY_FRAME_KW, OPARG_SIMPLE, 3 }, { _SAVE_RETURN_OFFSET, OPARG_SAVE_RETURN_OFFSET, 3 }, { _PUSH_FRAME, OPARG_SIMPLE, 3 } } }, - [CALL_LEN] = { .nuops = 3, .uops = { { _GUARD_NOS_NULL, OPARG_SIMPLE, 3 }, { _GUARD_CALLABLE_LEN, OPARG_SIMPLE, 3 }, { _CALL_LEN, OPARG_SIMPLE, 3 } } }, + [CALL_LEN] = { .nuops = 5, .uops = { { _GUARD_NOS_NULL, OPARG_SIMPLE, 3 }, { _GUARD_CALLABLE_LEN, OPARG_SIMPLE, 3 }, { _CALL_LEN, OPARG_SIMPLE, 3 }, { _POP_TOP, OPARG_SIMPLE, 3 }, { _POP_TOP, OPARG_SIMPLE, 3 } } }, [CALL_LIST_APPEND] = { .nuops = 4, .uops = { { _GUARD_CALLABLE_LIST_APPEND, OPARG_SIMPLE, 3 }, { _GUARD_NOS_NOT_NULL, OPARG_SIMPLE, 3 }, { _GUARD_NOS_LIST, OPARG_SIMPLE, 3 }, { _CALL_LIST_APPEND, OPARG_SIMPLE, 3 } } }, [CALL_METHOD_DESCRIPTOR_FAST] = { .nuops = 2, .uops = { { _CALL_METHOD_DESCRIPTOR_FAST, OPARG_SIMPLE, 3 }, { _CHECK_PERIODIC, OPARG_SIMPLE, 3 } } }, [CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS] = { .nuops = 2, .uops = { { _CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS, OPARG_SIMPLE, 3 }, { _CHECK_PERIODIC, OPARG_SIMPLE, 3 } } }, diff --git a/Lib/test/test_capi/test_opt.py b/Lib/test/test_capi/test_opt.py index e4c9a463855a69..e7f0a9a8ff4485 100644 --- a/Lib/test/test_capi/test_opt.py +++ b/Lib/test/test_capi/test_opt.py @@ -1967,6 +1967,7 @@ def testfunc(n): self.assertIn("_CALL_LEN", uops) self.assertNotIn("_GUARD_NOS_INT", uops) self.assertNotIn("_GUARD_TOS_INT", uops) + self.assertIn("_POP_TOP_NOP", uops) def test_call_len_known_length_small_int(self): def testfunc(n): diff --git a/Python/bytecodes.c b/Python/bytecodes.c index 1a5a9ff13a23a5..63ac32fe28f842 100644 --- a/Python/bytecodes.c +++ b/Python/bytecodes.c @@ -4315,7 +4315,9 @@ dummy_func( unused/2 + _GUARD_NOS_NULL + _GUARD_CALLABLE_LEN + - _CALL_LEN; + _CALL_LEN + + POP_TOP + + POP_TOP; op(_GUARD_CALLABLE_LEN, (callable, unused, unused -- callable, unused, unused)){ PyObject *callable_o = PyStackRef_AsPyObjectBorrow(callable); @@ -4323,10 +4325,10 @@ dummy_func( DEOPT_IF(callable_o != interp->callable_cache.len); } - op(_CALL_LEN, (callable, null, arg -- res)) { + op(_CALL_LEN, (callable, null, arg -- res, a, c)) { /* len(o) */ - (void)null; STAT_INC(CALL, hit); + INPUTS_DEAD(); PyObject *arg_o = PyStackRef_AsPyObjectBorrow(arg); Py_ssize_t len_i = PyObject_Length(arg_o); if (len_i < 0) { @@ -4337,10 +4339,9 @@ dummy_func( if (res_o == NULL) { ERROR_NO_POP(); } - PyStackRef_CLOSE(arg); - DEAD(null); - PyStackRef_CLOSE(callable); res = PyStackRef_FromPyObjectSteal(res_o); + a = arg; + c = callable; } op(_GUARD_CALLABLE_ISINSTANCE, (callable, unused, unused, unused -- callable, unused, unused, unused)) { diff --git a/Python/executor_cases.c.h b/Python/executor_cases.c.h index 46fc164a5b3bc2..9ca52bea3a9163 100644 --- a/Python/executor_cases.c.h +++ b/Python/executor_cases.c.h @@ -5937,15 +5937,16 @@ case _CALL_LEN: { _PyStackRef arg; - _PyStackRef null; _PyStackRef callable; _PyStackRef res; + _PyStackRef a; + _PyStackRef c; arg = stack_pointer[-1]; - null = stack_pointer[-2]; callable = stack_pointer[-3]; - (void)null; STAT_INC(CALL, hit); PyObject *arg_o = PyStackRef_AsPyObjectBorrow(arg); + stack_pointer += -3; + assert(WITHIN_STACK_BOUNDS()); _PyFrame_SetStackPointer(frame, stack_pointer); Py_ssize_t len_i = PyObject_Length(arg_o); stack_pointer = _PyFrame_GetStackPointer(frame); @@ -5957,19 +5958,13 @@ if (res_o == NULL) { JUMP_TO_ERROR(); } - stack_pointer += -1; - assert(WITHIN_STACK_BOUNDS()); - _PyFrame_SetStackPointer(frame, stack_pointer); - PyStackRef_CLOSE(arg); - stack_pointer = _PyFrame_GetStackPointer(frame); - stack_pointer += -2; - assert(WITHIN_STACK_BOUNDS()); - _PyFrame_SetStackPointer(frame, stack_pointer); - PyStackRef_CLOSE(callable); - stack_pointer = _PyFrame_GetStackPointer(frame); res = PyStackRef_FromPyObjectSteal(res_o); + a = arg; + c = callable; stack_pointer[0] = res; - stack_pointer += 1; + stack_pointer[1] = a; + stack_pointer[2] = c; + stack_pointer += 3; assert(WITHIN_STACK_BOUNDS()); break; } diff --git a/Python/generated_cases.c.h b/Python/generated_cases.c.h index 8f7932f0033c6f..f8dab3960bb102 100644 --- a/Python/generated_cases.c.h +++ b/Python/generated_cases.c.h @@ -3408,6 +3408,9 @@ _PyStackRef callable; _PyStackRef arg; _PyStackRef res; + _PyStackRef a; + _PyStackRef c; + _PyStackRef value; /* Skip 1 cache entry */ /* Skip 2 cache entries */ // _GUARD_NOS_NULL @@ -3433,9 +3436,10 @@ // _CALL_LEN { arg = stack_pointer[-1]; - (void)null; STAT_INC(CALL, hit); PyObject *arg_o = PyStackRef_AsPyObjectBorrow(arg); + stack_pointer += -3; + assert(WITHIN_STACK_BOUNDS()); _PyFrame_SetStackPointer(frame, stack_pointer); Py_ssize_t len_i = PyObject_Length(arg_o); stack_pointer = _PyFrame_GetStackPointer(frame); @@ -3447,21 +3451,30 @@ if (res_o == NULL) { JUMP_TO_LABEL(error); } - stack_pointer += -1; + res = PyStackRef_FromPyObjectSteal(res_o); + a = arg; + c = callable; + } + // _POP_TOP + { + value = c; + stack_pointer[0] = res; + stack_pointer[1] = a; + stack_pointer += 2; assert(WITHIN_STACK_BOUNDS()); _PyFrame_SetStackPointer(frame, stack_pointer); - PyStackRef_CLOSE(arg); + PyStackRef_XCLOSE(value); stack_pointer = _PyFrame_GetStackPointer(frame); - stack_pointer += -2; + } + // _POP_TOP + { + value = a; + stack_pointer += -1; assert(WITHIN_STACK_BOUNDS()); _PyFrame_SetStackPointer(frame, stack_pointer); - PyStackRef_CLOSE(callable); + PyStackRef_XCLOSE(value); stack_pointer = _PyFrame_GetStackPointer(frame); - res = PyStackRef_FromPyObjectSteal(res_o); } - stack_pointer[0] = res; - stack_pointer += 1; - assert(WITHIN_STACK_BOUNDS()); DISPATCH(); } diff --git a/Python/optimizer_bytecodes.c b/Python/optimizer_bytecodes.c index 3182e8b3b70144..158a8cae844351 100644 --- a/Python/optimizer_bytecodes.c +++ b/Python/optimizer_bytecodes.c @@ -1178,7 +1178,7 @@ dummy_func(void) { sym_set_const(callable, (PyObject *)&PyUnicode_Type); } - op(_CALL_LEN, (callable, null, arg -- res)) { + op(_CALL_LEN, (callable, null, arg -- res, a, c)) { res = sym_new_type(ctx, &PyLong_Type); int tuple_length = sym_tuple_length(arg); if (tuple_length >= 0) { @@ -1193,6 +1193,8 @@ dummy_func(void) { res = sym_new_const(ctx, temp); Py_DECREF(temp); } + a = arg; + c = callable; } op(_GET_LEN, (obj -- obj, len)) { diff --git a/Python/optimizer_cases.c.h b/Python/optimizer_cases.c.h index 8d30df3aa7d429..8b90cc773c5344 100644 --- a/Python/optimizer_cases.c.h +++ b/Python/optimizer_cases.c.h @@ -2460,8 +2460,12 @@ case _CALL_LEN: { JitOptRef arg; + JitOptRef callable; JitOptRef res; + JitOptRef a; + JitOptRef c; arg = stack_pointer[-1]; + callable = stack_pointer[-3]; res = sym_new_type(ctx, &PyLong_Type); int tuple_length = sym_tuple_length(arg); if (tuple_length >= 0) { @@ -2480,9 +2484,11 @@ Py_DECREF(temp); stack_pointer += 2; } + a = arg; + c = callable; stack_pointer[-3] = res; - stack_pointer += -2; - assert(WITHIN_STACK_BOUNDS()); + stack_pointer[-2] = a; + stack_pointer[-1] = c; break; } pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy