Issue #2389: Pickle array objects using a list representation for portability

across different machine architectures and compatibility with Python 3.x.
This commit is contained in:
Alexandre Vassalotti 2009-07-15 18:19:47 +00:00
parent d5a23e322f
commit 999ecc0eaf
2 changed files with 35 additions and 35 deletions

View File

@ -1262,6 +1262,8 @@ Tests
support.EnvironmentVarGuard objects restored the environment variables
incorrectly on __exit__.
- Issue #2389: Array objects are now pickled in a portable manner.
What's New in Python 2.6 final
==============================

View File

@ -1156,40 +1156,6 @@ PyDoc_STRVAR(byteswap_doc,
Byteswap all items of the array. If the items in the array are not 1, 2,\n\
4, or 8 bytes in size, RuntimeError is raised.");
static PyObject *
array_reduce(arrayobject *array)
{
PyObject *dict, *result;
dict = PyObject_GetAttrString((PyObject *)array, "__dict__");
if (dict == NULL) {
PyErr_Clear();
dict = Py_None;
Py_INCREF(dict);
}
if (Py_SIZE(array) > 0) {
if (array->ob_descr->itemsize
> PY_SSIZE_T_MAX / array->ob_size) {
return PyErr_NoMemory();
}
result = Py_BuildValue("O(cs#)O",
Py_TYPE(array),
array->ob_descr->typecode,
array->ob_item,
Py_SIZE(array) * array->ob_descr->itemsize,
dict);
} else {
result = Py_BuildValue("O(c)O",
Py_TYPE(array),
array->ob_descr->typecode,
dict);
}
Py_DECREF(dict);
return result;
}
PyDoc_STRVAR(array_doc, "Return state information for pickling.");
static PyObject *
array_reverse(arrayobject *self, PyObject *unused)
{
@ -1527,6 +1493,38 @@ an array of some other type.");
#endif /* Py_USING_UNICODE */
static PyObject *
array_reduce(arrayobject *array)
{
PyObject *dict, *result, *list;
dict = PyObject_GetAttrString((PyObject *)array, "__dict__");
if (dict == NULL) {
if (!PyErr_ExceptionMatches(PyExc_AttributeError))
return NULL;
PyErr_Clear();
dict = Py_None;
Py_INCREF(dict);
}
/* Unlike in Python 3.x, we never use the more efficient memory
* representation of an array for pickling. This is unfortunately
* necessary to allow array objects to be unpickled by Python 3.x,
* since str objects from 2.x are always decoded to unicode in
* Python 3.x.
*/
list = array_tolist(array, NULL);
if (list == NULL) {
Py_DECREF(dict);
return NULL;
}
result = Py_BuildValue(
"O(cO)O", Py_TYPE(array), array->ob_descr->typecode, list, dict);
Py_DECREF(list);
Py_DECREF(dict);
return result;
}
PyDoc_STRVAR(reduce_doc, "Return state information for pickling.");
static PyObject *
array_get_typecode(arrayobject *a, void *closure)
@ -1583,7 +1581,7 @@ static PyMethodDef array_methods[] = {
{"read", (PyCFunction)array_fromfile_as_read, METH_VARARGS,
fromfile_doc},
{"__reduce__", (PyCFunction)array_reduce, METH_NOARGS,
array_doc},
reduce_doc},
{"remove", (PyCFunction)array_remove, METH_O,
remove_doc},
{"reverse", (PyCFunction)array_reverse, METH_NOARGS,