[Python-checkins] r51506 - in python/branches/int_unification: Lib/pickle.py Modules/cPickle.c
martin.v.loewis
python-checkins at python.org
Wed Aug 23 17:00:21 CEST 2006
Author: martin.v.loewis
Date: Wed Aug 23 17:00:19 2006
New Revision: 51506
Modified:
python/branches/int_unification/Lib/pickle.py
python/branches/int_unification/Modules/cPickle.c
Log:
Adjust pickle implementation to int/long unification.
Use INT codes for small integers on binary protocols,
and LONG codes otherwise.
Modified: python/branches/int_unification/Lib/pickle.py
==============================================================================
--- python/branches/int_unification/Lib/pickle.py (original)
+++ python/branches/int_unification/Lib/pickle.py Wed Aug 23 17:00:19 2006
@@ -456,9 +456,29 @@
return
# Text pickle, or int too big to fit in signed 4-byte format.
self.write(INT + repr(obj) + '\n')
- dispatch[IntType] = save_int
+ # XXX save_int is merged into save_long
+ # dispatch[IntType] = save_int
def save_long(self, obj, pack=struct.pack):
+ if self.bin:
+ # If the int is small enough to fit in a signed 4-byte 2's-comp
+ # format, we can store it more efficiently than the general
+ # case.
+ # First one- and two-byte unsigned ints:
+ if obj >= 0:
+ if obj <= 0xff:
+ self.write(BININT1 + chr(obj))
+ return
+ if obj <= 0xffff:
+ self.write("%c%c%c" % (BININT2, obj&0xff, obj>>8))
+ return
+ # Next check for 4-byte signed ints:
+ high_bits = obj >> 31 # note that Python shift sign-extends
+ if high_bits == 0 or high_bits == -1:
+ # All high bits are copies of bit 2**31, so the value
+ # fits in a 4-byte signed int.
+ self.write(BININT + pack("<i", obj))
+ return
if self.proto >= 2:
bytes = encode_long(obj)
n = len(bytes)
Modified: python/branches/int_unification/Modules/cPickle.c
==============================================================================
--- python/branches/int_unification/Modules/cPickle.c (original)
+++ python/branches/int_unification/Modules/cPickle.c Wed Aug 23 17:00:19 2006
@@ -711,7 +711,9 @@
PyErr_SetString(PicklingError, "no int where int expected in memo");
return -1;
}
- c_value = PyInt_AS_LONG((PyIntObject*)value);
+ c_value = PyInt_AsLong(value);
+ if (c_value == -1 && PyErr_Occurred())
+ return -1;
if (!self->bin) {
s[0] = GET;
@@ -958,7 +960,7 @@
{
static const char *buf[2] = {FALSE, TRUE};
static char len[2] = {sizeof(FALSE)-1, sizeof(TRUE)-1};
- long l = PyInt_AS_LONG((PyIntObject *)args);
+ long l = args == Py_True;
if (self->proto >= 2) {
char opcode = l ? NEWTRUE : NEWFALSE;
@@ -971,10 +973,9 @@
}
static int
-save_int(Picklerobject *self, PyObject *args)
+save_int(Picklerobject *self, long l)
{
char c_str[32];
- long l = PyInt_AS_LONG((PyIntObject *)args);
int len = 0;
if (!self->bin
@@ -1027,9 +1028,16 @@
int size;
int res = -1;
PyObject *repr = NULL;
-
+ int val = PyInt_AsLong(args);
static char l = LONG;
+ if (val == -1 && PyErr_Occurred()) {
+ /* out of range for int pickling */
+ PyErr_Clear();
+ }
+ else
+ return save_int(self, val);
+
if (self->proto >= 2) {
/* Linear-time pickling. */
size_t nbits;
@@ -2179,13 +2187,6 @@
goto finally;
}
break;
- case 'i':
- if (type == &PyInt_Type) {
- res = save_int(self, args);
- goto finally;
- }
- break;
-
case 'l':
if (type == &PyLong_Type) {
res = save_long(self, args);
@@ -2482,7 +2483,9 @@
rsize += PyString_GET_SIZE(k);
else if (PyInt_Check(k)) { /* put */
- ik = PyInt_AS_LONG((PyIntObject*)k);
+ ik = PyInt_AsLong(k);
+ if (ik == -1 && PyErr_Occurred())
+ goto err;
if (ik >= lm || ik == 0) {
PyErr_SetString(PicklingError,
"Invalid get data");
@@ -2502,7 +2505,9 @@
}
else { /* put */
- ik = PyInt_AS_LONG((PyIntObject *)k);
+ ik = PyInt_AsLong(k);
+ if (ik == -1 && PyErr_Occurred())
+ goto err;
if (ik >= lm || ik == 0) {
PyErr_SetString(PicklingError,
"Invalid get data");
@@ -2531,8 +2536,9 @@
}
else if (PyTuple_Check(k)) { /* get */
- ik = PyInt_AS_LONG((PyIntObject *)
- PyTuple_GET_ITEM(k, 0));
+ ik = PyLong_AsLong(PyTuple_GET_ITEM(k, 0));
+ if (ik == -1 && PyErr_Occurred())
+ goto err;
if (ik < 256) {
*s++ = BINGET;
*s++ = (int)(ik & 0xff);
@@ -2547,7 +2553,9 @@
}
else { /* put */
- ik = PyInt_AS_LONG((PyIntObject*)k);
+ ik = PyLong_AsLong(k);
+ if (ik == -1 && PyErr_Occurred())
+ goto err;
if (have_get[ik]) { /* with matching get */
if (ik < 256) {
More information about the Python-checkins
mailing list