Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit e0a3907

Browse files
committed
PDATA_PUSH and PDATA_APPEND. documented, and reformatted for better
readability. load_bool(): Now that I know the intended difference between _PUSH and _APPEND, used the right one. Pdata_grow(): Squashed out a redundant overflow test.
1 parent 4b37364 commit e0a3907

1 file changed

Lines changed: 38 additions & 30 deletions

File tree

Modules/cPickle.c

Lines changed: 38 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -188,10 +188,8 @@ Pdata_grow(Pdata *self)
188188
int bigger;
189189
size_t nbytes;
190190

191-
if (! self->size)
192-
goto nomemory;
193191
bigger = self->size << 1;
194-
if (bigger <= 0)
192+
if (bigger <= 0) /* was 0, or new value overflows */
195193
goto nomemory;
196194
if ((int)(size_t)bigger != bigger)
197195
goto nomemory;
@@ -210,19 +208,47 @@ Pdata_grow(Pdata *self)
210208
return -1;
211209
}
212210

213-
/* D is a Pdata *. Pop the topmost element and store it into V, which
214-
* must be an lvalue holding PyObject *. On stack underflow, UnpicklingError
211+
/* D is a Pdata*. Pop the topmost element and store it into V, which
212+
* must be an lvalue holding PyObject*. On stack underflow, UnpicklingError
215213
* is raised and V is set to NULL. D and V may be evaluated several times.
216214
*/
217215
#define PDATA_POP(D, V) { \
218-
if ((D)->length) \
219-
(V) = (D)->data[--((D)->length)]; \
220-
else { \
221-
PyErr_SetString(UnpicklingError, "bad pickle data"); \
222-
(V) = NULL; \
223-
} \
216+
if ((D)->length) \
217+
(V) = (D)->data[--((D)->length)]; \
218+
else { \
219+
PyErr_SetString(UnpicklingError, "bad pickle data"); \
220+
(V) = NULL; \
221+
} \
222+
}
223+
224+
/* PDATA_PUSH and PDATA_APPEND both push rvalue PyObject* O on to Pdata*
225+
* D. If the Pdata stack can't be grown to hold the new value, both
226+
* raise MemoryError and execute "return ER". The difference is in ownership
227+
* of O after: _PUSH transfers ownership of O from the caller to the stack
228+
* (no incref of O is done, and in case of error O is decrefed), while
229+
* _APPEND pushes a new reference.
230+
*/
231+
232+
/* Push O on stack D, giving ownership of O to the stack. */
233+
#define PDATA_PUSH(D, O, ER) { \
234+
if (((Pdata*)(D))->length == ((Pdata*)(D))->size && \
235+
Pdata_grow((Pdata*)(D)) < 0) { \
236+
Py_DECREF(O); \
237+
return ER; \
238+
} \
239+
((Pdata*)(D))->data[((Pdata*)(D))->length++] = (O); \
240+
}
241+
242+
/* Push O on stack D, pushing a new reference. */
243+
#define PDATA_APPEND(D, O, ER) { \
244+
if (((Pdata*)(D))->length == ((Pdata*)(D))->size && \
245+
Pdata_grow((Pdata*)(D)) < 0) \
246+
return ER; \
247+
Py_INCREF(O); \
248+
((Pdata*)(D))->data[((Pdata*)(D))->length++] = (O); \
224249
}
225250

251+
226252
static PyObject *
227253
Pdata_popTuple(Pdata *self, int start)
228254
{
@@ -255,23 +281,6 @@ Pdata_popList(Pdata *self, int start)
255281
return r;
256282
}
257283

258-
#define PDATA_APPEND(D,O,ER) { \
259-
if (((Pdata*)(D))->length == ((Pdata*)(D))->size && \
260-
Pdata_grow((Pdata*)(D)) < 0) \
261-
return ER; \
262-
Py_INCREF(O); \
263-
((Pdata*)(D))->data[((Pdata*)(D))->length++]=O; \
264-
}
265-
266-
#define PDATA_PUSH(D,O,ER) { \
267-
if (((Pdata*)(D))->length == ((Pdata*)(D))->size && \
268-
Pdata_grow((Pdata*)(D)) < 0) { \
269-
Py_DECREF(O); \
270-
return ER; \
271-
} \
272-
((Pdata*)(D))->data[((Pdata*)(D))->length++]=O; \
273-
}
274-
275284
/*************************************************************************/
276285

277286
#define ARG_TUP(self, o) { \
@@ -2886,8 +2895,7 @@ static int
28862895
load_bool(Unpicklerobject *self, PyObject *boolean)
28872896
{
28882897
assert(boolean == Py_True || boolean == Py_False);
2889-
Py_INCREF(boolean);
2890-
PDATA_PUSH(self->stack, boolean, -1);
2898+
PDATA_APPEND(self->stack, boolean, -1);
28912899
return 0;
28922900
}
28932901

0 commit comments

Comments
 (0)