diff --git a/mypyc/lib-rt/bytes_ops.c b/mypyc/lib-rt/bytes_ops.c index 6ff34b021a9a..2129dcbff9ad 100644 --- a/mypyc/lib-rt/bytes_ops.c +++ b/mypyc/lib-rt/bytes_ops.c @@ -95,18 +95,22 @@ PyObject *CPyBytes_GetSlice(PyObject *obj, CPyTagged start, CPyTagged end) { return CPyObject_GetSlice(obj, start, end); } +static PyObject *join_id_unicode = NULL; + // Like _PyBytes_Join but fallback to dynamic call if 'sep' is not bytes // (mostly commonly, for bytearrays) PyObject *CPyBytes_Join(PyObject *sep, PyObject *iter) { if (PyBytes_CheckExact(sep)) { return PyBytes_Join(sep, iter); } else { - _Py_IDENTIFIER(join); - PyObject *name = _PyUnicode_FromId(&PyId_join); /* borrowed */ - if (name == NULL) { - return NULL; + if (join_id_unicode == NULL) { + _Py_IDENTIFIER(join); + join_id_unicode = _PyUnicode_FromId(&PyId_join); /* borrowed */ + if (join_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodOneArg(sep, name, iter); + return PyObject_CallMethodOneArg(sep, join_id_unicode, iter); } } diff --git a/mypyc/lib-rt/dict_ops.c b/mypyc/lib-rt/dict_ops.c index b102aba57307..1892116d7798 100644 --- a/mypyc/lib-rt/dict_ops.c +++ b/mypyc/lib-rt/dict_ops.c @@ -9,6 +9,16 @@ #define Py_TPFLAGS_MAPPING (1 << 6) #endif +// Caching _PyUnicode_FromId results for identifiers +static PyObject *setdefault_id_unicode = NULL; +static PyObject *update_id_unicode = NULL; +static PyObject *keys_id_unicode = NULL; +static PyObject *values_id_unicode = NULL; +static PyObject *items_id_unicode = NULL; +// dict_ prefix prevents a name conflict with list_ops +static PyObject *dict_copy_id_unicode = NULL; +static PyObject *dict_clear_id_unicode = NULL; + // Dict subclasses like defaultdict override things in interesting // ways, so we don't want to just directly use the dict methods. Not // sure if it is actually worth doing all this stuff, but it saves @@ -77,12 +87,14 @@ PyObject *CPyDict_SetDefault(PyObject *dict, PyObject *key, PyObject *value) { Py_XINCREF(ret); return ret; } - _Py_IDENTIFIER(setdefault); - PyObject *name = _PyUnicode_FromId(&PyId_setdefault); /* borrowed */ - if (name == NULL) { - return NULL; + if (setdefault_id_unicode == NULL) { + _Py_IDENTIFIER(setdefault); + setdefault_id_unicode = _PyUnicode_FromId(&PyId_setdefault); /* borrowed */ + if (setdefault_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodObjArgs(dict, name, key, value, NULL); + return PyObject_CallMethodObjArgs(dict, setdefault_id_unicode, key, value, NULL); } PyObject *CPyDict_SetDefaultWithNone(PyObject *dict, PyObject *key) { @@ -136,12 +148,14 @@ static inline int CPy_ObjectToStatus(PyObject *obj) { } static int CPyDict_UpdateGeneral(PyObject *dict, PyObject *stuff) { - _Py_IDENTIFIER(update); - PyObject *name = _PyUnicode_FromId(&PyId_update); /* borrowed */ - if (name == NULL) { - return -1; + if (update_id_unicode == NULL) { + _Py_IDENTIFIER(update); + update_id_unicode = _PyUnicode_FromId(&PyId_update); /* borrowed */ + if (update_id_unicode == NULL) { + return -1; + } } - PyObject *res = PyObject_CallMethodOneArg(dict, name, stuff); + PyObject *res = PyObject_CallMethodOneArg(dict, update_id_unicode, stuff); return CPy_ObjectToStatus(res); } @@ -207,36 +221,42 @@ PyObject *CPyDict_KeysView(PyObject *dict) { if (PyDict_CheckExact(dict)){ return _CPyDictView_New(dict, &PyDictKeys_Type); } - _Py_IDENTIFIER(keys); - PyObject *name = _PyUnicode_FromId(&PyId_keys); /* borrowed */ - if (name == NULL) { - return NULL; + if (keys_id_unicode == NULL) { + _Py_IDENTIFIER(keys); + keys_id_unicode = _PyUnicode_FromId(&PyId_keys); /* borrowed */ + if (keys_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodNoArgs(dict, name); + return PyObject_CallMethodNoArgs(dict, keys_id_unicode); } PyObject *CPyDict_ValuesView(PyObject *dict) { if (PyDict_CheckExact(dict)){ return _CPyDictView_New(dict, &PyDictValues_Type); } - _Py_IDENTIFIER(values); - PyObject *name = _PyUnicode_FromId(&PyId_values); /* borrowed */ - if (name == NULL) { - return NULL; + if (values_id_unicode == NULL) { + _Py_IDENTIFIER(values); + values_id_unicode = _PyUnicode_FromId(&PyId_values); /* borrowed */ + if (values_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodNoArgs(dict, name); + return PyObject_CallMethodNoArgs(dict, values_id_unicode); } PyObject *CPyDict_ItemsView(PyObject *dict) { if (PyDict_CheckExact(dict)){ return _CPyDictView_New(dict, &PyDictItems_Type); } - _Py_IDENTIFIER(items); - PyObject *name = _PyUnicode_FromId(&PyId_items); /* borrowed */ - if (name == NULL) { - return NULL; + if (items_id_unicode == NULL) { + _Py_IDENTIFIER(items); + items_id_unicode = _PyUnicode_FromId(&PyId_items); /* borrowed */ + if (items_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodNoArgs(dict, name); + return PyObject_CallMethodNoArgs(dict, items_id_unicode); } PyObject *CPyDict_Keys(PyObject *dict) { @@ -245,12 +265,14 @@ PyObject *CPyDict_Keys(PyObject *dict) { } // Inline generic fallback logic to also return a list. PyObject *list = PyList_New(0); - _Py_IDENTIFIER(keys); - PyObject *name = _PyUnicode_FromId(&PyId_keys); /* borrowed */ - if (name == NULL) { - return NULL; + if (keys_id_unicode == NULL) { + _Py_IDENTIFIER(keys); + keys_id_unicode = _PyUnicode_FromId(&PyId_keys); /* borrowed */ + if (keys_id_unicode == NULL) { + return NULL; + } } - PyObject *view = PyObject_CallMethodNoArgs(dict, name); + PyObject *view = PyObject_CallMethodNoArgs(dict, keys_id_unicode); if (view == NULL) { return NULL; } @@ -268,12 +290,14 @@ PyObject *CPyDict_Values(PyObject *dict) { } // Inline generic fallback logic to also return a list. PyObject *list = PyList_New(0); - _Py_IDENTIFIER(values); - PyObject *name = _PyUnicode_FromId(&PyId_values); /* borrowed */ - if (name == NULL) { - return NULL; + if (values_id_unicode == NULL) { + _Py_IDENTIFIER(values); + values_id_unicode = _PyUnicode_FromId(&PyId_values); /* borrowed */ + if (values_id_unicode == NULL) { + return NULL; + } } - PyObject *view = PyObject_CallMethodNoArgs(dict, name); + PyObject *view = PyObject_CallMethodNoArgs(dict, values_id_unicode); if (view == NULL) { return NULL; } @@ -291,12 +315,14 @@ PyObject *CPyDict_Items(PyObject *dict) { } // Inline generic fallback logic to also return a list. PyObject *list = PyList_New(0); - _Py_IDENTIFIER(items); - PyObject *name = _PyUnicode_FromId(&PyId_items); /* borrowed */ - if (name == NULL) { - return NULL; + if (items_id_unicode == NULL) { + _Py_IDENTIFIER(items); + items_id_unicode = _PyUnicode_FromId(&PyId_items); /* borrowed */ + if (items_id_unicode == NULL) { + return NULL; + } } - PyObject *view = PyObject_CallMethodNoArgs(dict, name); + PyObject *view = PyObject_CallMethodNoArgs(dict, items_id_unicode); if (view == NULL) { return NULL; } @@ -312,12 +338,14 @@ char CPyDict_Clear(PyObject *dict) { if (PyDict_CheckExact(dict)) { PyDict_Clear(dict); } else { - _Py_IDENTIFIER(clear); - PyObject *name = _PyUnicode_FromId(&PyId_clear); /* borrowed */ - if (name == NULL) { - return 0; + if (dict_clear_id_unicode == NULL) { + _Py_IDENTIFIER(clear); + dict_clear_id_unicode = _PyUnicode_FromId(&PyId_clear); /* borrowed */ + if (dict_clear_id_unicode == NULL) { + return 0; + } } - PyObject *res = PyObject_CallMethodNoArgs(dict, name); + PyObject *res = PyObject_CallMethodNoArgs(dict, dict_clear_id_unicode); if (res == NULL) { return 0; } @@ -329,12 +357,14 @@ PyObject *CPyDict_Copy(PyObject *dict) { if (PyDict_CheckExact(dict)) { return PyDict_Copy(dict); } - _Py_IDENTIFIER(copy); - PyObject *name = _PyUnicode_FromId(&PyId_copy); /* borrowed */ - if (name == NULL) { - return NULL; + if (dict_copy_id_unicode == NULL) { + _Py_IDENTIFIER(copy); + dict_copy_id_unicode = _PyUnicode_FromId(&PyId_copy); /* borrowed */ + if (dict_copy_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodNoArgs(dict, name); + return PyObject_CallMethodNoArgs(dict, dict_copy_id_unicode); } PyObject *CPyDict_GetKeysIter(PyObject *dict) { @@ -352,12 +382,14 @@ PyObject *CPyDict_GetItemsIter(PyObject *dict) { Py_INCREF(dict); return dict; } - _Py_IDENTIFIER(items); - PyObject *name = _PyUnicode_FromId(&PyId_items); /* borrowed */ - if (name == NULL) { - return NULL; + if (items_id_unicode == NULL) { + _Py_IDENTIFIER(items); + items_id_unicode = _PyUnicode_FromId(&PyId_items); /* borrowed */ + if (items_id_unicode == NULL) { + return NULL; + } } - PyObject *view = PyObject_CallMethodNoArgs(dict, name); + PyObject *view = PyObject_CallMethodNoArgs(dict, items_id_unicode); if (view == NULL) { return NULL; } @@ -372,12 +404,14 @@ PyObject *CPyDict_GetValuesIter(PyObject *dict) { Py_INCREF(dict); return dict; } - _Py_IDENTIFIER(values); - PyObject *name = _PyUnicode_FromId(&PyId_values); /* borrowed */ - if (name == NULL) { - return NULL; + if (values_id_unicode == NULL) { + _Py_IDENTIFIER(values); + values_id_unicode = _PyUnicode_FromId(&PyId_values); /* borrowed */ + if (values_id_unicode == NULL) { + return NULL; + } } - PyObject *view = PyObject_CallMethodNoArgs(dict, name); + PyObject *view = PyObject_CallMethodNoArgs(dict, values_id_unicode); if (view == NULL) { return NULL; } diff --git a/mypyc/lib-rt/list_ops.c b/mypyc/lib-rt/list_ops.c index c611907fb601..e9f6c6d9f3fe 100644 --- a/mypyc/lib-rt/list_ops.c +++ b/mypyc/lib-rt/list_ops.c @@ -9,6 +9,10 @@ #define Py_TPFLAGS_SEQUENCE (1 << 5) #endif +// list_ prefix prevents a name conflict with dict_ops +static PyObject *list_clear_id_unicode = NULL; +static PyObject *list_copy_id_unicode = NULL; + PyObject *CPyList_Build(Py_ssize_t len, ...) { Py_ssize_t i; @@ -33,12 +37,14 @@ char CPyList_Clear(PyObject *list) { if (PyList_CheckExact(list)) { PyList_Clear(list); } else { - _Py_IDENTIFIER(clear); - PyObject *name = _PyUnicode_FromId(&PyId_clear); - if (name == NULL) { - return 0; + if (list_clear_id_unicode == NULL) { + _Py_IDENTIFIER(clear); + list_clear_id_unicode = _PyUnicode_FromId(&PyId_clear); + if (list_clear_id_unicode == NULL) { + return 0; + } } - PyObject *res = PyObject_CallMethodNoArgs(list, name); + PyObject *res = PyObject_CallMethodNoArgs(list, list_clear_id_unicode); if (res == NULL) { return 0; } @@ -50,13 +56,14 @@ PyObject *CPyList_Copy(PyObject *list) { if(PyList_CheckExact(list)) { return PyList_GetSlice(list, 0, PyList_GET_SIZE(list)); } - _Py_IDENTIFIER(copy); - - PyObject *name = _PyUnicode_FromId(&PyId_copy); - if (name == NULL) { - return NULL; + if (list_copy_id_unicode == NULL) { + _Py_IDENTIFIER(copy); + list_copy_id_unicode = _PyUnicode_FromId(&PyId_copy); + if (list_copy_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodNoArgs(list, name); + return PyObject_CallMethodNoArgs(list, list_copy_id_unicode); } PyObject *CPyList_GetItemShort(PyObject *list, CPyTagged index) { diff --git a/mypyc/lib-rt/misc_ops.c b/mypyc/lib-rt/misc_ops.c index ca09c347b4ff..ace2c480349b 100644 --- a/mypyc/lib-rt/misc_ops.c +++ b/mypyc/lib-rt/misc_ops.c @@ -20,6 +20,8 @@ PyObject *CPy_GetCoro(PyObject *obj) } } +static PyObject *send_id_unicode = NULL; + PyObject *CPyIter_Send(PyObject *iter, PyObject *val) { // Do a send, or a next if second arg is None. @@ -27,12 +29,14 @@ PyObject *CPyIter_Send(PyObject *iter, PyObject *val) if (Py_IsNone(val)) { return CPyIter_Next(iter); } else { - _Py_IDENTIFIER(send); - PyObject *name = _PyUnicode_FromId(&PyId_send); /* borrowed */ - if (name == NULL) { - return NULL; + if (send_id_unicode == NULL) { + _Py_IDENTIFIER(send); + send_id_unicode = _PyUnicode_FromId(&PyId_send); /* borrowed */ + if (send_id_unicode == NULL) { + return NULL; + } } - return PyObject_CallMethodOneArg(iter, name, val); + return PyObject_CallMethodOneArg(iter, send_id_unicode, val); } } @@ -1058,14 +1062,21 @@ PyObject *CPy_GetANext(PyObject *aiter) #if CPY_3_11_FEATURES +static PyObject *__name___id_unicode = NULL; + // Return obj.__name__ (specialized to type objects, which are the most common target). PyObject *CPy_GetName(PyObject *obj) { if (PyType_Check(obj)) { return PyType_GetName((PyTypeObject *)obj); } - _Py_IDENTIFIER(__name__); - PyObject *name = _PyUnicode_FromId(&PyId___name__); /* borrowed */ - return PyObject_GetAttr(obj, name); + if (__name___id_unicode == NULL) { + _Py_IDENTIFIER(__name__); + __name___id_unicode = _PyUnicode_FromId(&PyId___name__); /* borrowed */ + if (__name___id_unicode == NULL) { + return NULL; + } + } + return PyObject_GetAttr(obj, __name___id_unicode); } #endif