diff options
author | Victor Stinner <victor.stinner@gmail.com> | 2016-12-09 14:18:31 (GMT) |
---|---|---|
committer | Victor Stinner <victor.stinner@gmail.com> | 2016-12-09 14:18:31 (GMT) |
commit | 56707648120de77a5167c363cc4104dfe2cef5be (patch) | |
tree | 505f07e4094676895b21139be187b1c5c165d985 | |
parent | ddc120f4cf6fb049570d5483bb7678491d27b3d5 (diff) | |
download | cpython-56707648120de77a5167c363cc4104dfe2cef5be.zip cpython-56707648120de77a5167c363cc4104dfe2cef5be.tar.gz cpython-56707648120de77a5167c363cc4104dfe2cef5be.tar.bz2 |
Use _PyObject_CallMethodIdObjArgs() in _ctypes
Issue #28915: Replace _PyObject_CallMethodId() with
_PyObject_CallMethodIdObjArgs() in unpickle(). _PyObject_CallMethodIdObjArgs()
avoids the creation of a temporary tuple and doesn't have to parse a format
string.
Replace _PyObject_CallMethodId() with _PyObject_GetAttrId()+PyObject_Call() for
the second call since it requires to "unpack" a tuple.
Add also a check in the type of the second parameter (state): it must be a
tuple.
-rw-r--r-- | Modules/_ctypes/callproc.c | 34 |
1 files changed, 21 insertions, 13 deletions
diff --git a/Modules/_ctypes/callproc.c b/Modules/_ctypes/callproc.c index 7d542fb..f408fd3 100644 --- a/Modules/_ctypes/callproc.c +++ b/Modules/_ctypes/callproc.c @@ -1631,25 +1631,33 @@ resize(PyObject *self, PyObject *args) static PyObject * unpickle(PyObject *self, PyObject *args) { - PyObject *typ; - PyObject *state; - PyObject *result; - PyObject *tmp; + PyObject *typ, *state, *meth, *obj, *result; _Py_IDENTIFIER(__new__); _Py_IDENTIFIER(__setstate__); - if (!PyArg_ParseTuple(args, "OO", &typ, &state)) + if (!PyArg_ParseTuple(args, "OO!", &typ, &PyTuple_Type, &state)) return NULL; - result = _PyObject_CallMethodId(typ, &PyId___new__, "O", typ); - if (result == NULL) - return NULL; - tmp = _PyObject_CallMethodId(result, &PyId___setstate__, "O", state); - if (tmp == NULL) { - Py_DECREF(result); + obj = _PyObject_CallMethodIdObjArgs(typ, &PyId___new__, typ, NULL); + if (obj == NULL) return NULL; + + meth = _PyObject_GetAttrId(obj, &PyId___setstate__); + if (meth == NULL) { + goto error; } - Py_DECREF(tmp); - return result; + + result = PyObject_Call(meth, state, NULL); + Py_DECREF(meth); + if (result == NULL) { + goto error; + } + Py_DECREF(result); + + return obj; + +error: + Py_DECREF(obj); + return NULL; } static PyObject * |