Skip to content

Commit 21403af

Browse files
authored
gh-142217: Add tests on the deprecated _Py_Identifier C API (#157638)
Replace also PyDict_GetItemWithError() with PyDict_GetItemRef() and remove outdated comment in Modules/_pickle.c.
1 parent 9ab004d commit 21403af

4 files changed

Lines changed: 58 additions & 12 deletions

File tree

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
Add tests on the undocumented and deprecated ``_Py_Identifier`` C API. Patch
2+
by Victor Stinner.

Modules/_pickle.c

Lines changed: 3 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -4745,17 +4745,9 @@ save(PickleState *st, PicklerObject *self, PyObject *obj, int pers_save)
47454745
* __reduce_ex__ method, or the object's __reduce__ method.
47464746
*/
47474747
if (self->dispatch_table == NULL) {
4748-
reduce_func = PyDict_GetItemWithError(st->dispatch_table,
4749-
(PyObject *)type);
4750-
if (reduce_func == NULL) {
4751-
if (PyErr_Occurred()) {
4752-
goto error;
4753-
}
4754-
} else {
4755-
/* PyDict_GetItemWithError() returns a borrowed reference.
4756-
Increase the reference count to be consistent with
4757-
PyObject_GetItem and _PyObject_GetAttrId used below. */
4758-
Py_INCREF(reduce_func);
4748+
if (PyDict_GetItemRef(st->dispatch_table, (PyObject *)type,
4749+
&reduce_func) < 0) {
4750+
goto error;
47594751
}
47604752
}
47614753
else if (PyMapping_GetOptionalItem(self->dispatch_table, (PyObject *)type,

Modules/_testcapi/unicode.c

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -227,6 +227,55 @@ unicode_GET_CACHED_HASH(PyObject *self, PyObject *arg)
227227
}
228228

229229

230+
// Test the deprecated _Py_Identifier C API:
231+
// - _Py_IDENTIFIER()
232+
// - _Py_static_string()
233+
// - _Py_static_string_init()
234+
// - _PyObject_CallMethodId()
235+
// - _PyObject_GetAttrId()
236+
// - _PyUnicode_FromId()
237+
//
238+
// _testembed also has tests on _PyUnicode_FromId().
239+
static PyObject*
240+
test_py_identifier(PyObject *self, PyObject *Py_UNUSED(args))
241+
{
242+
// Ignore deprecation warnings
243+
_Py_COMP_DIAG_PUSH
244+
_Py_COMP_DIAG_IGNORE_DEPR_DECLS
245+
246+
_Py_IDENTIFIER(hello);
247+
PyObject *str = _PyUnicode_FromId(&PyId_hello); // borrowed ref
248+
if (str == NULL) {
249+
return NULL;
250+
}
251+
assert(PyUnicode_EqualToUTF8(str, "hello") == 1);
252+
253+
// Calling twice return the same object
254+
PyObject *str2 = _PyUnicode_FromId(&PyId_hello); // borrowed ref
255+
assert(str2 == str);
256+
257+
PyObject *number = Py_GetConstant(Py_CONSTANT_ONE); // immortal
258+
_Py_static_string(to_bytes_id, "to_bytes");
259+
PyObject *res = _PyObject_CallMethodId(number, &to_bytes_id, NULL);
260+
if (res == NULL) {
261+
return NULL;
262+
}
263+
Py_DECREF(res);
264+
265+
static _Py_Identifier real_id = _Py_static_string_init("real");
266+
res = _PyObject_GetAttrId(number, &real_id);
267+
if (res == NULL) {
268+
return NULL;
269+
}
270+
assert(res == number);
271+
Py_DECREF(res);
272+
273+
Py_RETURN_NONE;
274+
275+
_Py_COMP_DIAG_POP
276+
}
277+
278+
230279
// --- PyUnicodeWriter type -------------------------------------------------
231280

232281
typedef struct {
@@ -572,6 +621,7 @@ static PyMethodDef TestMethods[] = {
572621
{"unicode_asutf8", unicode_asutf8, METH_VARARGS},
573622
{"unicode_copycharacters", unicode_copycharacters, METH_VARARGS},
574623
{"unicode_GET_CACHED_HASH", unicode_GET_CACHED_HASH, METH_O},
624+
{"test_py_identifier", test_py_identifier, METH_NOARGS},
575625
{NULL},
576626
};
577627

Tools/c-analyzer/cpython/ignored.tsv

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -787,7 +787,9 @@ Modules/clinic/grpmodule.c.h grp_getgrgid _keywords -
787787
Modules/clinic/grpmodule.c.h grp_getgrnam _keywords -
788788
Objects/object.c - constants static PyObject*[]
789789
Objects/dictobject.c - PyFrozenDict_Type -
790-
790+
Modules/_testcapi/unicode.c test_py_identifier PyId_hello -
791+
Modules/_testcapi/unicode.c test_py_identifier to_bytes_id -
792+
Modules/_testcapi/unicode.c test_py_identifier real_id -
791793

792794
## False positives
793795
Python/specialize.c - _Py_InitCleanup -

0 commit comments

Comments
 (0)