blob: 3391085ccb077b82ed43416447dfc2476ddecdc0 [file] [log] [blame]
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001
2/* Write Python objects to files and read them back.
3 This is intended for writing and reading compiled Python code only;
4 a true persistent storage facility would be much harder, since
5 it would have to take circular links and sharing into account. */
6
Thomas Wouters695934a2006-03-01 23:49:13 +00007#define PY_SSIZE_T_CLEAN
8
Guido van Rossum79f25d91997-04-29 20:08:16 +00009#include "Python.h"
Guido van Rossumdce2e3d1991-06-04 19:42:30 +000010#include "longintrepr.h"
Jeremy Hylton3e0055f2005-10-20 19:59:25 +000011#include "code.h"
Guido van Rossumdce2e3d1991-06-04 19:42:30 +000012#include "marshal.h"
13
Mark Dickinsonbd792642009-03-18 20:06:12 +000014#define ABS(x) ((x) < 0 ? -(x) : (x))
15
Fred Drake6da0b912000-06-28 18:47:56 +000016/* High water mark to determine when the marshalled object is dangerously deep
17 * and risks coring the interpreter. When the object stack gets this deep,
18 * raise an exception instead of continuing.
Guido van Rossum63175a12007-08-29 20:39:13 +000019 * On Windows debug builds, reduce this value.
Fred Drake6da0b912000-06-28 18:47:56 +000020 */
Guido van Rossum63175a12007-08-29 20:39:13 +000021#if defined(MS_WINDOWS) && defined(_DEBUG)
22#define MAX_MARSHAL_STACK_DEPTH 1500
23#else
Guido van Rossumd59da4b2007-05-22 18:11:13 +000024#define MAX_MARSHAL_STACK_DEPTH 2000
Guido van Rossum63175a12007-08-29 20:39:13 +000025#endif
Fred Drake6da0b912000-06-28 18:47:56 +000026
Michael W. Hudsondf888462005-06-03 14:41:55 +000027#define TYPE_NULL '0'
28#define TYPE_NONE 'N'
29#define TYPE_FALSE 'F'
30#define TYPE_TRUE 'T'
31#define TYPE_STOPITER 'S'
32#define TYPE_ELLIPSIS '.'
33#define TYPE_INT 'i'
34#define TYPE_INT64 'I'
35#define TYPE_FLOAT 'f'
36#define TYPE_BINARY_FLOAT 'g'
37#define TYPE_COMPLEX 'x'
38#define TYPE_BINARY_COMPLEX 'y'
39#define TYPE_LONG 'l'
40#define TYPE_STRING 's'
Michael W. Hudsondf888462005-06-03 14:41:55 +000041#define TYPE_TUPLE '('
42#define TYPE_LIST '['
43#define TYPE_DICT '{'
44#define TYPE_CODE 'c'
45#define TYPE_UNICODE 'u'
46#define TYPE_UNKNOWN '?'
47#define TYPE_SET '<'
48#define TYPE_FROZENSET '>'
Guido van Rossumdce2e3d1991-06-04 19:42:30 +000049
Eric Smithb1a03cf2009-04-21 11:57:38 +000050#define WFERR_OK 0
51#define WFERR_UNMARSHALLABLE 1
52#define WFERR_NESTEDTOODEEP 2
53#define WFERR_NOMEMORY 3
54
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000055typedef struct {
56 FILE *fp;
Eric Smithb1a03cf2009-04-21 11:57:38 +000057 int error; /* see WFERR_* values */
Fred Drake6da0b912000-06-28 18:47:56 +000058 int depth;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000059 /* If fp == NULL, the following are valid: */
Guido van Rossum79f25d91997-04-29 20:08:16 +000060 PyObject *str;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000061 char *ptr;
62 char *end;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +000063 PyObject *strings; /* dict on marshal, list on unmarshal */
Michael W. Hudsondf888462005-06-03 14:41:55 +000064 int version;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000065} WFILE;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +000066
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000067#define w_byte(c, p) if (((p)->fp)) putc((c), (p)->fp); \
68 else if ((p)->ptr != (p)->end) *(p)->ptr++ = (c); \
69 else w_more(c, p)
70
71static void
Fredrik Lundh11534382000-07-23 18:24:06 +000072w_more(int c, WFILE *p)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000073{
Martin v. Löwis18e16552006-02-15 17:27:45 +000074 Py_ssize_t size, newsize;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000075 if (p->str == NULL)
76 return; /* An error already occurred */
Christian Heimes72b710a2008-05-26 13:28:38 +000077 size = PyBytes_Size(p->str);
Alexandre Vassalotti5f8ced22008-05-16 00:03:33 +000078 newsize = size + size + 1024;
79 if (newsize > 32*1024*1024) {
Amaury Forgeot d'Arc35c86582008-06-17 21:11:29 +000080 newsize = size + (size >> 3); /* 12.5% overallocation */
Alexandre Vassalotti5f8ced22008-05-16 00:03:33 +000081 }
Christian Heimes72b710a2008-05-26 13:28:38 +000082 if (_PyBytes_Resize(&p->str, newsize) != 0) {
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000083 p->ptr = p->end = NULL;
84 }
85 else {
Christian Heimes72b710a2008-05-26 13:28:38 +000086 p->ptr = PyBytes_AS_STRING((PyBytesObject *)p->str) + size;
Guido van Rossum79f25d91997-04-29 20:08:16 +000087 p->end =
Christian Heimes72b710a2008-05-26 13:28:38 +000088 PyBytes_AS_STRING((PyBytesObject *)p->str) + newsize;
Tim Peters8315ea52000-07-23 19:28:35 +000089 *p->ptr++ = Py_SAFE_DOWNCAST(c, int, char);
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000090 }
91}
92
93static void
Thomas Woutersf70ef4f2000-07-22 18:47:25 +000094w_string(char *s, int n, WFILE *p)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000095{
96 if (p->fp != NULL) {
97 fwrite(s, 1, n, p->fp);
98 }
99 else {
100 while (--n >= 0) {
101 w_byte(*s, p);
102 s++;
103 }
104 }
105}
106
107static void
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000108w_short(int x, WFILE *p)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000109{
Thomas Heller3e1c18a2002-07-30 11:40:57 +0000110 w_byte((char)( x & 0xff), p);
111 w_byte((char)((x>> 8) & 0xff), p);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000112}
113
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000114static void
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000115w_long(long x, WFILE *p)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000116{
Thomas Heller37d5a152002-07-30 11:44:44 +0000117 w_byte((char)( x & 0xff), p);
118 w_byte((char)((x>> 8) & 0xff), p);
119 w_byte((char)((x>>16) & 0xff), p);
120 w_byte((char)((x>>24) & 0xff), p);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000121}
122
Guido van Rossumc1547d91996-12-10 15:39:04 +0000123#if SIZEOF_LONG > 4
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000124static void
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000125w_long64(long x, WFILE *p)
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000126{
127 w_long(x, p);
Guido van Rossumc1547d91996-12-10 15:39:04 +0000128 w_long(x>>32, p);
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000129}
Guido van Rossumc1547d91996-12-10 15:39:04 +0000130#endif
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000131
Mark Dickinsonbd792642009-03-18 20:06:12 +0000132/* We assume that Python longs are stored internally in base some power of
133 2**15; for the sake of portability we'll always read and write them in base
134 exactly 2**15. */
135
136#define PyLong_MARSHAL_SHIFT 15
137#define PyLong_MARSHAL_BASE ((short)1 << PyLong_MARSHAL_SHIFT)
138#define PyLong_MARSHAL_MASK (PyLong_MARSHAL_BASE - 1)
139#if PyLong_SHIFT % PyLong_MARSHAL_SHIFT != 0
140#error "PyLong_SHIFT must be a multiple of PyLong_MARSHAL_SHIFT"
141#endif
142#define PyLong_MARSHAL_RATIO (PyLong_SHIFT / PyLong_MARSHAL_SHIFT)
143
144static void
145w_PyLong(const PyLongObject *ob, WFILE *p)
146{
147 Py_ssize_t i, j, n, l;
148 digit d;
149
150 w_byte(TYPE_LONG, p);
151 if (Py_SIZE(ob) == 0) {
152 w_long((long)0, p);
153 return;
154 }
155
156 /* set l to number of base PyLong_MARSHAL_BASE digits */
157 n = ABS(Py_SIZE(ob));
158 l = (n-1) * PyLong_MARSHAL_RATIO;
159 d = ob->ob_digit[n-1];
160 assert(d != 0); /* a PyLong is always normalized */
161 do {
162 d >>= PyLong_MARSHAL_SHIFT;
163 l++;
164 } while (d != 0);
165 w_long((long)(Py_SIZE(ob) > 0 ? l : -l), p);
166
167 for (i=0; i < n-1; i++) {
168 d = ob->ob_digit[i];
169 for (j=0; j < PyLong_MARSHAL_RATIO; j++) {
170 w_short(d & PyLong_MARSHAL_MASK, p);
171 d >>= PyLong_MARSHAL_SHIFT;
172 }
173 assert (d == 0);
174 }
175 d = ob->ob_digit[n-1];
176 do {
177 w_short(d & PyLong_MARSHAL_MASK, p);
178 d >>= PyLong_MARSHAL_SHIFT;
179 } while (d != 0);
180}
181
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000182static void
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000183w_object(PyObject *v, WFILE *p)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000184{
Martin v. Löwis18e16552006-02-15 17:27:45 +0000185 Py_ssize_t i, n;
Fred Drake6da0b912000-06-28 18:47:56 +0000186
187 p->depth++;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000188
Fred Drake6da0b912000-06-28 18:47:56 +0000189 if (p->depth > MAX_MARSHAL_STACK_DEPTH) {
Eric Smithb1a03cf2009-04-21 11:57:38 +0000190 p->error = WFERR_NESTEDTOODEEP;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000191 }
Fred Drake6da0b912000-06-28 18:47:56 +0000192 else if (v == NULL) {
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000193 w_byte(TYPE_NULL, p);
Guido van Rossum730806d1998-04-10 22:27:42 +0000194 }
195 else if (v == Py_None) {
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000196 w_byte(TYPE_NONE, p);
Guido van Rossum730806d1998-04-10 22:27:42 +0000197 }
Tim Peters5ca576e2001-06-18 22:08:13 +0000198 else if (v == PyExc_StopIteration) {
199 w_byte(TYPE_STOPITER, p);
200 }
Guido van Rossum730806d1998-04-10 22:27:42 +0000201 else if (v == Py_Ellipsis) {
202 w_byte(TYPE_ELLIPSIS, p);
203 }
Guido van Rossum77f6a652002-04-03 22:41:51 +0000204 else if (v == Py_False) {
205 w_byte(TYPE_FALSE, p);
206 }
207 else if (v == Py_True) {
208 w_byte(TYPE_TRUE, p);
209 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000210 else if (PyLong_CheckExact(v)) {
Guido van Rossumddefaf32007-01-14 03:31:43 +0000211 long x = PyLong_AsLong(v);
212 if ((x == -1) && PyErr_Occurred()) {
213 PyLongObject *ob = (PyLongObject *)v;
214 PyErr_Clear();
Mark Dickinsonbd792642009-03-18 20:06:12 +0000215 w_PyLong(ob, p);
216 }
Guido van Rossumddefaf32007-01-14 03:31:43 +0000217 else {
Guido van Rossumc1547d91996-12-10 15:39:04 +0000218#if SIZEOF_LONG > 4
Guido van Rossumddefaf32007-01-14 03:31:43 +0000219 long y = Py_ARITHMETIC_RIGHT_SHIFT(long, x, 31);
220 if (y && y != -1) {
221 w_byte(TYPE_INT64, p);
222 w_long64(x, p);
223 }
224 else
Guido van Rossumc1547d91996-12-10 15:39:04 +0000225#endif
226 {
Guido van Rossumddefaf32007-01-14 03:31:43 +0000227 w_byte(TYPE_INT, p);
228 w_long(x, p);
229 }
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000230 }
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000231 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000232 else if (PyFloat_CheckExact(v)) {
Michael W. Hudsondf888462005-06-03 14:41:55 +0000233 if (p->version > 1) {
Brett Cannonc9371d42005-06-25 08:23:41 +0000234 unsigned char buf[8];
Michael W. Hudsondf888462005-06-03 14:41:55 +0000235 if (_PyFloat_Pack8(PyFloat_AsDouble(v),
236 buf, 1) < 0) {
Eric Smithb1a03cf2009-04-21 11:57:38 +0000237 p->error = WFERR_UNMARSHALLABLE;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000238 return;
239 }
240 w_byte(TYPE_BINARY_FLOAT, p);
Brett Cannonc9371d42005-06-25 08:23:41 +0000241 w_string((char*)buf, 8, p);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000242 }
243 else {
Eric Smith0923d1d2009-04-16 20:16:10 +0000244 char *buf = PyOS_double_to_string(PyFloat_AS_DOUBLE(v),
Mark Dickinson3e09f432009-04-17 08:41:23 +0000245 'g', 17, 0, NULL);
Eric Smithb1a03cf2009-04-21 11:57:38 +0000246 if (!buf) {
247 p->error = WFERR_NOMEMORY;
248 return;
249 }
Eric Smith0923d1d2009-04-16 20:16:10 +0000250 n = strlen(buf);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000251 w_byte(TYPE_FLOAT, p);
Martin v. Löwis67baee62006-02-16 14:37:48 +0000252 w_byte((int)n, p);
Martin v. Löwis725507b2006-03-07 12:08:51 +0000253 w_string(buf, (int)n, p);
Eric Smith0923d1d2009-04-16 20:16:10 +0000254 PyMem_Free(buf);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000255 }
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000256 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000257 else if (PyComplex_CheckExact(v)) {
Michael W. Hudsondf888462005-06-03 14:41:55 +0000258 if (p->version > 1) {
Brett Cannonc9371d42005-06-25 08:23:41 +0000259 unsigned char buf[8];
Michael W. Hudsondf888462005-06-03 14:41:55 +0000260 if (_PyFloat_Pack8(PyComplex_RealAsDouble(v),
261 buf, 1) < 0) {
Eric Smithb1a03cf2009-04-21 11:57:38 +0000262 p->error = WFERR_UNMARSHALLABLE;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000263 return;
264 }
265 w_byte(TYPE_BINARY_COMPLEX, p);
Brett Cannonc9371d42005-06-25 08:23:41 +0000266 w_string((char*)buf, 8, p);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000267 if (_PyFloat_Pack8(PyComplex_ImagAsDouble(v),
268 buf, 1) < 0) {
Eric Smithb1a03cf2009-04-21 11:57:38 +0000269 p->error = WFERR_UNMARSHALLABLE;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000270 return;
271 }
Brett Cannonc9371d42005-06-25 08:23:41 +0000272 w_string((char*)buf, 8, p);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000273 }
274 else {
Eric Smith0923d1d2009-04-16 20:16:10 +0000275 char *buf;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000276 w_byte(TYPE_COMPLEX, p);
Eric Smith0923d1d2009-04-16 20:16:10 +0000277 buf = PyOS_double_to_string(PyComplex_RealAsDouble(v),
Mark Dickinson3e09f432009-04-17 08:41:23 +0000278 'g', 17, 0, NULL);
Eric Smithb1a03cf2009-04-21 11:57:38 +0000279 if (!buf) {
280 p->error = WFERR_NOMEMORY;
281 return;
282 }
Martin v. Löwis725507b2006-03-07 12:08:51 +0000283 n = strlen(buf);
284 w_byte((int)n, p);
285 w_string(buf, (int)n, p);
Eric Smith0923d1d2009-04-16 20:16:10 +0000286 PyMem_Free(buf);
287 buf = PyOS_double_to_string(PyComplex_ImagAsDouble(v),
Mark Dickinson3e09f432009-04-17 08:41:23 +0000288 'g', 17, 0, NULL);
Eric Smithb1a03cf2009-04-21 11:57:38 +0000289 if (!buf) {
290 p->error = WFERR_NOMEMORY;
291 return;
292 }
Eric Smith0923d1d2009-04-16 20:16:10 +0000293 n = strlen(buf);
Martin v. Löwis725507b2006-03-07 12:08:51 +0000294 w_byte((int)n, p);
295 w_string(buf, (int)n, p);
Eric Smith0923d1d2009-04-16 20:16:10 +0000296 PyMem_Free(buf);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000297 }
Guido van Rossum8a5c5d21996-01-12 01:09:56 +0000298 }
Christian Heimes72b710a2008-05-26 13:28:38 +0000299 else if (PyBytes_CheckExact(v)) {
Guido van Rossum98297ee2007-11-06 21:34:58 +0000300 w_byte(TYPE_STRING, p);
Christian Heimes72b710a2008-05-26 13:28:38 +0000301 n = PyBytes_GET_SIZE(v);
Martin v. Löwis725507b2006-03-07 12:08:51 +0000302 if (n > INT_MAX) {
303 /* huge strings are not supported */
304 p->depth--;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000305 p->error = WFERR_UNMARSHALLABLE;
Martin v. Löwis725507b2006-03-07 12:08:51 +0000306 return;
307 }
Guido van Rossum3a205f71995-02-17 15:10:07 +0000308 w_long((long)n, p);
Christian Heimes72b710a2008-05-26 13:28:38 +0000309 w_string(PyBytes_AS_STRING(v), (int)n, p);
Guido van Rossumc279b532000-03-10 23:03:02 +0000310 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000311 else if (PyUnicode_CheckExact(v)) {
Guido van Rossumc279b532000-03-10 23:03:02 +0000312 PyObject *utf8;
Martin v. Löwisdb12d452009-05-02 18:52:14 +0000313 utf8 = PyUnicode_EncodeUTF8(PyUnicode_AS_UNICODE(v),
314 PyUnicode_GET_SIZE(v),
Martin v. Löwise0a2b722009-05-10 08:08:56 +0000315 "surrogatepass");
Guido van Rossumc279b532000-03-10 23:03:02 +0000316 if (utf8 == NULL) {
Guido van Rossum98626cd2000-06-28 23:24:19 +0000317 p->depth--;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000318 p->error = WFERR_UNMARSHALLABLE;
Guido van Rossum98626cd2000-06-28 23:24:19 +0000319 return;
Guido van Rossumc279b532000-03-10 23:03:02 +0000320 }
321 w_byte(TYPE_UNICODE, p);
Christian Heimes72b710a2008-05-26 13:28:38 +0000322 n = PyBytes_GET_SIZE(utf8);
Martin v. Löwis725507b2006-03-07 12:08:51 +0000323 if (n > INT_MAX) {
324 p->depth--;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000325 p->error = WFERR_UNMARSHALLABLE;
Martin v. Löwis725507b2006-03-07 12:08:51 +0000326 return;
327 }
Guido van Rossumc279b532000-03-10 23:03:02 +0000328 w_long((long)n, p);
Christian Heimes72b710a2008-05-26 13:28:38 +0000329 w_string(PyBytes_AS_STRING(utf8), (int)n, p);
Guido van Rossumc279b532000-03-10 23:03:02 +0000330 Py_DECREF(utf8);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000331 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000332 else if (PyTuple_CheckExact(v)) {
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000333 w_byte(TYPE_TUPLE, p);
Guido van Rossum79f25d91997-04-29 20:08:16 +0000334 n = PyTuple_Size(v);
Guido van Rossum3a205f71995-02-17 15:10:07 +0000335 w_long((long)n, p);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000336 for (i = 0; i < n; i++) {
Guido van Rossum79f25d91997-04-29 20:08:16 +0000337 w_object(PyTuple_GET_ITEM(v, i), p);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000338 }
339 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000340 else if (PyList_CheckExact(v)) {
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000341 w_byte(TYPE_LIST, p);
Guido van Rossumc279b532000-03-10 23:03:02 +0000342 n = PyList_GET_SIZE(v);
Guido van Rossum3a205f71995-02-17 15:10:07 +0000343 w_long((long)n, p);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000344 for (i = 0; i < n; i++) {
Guido van Rossumc279b532000-03-10 23:03:02 +0000345 w_object(PyList_GET_ITEM(v, i), p);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000346 }
347 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000348 else if (PyDict_CheckExact(v)) {
Martin v. Löwis18e16552006-02-15 17:27:45 +0000349 Py_ssize_t pos;
Guido van Rossum79f25d91997-04-29 20:08:16 +0000350 PyObject *key, *value;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000351 w_byte(TYPE_DICT, p);
Guido van Rossum64b45521991-06-07 13:58:22 +0000352 /* This one is NULL object terminated! */
Guido van Rossum25831651993-05-19 14:50:45 +0000353 pos = 0;
Guido van Rossum79f25d91997-04-29 20:08:16 +0000354 while (PyDict_Next(v, &pos, &key, &value)) {
Guido van Rossum25831651993-05-19 14:50:45 +0000355 w_object(key, p);
356 w_object(value, p);
Guido van Rossum64b45521991-06-07 13:58:22 +0000357 }
Guido van Rossum79f25d91997-04-29 20:08:16 +0000358 w_object((PyObject *)NULL, p);
Guido van Rossum64b45521991-06-07 13:58:22 +0000359 }
Guido van Rossum58da9312007-11-10 23:39:45 +0000360 else if (PyAnySet_CheckExact(v)) {
Raymond Hettingera422c342005-01-11 03:03:27 +0000361 PyObject *value, *it;
362
363 if (PyObject_TypeCheck(v, &PySet_Type))
364 w_byte(TYPE_SET, p);
365 else
366 w_byte(TYPE_FROZENSET, p);
367 n = PyObject_Size(v);
368 if (n == -1) {
369 p->depth--;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000370 p->error = WFERR_UNMARSHALLABLE;
Raymond Hettingera422c342005-01-11 03:03:27 +0000371 return;
372 }
373 w_long((long)n, p);
374 it = PyObject_GetIter(v);
375 if (it == NULL) {
376 p->depth--;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000377 p->error = WFERR_UNMARSHALLABLE;
Raymond Hettingera422c342005-01-11 03:03:27 +0000378 return;
379 }
380 while ((value = PyIter_Next(it)) != NULL) {
381 w_object(value, p);
382 Py_DECREF(value);
383 }
384 Py_DECREF(it);
385 if (PyErr_Occurred()) {
386 p->depth--;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000387 p->error = WFERR_UNMARSHALLABLE;
Raymond Hettingera422c342005-01-11 03:03:27 +0000388 return;
389 }
390 }
Guido van Rossum79f25d91997-04-29 20:08:16 +0000391 else if (PyCode_Check(v)) {
392 PyCodeObject *co = (PyCodeObject *)v;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000393 w_byte(TYPE_CODE, p);
Neal Norwitz7fdcb412002-06-14 01:07:39 +0000394 w_long(co->co_argcount, p);
Guido van Rossum4f72a782006-10-27 23:31:49 +0000395 w_long(co->co_kwonlyargcount, p);
Neal Norwitz7fdcb412002-06-14 01:07:39 +0000396 w_long(co->co_nlocals, p);
397 w_long(co->co_stacksize, p);
398 w_long(co->co_flags, p);
Guido van Rossumd076c731998-10-07 19:42:25 +0000399 w_object(co->co_code, p);
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000400 w_object(co->co_consts, p);
401 w_object(co->co_names, p);
Guido van Rossum681d79a1995-07-18 14:51:37 +0000402 w_object(co->co_varnames, p);
Jeremy Hylton64949cb2001-01-25 20:06:59 +0000403 w_object(co->co_freevars, p);
404 w_object(co->co_cellvars, p);
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000405 w_object(co->co_filename, p);
Guido van Rossum9bfef441993-03-29 10:43:31 +0000406 w_object(co->co_name, p);
Neal Norwitz7fdcb412002-06-14 01:07:39 +0000407 w_long(co->co_firstlineno, p);
Guido van Rossumd031c891997-01-24 03:44:17 +0000408 w_object(co->co_lnotab, p);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000409 }
Travis E. Oliphantb99f7622007-08-18 11:21:56 +0000410 else if (PyObject_CheckBuffer(v)) {
Guido van Rossumd076c731998-10-07 19:42:25 +0000411 /* Write unknown buffer-style objects as a string */
412 char *s;
Jeremy Hylton9f64caa2001-11-09 22:02:48 +0000413 PyBufferProcs *pb = v->ob_type->tp_as_buffer;
Travis E. Oliphant8ae62b62007-09-23 02:00:13 +0000414 Py_buffer view;
Travis E. Oliphantb99f7622007-08-18 11:21:56 +0000415 if ((*pb->bf_getbuffer)(v, &view, PyBUF_SIMPLE) != 0) {
416 w_byte(TYPE_UNKNOWN, p);
Eric Smithb1a03cf2009-04-21 11:57:38 +0000417 p->error = WFERR_UNMARSHALLABLE;
Travis E. Oliphantb99f7622007-08-18 11:21:56 +0000418 }
Guido van Rossumd076c731998-10-07 19:42:25 +0000419 w_byte(TYPE_STRING, p);
Travis E. Oliphantb99f7622007-08-18 11:21:56 +0000420 n = view.len;
421 s = view.buf;
Martin v. Löwis725507b2006-03-07 12:08:51 +0000422 if (n > INT_MAX) {
423 p->depth--;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000424 p->error = WFERR_UNMARSHALLABLE;
Martin v. Löwis725507b2006-03-07 12:08:51 +0000425 return;
426 }
Guido van Rossumd076c731998-10-07 19:42:25 +0000427 w_long((long)n, p);
Martin v. Löwis725507b2006-03-07 12:08:51 +0000428 w_string(s, (int)n, p);
Travis E. Oliphantb99f7622007-08-18 11:21:56 +0000429 if (pb->bf_releasebuffer != NULL)
430 (*pb->bf_releasebuffer)(v, &view);
Guido van Rossumd076c731998-10-07 19:42:25 +0000431 }
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000432 else {
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000433 w_byte(TYPE_UNKNOWN, p);
Eric Smithb1a03cf2009-04-21 11:57:38 +0000434 p->error = WFERR_UNMARSHALLABLE;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000435 }
Guido van Rossum98626cd2000-06-28 23:24:19 +0000436 p->depth--;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000437}
438
Martin v. Löwisef82d2f2004-06-27 16:51:46 +0000439/* version currently has no effect for writing longs. */
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000440void
Martin v. Löwisef82d2f2004-06-27 16:51:46 +0000441PyMarshal_WriteLongToFile(long x, FILE *fp, int version)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000442{
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000443 WFILE wf;
444 wf.fp = fp;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000445 wf.error = WFERR_OK;
Fred Drake6da0b912000-06-28 18:47:56 +0000446 wf.depth = 0;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +0000447 wf.strings = NULL;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000448 wf.version = version;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000449 w_long(x, &wf);
450}
451
452void
Martin v. Löwisef82d2f2004-06-27 16:51:46 +0000453PyMarshal_WriteObjectToFile(PyObject *x, FILE *fp, int version)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000454{
455 WFILE wf;
456 wf.fp = fp;
Eric Smithb1a03cf2009-04-21 11:57:38 +0000457 wf.error = WFERR_OK;
Guido van Rossum98626cd2000-06-28 23:24:19 +0000458 wf.depth = 0;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +0000459 wf.strings = (version > 0) ? PyDict_New() : NULL;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000460 wf.version = version;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000461 w_object(x, &wf);
Martin v. Löwisef82d2f2004-06-27 16:51:46 +0000462 Py_XDECREF(wf.strings);
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000463}
464
465typedef WFILE RFILE; /* Same struct with different invariants */
466
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000467#define rs_byte(p) (((p)->ptr < (p)->end) ? (unsigned char)*(p)->ptr++ : EOF)
Guido van Rossum8d617a61995-03-09 12:12:11 +0000468
469#define r_byte(p) ((p)->fp ? getc((p)->fp) : rs_byte(p))
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000470
471static int
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000472r_string(char *s, int n, RFILE *p)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000473{
474 if (p->fp != NULL)
Martin v. Löwis18e16552006-02-15 17:27:45 +0000475 /* The result fits into int because it must be <=n. */
476 return (int)fread(s, 1, n, p->fp);
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000477 if (p->end - p->ptr < n)
Martin v. Löwis18e16552006-02-15 17:27:45 +0000478 n = (int)(p->end - p->ptr);
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000479 memcpy(s, p->ptr, n);
480 p->ptr += n;
481 return n;
482}
483
484static int
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000485r_short(RFILE *p)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000486{
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000487 register short x;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000488 x = r_byte(p);
489 x |= r_byte(p) << 8;
Tim Peterse84b7402000-09-19 08:54:13 +0000490 /* Sign-extension, in case short greater than 16 bits */
491 x |= -(x & 0x8000);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000492 return x;
493}
494
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000495static long
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000496r_long(RFILE *p)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000497{
498 register long x;
Guido van Rossum8d617a61995-03-09 12:12:11 +0000499 register FILE *fp = p->fp;
500 if (fp) {
501 x = getc(fp);
502 x |= (long)getc(fp) << 8;
503 x |= (long)getc(fp) << 16;
504 x |= (long)getc(fp) << 24;
505 }
506 else {
507 x = rs_byte(p);
508 x |= (long)rs_byte(p) << 8;
509 x |= (long)rs_byte(p) << 16;
510 x |= (long)rs_byte(p) << 24;
511 }
Guido van Rossumc1547d91996-12-10 15:39:04 +0000512#if SIZEOF_LONG > 4
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000513 /* Sign extension for 64-bit machines */
Tim Peterse84b7402000-09-19 08:54:13 +0000514 x |= -(x & 0x80000000L);
Guido van Rossumc1547d91996-12-10 15:39:04 +0000515#endif
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000516 return x;
517}
518
Tim Peters82112372001-08-29 02:28:42 +0000519/* r_long64 deals with the TYPE_INT64 code. On a machine with
520 sizeof(long) > 4, it returns a Python int object, else a Python long
521 object. Note that w_long64 writes out TYPE_INT if 32 bits is enough,
522 so there's no inefficiency here in returning a PyLong on 32-bit boxes
523 for everything written via TYPE_INT64 (i.e., if an int is written via
524 TYPE_INT64, it *needs* more than 32 bits).
525*/
526static PyObject *
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000527r_long64(RFILE *p)
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000528{
Tim Peters82112372001-08-29 02:28:42 +0000529 long lo4 = r_long(p);
530 long hi4 = r_long(p);
Guido van Rossumc1547d91996-12-10 15:39:04 +0000531#if SIZEOF_LONG > 4
Tim Peters82112372001-08-29 02:28:42 +0000532 long x = (hi4 << 32) | (lo4 & 0xFFFFFFFFL);
Christian Heimes217cfd12007-12-02 14:31:20 +0000533 return PyLong_FromLong(x);
Guido van Rossumc1547d91996-12-10 15:39:04 +0000534#else
Tim Peters82112372001-08-29 02:28:42 +0000535 unsigned char buf[8];
536 int one = 1;
537 int is_little_endian = (int)*(char*)&one;
538 if (is_little_endian) {
539 memcpy(buf, &lo4, 4);
540 memcpy(buf+4, &hi4, 4);
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000541 }
Tim Peters82112372001-08-29 02:28:42 +0000542 else {
543 memcpy(buf, &hi4, 4);
544 memcpy(buf+4, &lo4, 4);
545 }
546 return _PyLong_FromByteArray(buf, 8, is_little_endian, 1);
Guido van Rossumc1547d91996-12-10 15:39:04 +0000547#endif
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000548}
549
Guido van Rossum79f25d91997-04-29 20:08:16 +0000550static PyObject *
Mark Dickinsonbd792642009-03-18 20:06:12 +0000551r_PyLong(RFILE *p)
552{
553 PyLongObject *ob;
Mark Dickinson2683ab02009-09-29 19:21:35 +0000554 int size, i, j, md, shorts_in_top_digit;
Mark Dickinsonbd792642009-03-18 20:06:12 +0000555 long n;
556 digit d;
557
558 n = r_long(p);
559 if (n == 0)
560 return (PyObject *)_PyLong_New(0);
561 if (n < -INT_MAX || n > INT_MAX) {
562 PyErr_SetString(PyExc_ValueError,
563 "bad marshal data (long size out of range)");
564 return NULL;
565 }
566
Mark Dickinson2683ab02009-09-29 19:21:35 +0000567 size = 1 + (ABS(n) - 1) / PyLong_MARSHAL_RATIO;
568 shorts_in_top_digit = 1 + (ABS(n) - 1) % PyLong_MARSHAL_RATIO;
Mark Dickinsonbd792642009-03-18 20:06:12 +0000569 ob = _PyLong_New(size);
570 if (ob == NULL)
571 return NULL;
572 Py_SIZE(ob) = n > 0 ? size : -size;
573
574 for (i = 0; i < size-1; i++) {
575 d = 0;
576 for (j=0; j < PyLong_MARSHAL_RATIO; j++) {
577 md = r_short(p);
578 if (md < 0 || md > PyLong_MARSHAL_BASE)
579 goto bad_digit;
580 d += (digit)md << j*PyLong_MARSHAL_SHIFT;
581 }
582 ob->ob_digit[i] = d;
583 }
584 d = 0;
Mark Dickinson2683ab02009-09-29 19:21:35 +0000585 for (j=0; j < shorts_in_top_digit; j++) {
Mark Dickinsonbd792642009-03-18 20:06:12 +0000586 md = r_short(p);
587 if (md < 0 || md > PyLong_MARSHAL_BASE)
588 goto bad_digit;
Mark Dickinson2683ab02009-09-29 19:21:35 +0000589 /* topmost marshal digit should be nonzero */
590 if (md == 0 && j == shorts_in_top_digit - 1) {
591 Py_DECREF(ob);
592 PyErr_SetString(PyExc_ValueError,
593 "bad marshal data (unnormalized long data)");
594 return NULL;
595 }
Mark Dickinsonbd792642009-03-18 20:06:12 +0000596 d += (digit)md << j*PyLong_MARSHAL_SHIFT;
597 }
Mark Dickinson2683ab02009-09-29 19:21:35 +0000598 /* top digit should be nonzero, else the resulting PyLong won't be
599 normalized */
Mark Dickinsonbd792642009-03-18 20:06:12 +0000600 ob->ob_digit[size-1] = d;
601 return (PyObject *)ob;
602 bad_digit:
603 Py_DECREF(ob);
604 PyErr_SetString(PyExc_ValueError,
605 "bad marshal data (digit out of range in long)");
606 return NULL;
607}
608
609
610static PyObject *
Thomas Woutersf70ef4f2000-07-22 18:47:25 +0000611r_object(RFILE *p)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000612{
Armin Rigo01ab2792004-03-26 15:09:27 +0000613 /* NULL is a valid return value, it does not necessarily means that
614 an exception is set. */
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000615 PyObject *v, *v2;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000616 long i, n;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000617 int type = r_byte(p);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000618 PyObject *retval;
619
620 p->depth++;
621
622 if (p->depth > MAX_MARSHAL_STACK_DEPTH) {
623 p->depth--;
624 PyErr_SetString(PyExc_ValueError, "recursion limit exceeded");
625 return NULL;
626 }
Tim Petersd9b9ac82001-01-28 00:27:39 +0000627
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000628 switch (type) {
Tim Petersd9b9ac82001-01-28 00:27:39 +0000629
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000630 case EOF:
Guido van Rossum79f25d91997-04-29 20:08:16 +0000631 PyErr_SetString(PyExc_EOFError,
632 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000633 retval = NULL;
634 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000635
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000636 case TYPE_NULL:
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000637 retval = NULL;
638 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000639
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000640 case TYPE_NONE:
Guido van Rossum79f25d91997-04-29 20:08:16 +0000641 Py_INCREF(Py_None);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000642 retval = Py_None;
643 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000644
Tim Peters5ca576e2001-06-18 22:08:13 +0000645 case TYPE_STOPITER:
646 Py_INCREF(PyExc_StopIteration);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000647 retval = PyExc_StopIteration;
648 break;
Tim Peters5ca576e2001-06-18 22:08:13 +0000649
Guido van Rossume449af71996-10-11 16:25:41 +0000650 case TYPE_ELLIPSIS:
Guido van Rossum79f25d91997-04-29 20:08:16 +0000651 Py_INCREF(Py_Ellipsis);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000652 retval = Py_Ellipsis;
653 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000654
Guido van Rossum77f6a652002-04-03 22:41:51 +0000655 case TYPE_FALSE:
656 Py_INCREF(Py_False);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000657 retval = Py_False;
658 break;
Guido van Rossum77f6a652002-04-03 22:41:51 +0000659
660 case TYPE_TRUE:
661 Py_INCREF(Py_True);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000662 retval = Py_True;
663 break;
Guido van Rossum77f6a652002-04-03 22:41:51 +0000664
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000665 case TYPE_INT:
Christian Heimes217cfd12007-12-02 14:31:20 +0000666 retval = PyLong_FromLong(r_long(p));
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000667 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000668
Guido van Rossumb0c168c1996-12-05 23:15:02 +0000669 case TYPE_INT64:
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000670 retval = r_long64(p);
671 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000672
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000673 case TYPE_LONG:
Mark Dickinsonbd792642009-03-18 20:06:12 +0000674 retval = r_PyLong(p);
675 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000676
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000677 case TYPE_FLOAT:
678 {
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000679 char buf[256];
Guido van Rossum0ae748d1997-02-14 22:58:07 +0000680 double dx;
Mark Dickinson725bfd82009-05-03 20:33:40 +0000681 retval = NULL;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000682 n = r_byte(p);
Armin Rigo01ab2792004-03-26 15:09:27 +0000683 if (n == EOF || r_string(buf, (int)n, p) != n) {
Guido van Rossum79f25d91997-04-29 20:08:16 +0000684 PyErr_SetString(PyExc_EOFError,
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000685 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000686 break;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000687 }
688 buf[n] = '\0';
Mark Dickinson725bfd82009-05-03 20:33:40 +0000689 dx = PyOS_string_to_double(buf, NULL, NULL);
690 if (dx == -1.0 && PyErr_Occurred())
691 break;
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000692 retval = PyFloat_FromDouble(dx);
693 break;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000694 }
Tim Petersd9b9ac82001-01-28 00:27:39 +0000695
Michael W. Hudsondf888462005-06-03 14:41:55 +0000696 case TYPE_BINARY_FLOAT:
697 {
Brett Cannonc9371d42005-06-25 08:23:41 +0000698 unsigned char buf[8];
Michael W. Hudsondf888462005-06-03 14:41:55 +0000699 double x;
Brett Cannonc9371d42005-06-25 08:23:41 +0000700 if (r_string((char*)buf, 8, p) != 8) {
Michael W. Hudsondf888462005-06-03 14:41:55 +0000701 PyErr_SetString(PyExc_EOFError,
702 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000703 retval = NULL;
704 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000705 }
706 x = _PyFloat_Unpack8(buf, 1);
707 if (x == -1.0 && PyErr_Occurred()) {
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000708 retval = NULL;
709 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000710 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000711 retval = PyFloat_FromDouble(x);
712 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000713 }
714
Guido van Rossum8a5c5d21996-01-12 01:09:56 +0000715 case TYPE_COMPLEX:
716 {
Guido van Rossum8a5c5d21996-01-12 01:09:56 +0000717 char buf[256];
Guido van Rossum530956d1996-07-21 02:27:43 +0000718 Py_complex c;
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000719 retval = NULL;
Guido van Rossum8a5c5d21996-01-12 01:09:56 +0000720 n = r_byte(p);
Armin Rigo01ab2792004-03-26 15:09:27 +0000721 if (n == EOF || r_string(buf, (int)n, p) != n) {
Guido van Rossum79f25d91997-04-29 20:08:16 +0000722 PyErr_SetString(PyExc_EOFError,
Guido van Rossum8a5c5d21996-01-12 01:09:56 +0000723 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000724 break;
Guido van Rossum8a5c5d21996-01-12 01:09:56 +0000725 }
726 buf[n] = '\0';
Mark Dickinson725bfd82009-05-03 20:33:40 +0000727 c.real = PyOS_string_to_double(buf, NULL, NULL);
728 if (c.real == -1.0 && PyErr_Occurred())
729 break;
730 n = r_byte(p);
731 if (n == EOF || r_string(buf, (int)n, p) != n) {
732 PyErr_SetString(PyExc_EOFError,
733 "EOF read where object expected");
734 break;
735 }
736 buf[n] = '\0';
737 c.imag = PyOS_string_to_double(buf, NULL, NULL);
738 if (c.imag == -1.0 && PyErr_Occurred())
739 break;
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000740 retval = PyComplex_FromCComplex(c);
741 break;
Guido van Rossum8a5c5d21996-01-12 01:09:56 +0000742 }
Michael W. Hudsondf888462005-06-03 14:41:55 +0000743
744 case TYPE_BINARY_COMPLEX:
745 {
Brett Cannonc9371d42005-06-25 08:23:41 +0000746 unsigned char buf[8];
Michael W. Hudsondf888462005-06-03 14:41:55 +0000747 Py_complex c;
Brett Cannonc9371d42005-06-25 08:23:41 +0000748 if (r_string((char*)buf, 8, p) != 8) {
Michael W. Hudsondf888462005-06-03 14:41:55 +0000749 PyErr_SetString(PyExc_EOFError,
750 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000751 retval = NULL;
752 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000753 }
754 c.real = _PyFloat_Unpack8(buf, 1);
755 if (c.real == -1.0 && PyErr_Occurred()) {
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000756 retval = NULL;
757 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000758 }
Brett Cannonc9371d42005-06-25 08:23:41 +0000759 if (r_string((char*)buf, 8, p) != 8) {
Michael W. Hudsondf888462005-06-03 14:41:55 +0000760 PyErr_SetString(PyExc_EOFError,
761 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000762 retval = NULL;
763 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000764 }
765 c.imag = _PyFloat_Unpack8(buf, 1);
766 if (c.imag == -1.0 && PyErr_Occurred()) {
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000767 retval = NULL;
768 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000769 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000770 retval = PyComplex_FromCComplex(c);
771 break;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000772 }
Tim Petersd9b9ac82001-01-28 00:27:39 +0000773
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000774 case TYPE_STRING:
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000775 n = r_long(p);
Thomas Wouters89f507f2006-12-13 04:49:30 +0000776 if (n < 0 || n > INT_MAX) {
Nick Coghlan93095832009-03-15 05:07:56 +0000777 PyErr_SetString(PyExc_ValueError, "bad marshal data (string size out of range)");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000778 retval = NULL;
779 break;
Guido van Rossuma45cb451998-06-08 20:27:29 +0000780 }
Christian Heimes72b710a2008-05-26 13:28:38 +0000781 v = PyBytes_FromStringAndSize((char *)NULL, n);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000782 if (v == NULL) {
783 retval = NULL;
784 break;
785 }
Christian Heimes72b710a2008-05-26 13:28:38 +0000786 if (r_string(PyBytes_AS_STRING(v), (int)n, p) != n) {
Michael W. Hudson6d6917b2005-06-03 15:17:16 +0000787 Py_DECREF(v);
788 PyErr_SetString(PyExc_EOFError,
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000789 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000790 retval = NULL;
791 break;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000792 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000793 retval = v;
794 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000795
Guido van Rossumc279b532000-03-10 23:03:02 +0000796 case TYPE_UNICODE:
797 {
798 char *buffer;
799
800 n = r_long(p);
Thomas Wouters89f507f2006-12-13 04:49:30 +0000801 if (n < 0 || n > INT_MAX) {
Nick Coghlan93095832009-03-15 05:07:56 +0000802 PyErr_SetString(PyExc_ValueError, "bad marshal data (unicode size out of range)");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000803 retval = NULL;
804 break;
Guido van Rossumc279b532000-03-10 23:03:02 +0000805 }
Guido van Rossumb18618d2000-05-03 23:44:39 +0000806 buffer = PyMem_NEW(char, n);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000807 if (buffer == NULL) {
808 retval = PyErr_NoMemory();
809 break;
810 }
Guido van Rossumc279b532000-03-10 23:03:02 +0000811 if (r_string(buffer, (int)n, p) != n) {
Guido van Rossumb18618d2000-05-03 23:44:39 +0000812 PyMem_DEL(buffer);
Guido van Rossumc279b532000-03-10 23:03:02 +0000813 PyErr_SetString(PyExc_EOFError,
814 "EOF read where object expected");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000815 retval = NULL;
816 break;
Guido van Rossumc279b532000-03-10 23:03:02 +0000817 }
Martin v. Löwise0a2b722009-05-10 08:08:56 +0000818 v = PyUnicode_DecodeUTF8(buffer, n, "surrogatepass");
Guido van Rossumb18618d2000-05-03 23:44:39 +0000819 PyMem_DEL(buffer);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000820 retval = v;
821 break;
Guido van Rossumc279b532000-03-10 23:03:02 +0000822 }
Tim Petersd9b9ac82001-01-28 00:27:39 +0000823
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000824 case TYPE_TUPLE:
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000825 n = r_long(p);
Thomas Wouters89f507f2006-12-13 04:49:30 +0000826 if (n < 0 || n > INT_MAX) {
Nick Coghlan93095832009-03-15 05:07:56 +0000827 PyErr_SetString(PyExc_ValueError, "bad marshal data (tuple size out of range)");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000828 retval = NULL;
829 break;
Guido van Rossuma45cb451998-06-08 20:27:29 +0000830 }
Guido van Rossum79f25d91997-04-29 20:08:16 +0000831 v = PyTuple_New((int)n);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000832 if (v == NULL) {
833 retval = NULL;
834 break;
835 }
Jack Jansen9513f2c1995-10-27 13:21:28 +0000836 for (i = 0; i < n; i++) {
837 v2 = r_object(p);
838 if ( v2 == NULL ) {
Armin Rigo01ab2792004-03-26 15:09:27 +0000839 if (!PyErr_Occurred())
840 PyErr_SetString(PyExc_TypeError,
Nick Coghlan93095832009-03-15 05:07:56 +0000841 "NULL object in marshal data for tuple");
Guido van Rossum79f25d91997-04-29 20:08:16 +0000842 Py_DECREF(v);
Jack Jansen9513f2c1995-10-27 13:21:28 +0000843 v = NULL;
844 break;
845 }
Guido van Rossum79f25d91997-04-29 20:08:16 +0000846 PyTuple_SET_ITEM(v, (int)i, v2);
Jack Jansen9513f2c1995-10-27 13:21:28 +0000847 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000848 retval = v;
849 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000850
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000851 case TYPE_LIST:
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000852 n = r_long(p);
Thomas Wouters89f507f2006-12-13 04:49:30 +0000853 if (n < 0 || n > INT_MAX) {
Nick Coghlan93095832009-03-15 05:07:56 +0000854 PyErr_SetString(PyExc_ValueError, "bad marshal data (list size out of range)");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000855 retval = NULL;
856 break;
Guido van Rossuma45cb451998-06-08 20:27:29 +0000857 }
Guido van Rossum79f25d91997-04-29 20:08:16 +0000858 v = PyList_New((int)n);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000859 if (v == NULL) {
860 retval = NULL;
861 break;
862 }
Jack Jansen9513f2c1995-10-27 13:21:28 +0000863 for (i = 0; i < n; i++) {
864 v2 = r_object(p);
865 if ( v2 == NULL ) {
Armin Rigo01ab2792004-03-26 15:09:27 +0000866 if (!PyErr_Occurred())
867 PyErr_SetString(PyExc_TypeError,
Nick Coghlan93095832009-03-15 05:07:56 +0000868 "NULL object in marshal data for list");
Guido van Rossum79f25d91997-04-29 20:08:16 +0000869 Py_DECREF(v);
Jack Jansen9513f2c1995-10-27 13:21:28 +0000870 v = NULL;
871 break;
872 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000873 PyList_SET_ITEM(v, (int)i, v2);
Jack Jansen9513f2c1995-10-27 13:21:28 +0000874 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000875 retval = v;
876 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000877
Guido van Rossum64b45521991-06-07 13:58:22 +0000878 case TYPE_DICT:
Guido van Rossum79f25d91997-04-29 20:08:16 +0000879 v = PyDict_New();
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000880 if (v == NULL) {
881 retval = NULL;
882 break;
883 }
Guido van Rossum64b45521991-06-07 13:58:22 +0000884 for (;;) {
Guido van Rossum79f25d91997-04-29 20:08:16 +0000885 PyObject *key, *val;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000886 key = r_object(p);
Guido van Rossum64b45521991-06-07 13:58:22 +0000887 if (key == NULL)
Armin Rigo01ab2792004-03-26 15:09:27 +0000888 break;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000889 val = r_object(p);
Guido van Rossumf2150601996-06-26 20:41:23 +0000890 if (val != NULL)
Guido van Rossum79f25d91997-04-29 20:08:16 +0000891 PyDict_SetItem(v, key, val);
892 Py_DECREF(key);
893 Py_XDECREF(val);
Guido van Rossum64b45521991-06-07 13:58:22 +0000894 }
Armin Rigo01ab2792004-03-26 15:09:27 +0000895 if (PyErr_Occurred()) {
896 Py_DECREF(v);
897 v = NULL;
898 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000899 retval = v;
900 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000901
Raymond Hettingera422c342005-01-11 03:03:27 +0000902 case TYPE_SET:
903 case TYPE_FROZENSET:
904 n = r_long(p);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000905 if (n < 0 || n > INT_MAX) {
Nick Coghlan93095832009-03-15 05:07:56 +0000906 PyErr_SetString(PyExc_ValueError, "bad marshal data (set size out of range)");
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000907 retval = NULL;
908 break;
Raymond Hettingera422c342005-01-11 03:03:27 +0000909 }
Christian Heimesfd66e512008-01-29 12:18:50 +0000910 v = (type == TYPE_SET) ? PySet_New(NULL) : PyFrozenSet_New(NULL);
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000911 if (v == NULL) {
912 retval = NULL;
913 break;
914 }
Raymond Hettingera422c342005-01-11 03:03:27 +0000915 for (i = 0; i < n; i++) {
916 v2 = r_object(p);
917 if ( v2 == NULL ) {
918 if (!PyErr_Occurred())
919 PyErr_SetString(PyExc_TypeError,
Nick Coghlan93095832009-03-15 05:07:56 +0000920 "NULL object in marshal data for set");
Raymond Hettingera422c342005-01-11 03:03:27 +0000921 Py_DECREF(v);
922 v = NULL;
923 break;
924 }
Christian Heimesfd66e512008-01-29 12:18:50 +0000925 if (PySet_Add(v, v2) == -1) {
926 Py_DECREF(v);
927 Py_DECREF(v2);
928 v = NULL;
929 break;
930 }
Christian Heimes400adb02008-02-01 08:12:03 +0000931 Py_DECREF(v2);
Raymond Hettingera422c342005-01-11 03:03:27 +0000932 }
Christian Heimesfd66e512008-01-29 12:18:50 +0000933 retval = v;
Guido van Rossumd59da4b2007-05-22 18:11:13 +0000934 break;
Raymond Hettingera422c342005-01-11 03:03:27 +0000935
Guido van Rossumdce2e3d1991-06-04 19:42:30 +0000936 case TYPE_CODE:
Guido van Rossuma8add0e2007-05-14 22:03:55 +0000937 {
Michael W. Hudsondf888462005-06-03 14:41:55 +0000938 int argcount;
Guido van Rossum4f72a782006-10-27 23:31:49 +0000939 int kwonlyargcount;
Michael W. Hudsondf888462005-06-03 14:41:55 +0000940 int nlocals;
941 int stacksize;
942 int flags;
943 PyObject *code = NULL;
944 PyObject *consts = NULL;
945 PyObject *names = NULL;
946 PyObject *varnames = NULL;
947 PyObject *freevars = NULL;
948 PyObject *cellvars = NULL;
949 PyObject *filename = NULL;
950 PyObject *name = NULL;
951 int firstlineno;
952 PyObject *lnotab = NULL;
953
954 v = NULL;
Tim Petersd9b9ac82001-01-28 00:27:39 +0000955
Guido van Rossuma8add0e2007-05-14 22:03:55 +0000956 /* XXX ignore long->int overflows for now */
Thomas Wouters89f507f2006-12-13 04:49:30 +0000957 argcount = (int)r_long(p);
958 kwonlyargcount = (int)r_long(p);
959 nlocals = (int)r_long(p);
960 stacksize = (int)r_long(p);
961 flags = (int)r_long(p);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000962 code = r_object(p);
963 if (code == NULL)
964 goto code_error;
965 consts = r_object(p);
966 if (consts == NULL)
967 goto code_error;
968 names = r_object(p);
969 if (names == NULL)
970 goto code_error;
971 varnames = r_object(p);
972 if (varnames == NULL)
973 goto code_error;
974 freevars = r_object(p);
975 if (freevars == NULL)
976 goto code_error;
977 cellvars = r_object(p);
978 if (cellvars == NULL)
979 goto code_error;
980 filename = r_object(p);
981 if (filename == NULL)
982 goto code_error;
983 name = r_object(p);
984 if (name == NULL)
985 goto code_error;
Thomas Wouters89f507f2006-12-13 04:49:30 +0000986 firstlineno = (int)r_long(p);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000987 lnotab = r_object(p);
988 if (lnotab == NULL)
989 goto code_error;
990
991 v = (PyObject *) PyCode_New(
Guido van Rossum4f72a782006-10-27 23:31:49 +0000992 argcount, kwonlyargcount,
993 nlocals, stacksize, flags,
Guido van Rossum681d79a1995-07-18 14:51:37 +0000994 code, consts, names, varnames,
Tim Petersd9b9ac82001-01-28 00:27:39 +0000995 freevars, cellvars, filename, name,
996 firstlineno, lnotab);
Michael W. Hudsondf888462005-06-03 14:41:55 +0000997
998 code_error:
Guido van Rossum79f25d91997-04-29 20:08:16 +0000999 Py_XDECREF(code);
1000 Py_XDECREF(consts);
1001 Py_XDECREF(names);
1002 Py_XDECREF(varnames);
Jeremy Hylton64949cb2001-01-25 20:06:59 +00001003 Py_XDECREF(freevars);
1004 Py_XDECREF(cellvars);
Guido van Rossum79f25d91997-04-29 20:08:16 +00001005 Py_XDECREF(filename);
1006 Py_XDECREF(name);
Guido van Rossum6fc06e71997-07-26 23:30:18 +00001007 Py_XDECREF(lnotab);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001008 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +00001009 retval = v;
1010 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +00001011
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001012 default:
Guido van Rossumf2150601996-06-26 20:41:23 +00001013 /* Bogus data got written, which isn't ideal.
1014 This will let you keep working and recover. */
Nick Coghlan93095832009-03-15 05:07:56 +00001015 PyErr_SetString(PyExc_ValueError, "bad marshal data (unknown type code)");
Guido van Rossumd59da4b2007-05-22 18:11:13 +00001016 retval = NULL;
1017 break;
Tim Petersd9b9ac82001-01-28 00:27:39 +00001018
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001019 }
Guido van Rossumd59da4b2007-05-22 18:11:13 +00001020 p->depth--;
1021 return retval;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001022}
1023
Neal Norwitzd85c4522004-06-13 20:31:49 +00001024static PyObject *
Armin Rigo01ab2792004-03-26 15:09:27 +00001025read_object(RFILE *p)
1026{
1027 PyObject *v;
1028 if (PyErr_Occurred()) {
1029 fprintf(stderr, "XXX readobject called with exception set\n");
1030 return NULL;
1031 }
1032 v = r_object(p);
1033 if (v == NULL && !PyErr_Occurred())
Nick Coghlan93095832009-03-15 05:07:56 +00001034 PyErr_SetString(PyExc_TypeError, "NULL object in marshal data for object");
Armin Rigo01ab2792004-03-26 15:09:27 +00001035 return v;
1036}
1037
Guido van Rossumb8cf3e62001-10-19 01:46:21 +00001038int
1039PyMarshal_ReadShortFromFile(FILE *fp)
1040{
1041 RFILE rf;
Thomas Wouters7f401ef2006-03-01 22:30:47 +00001042 assert(fp);
Guido van Rossumb8cf3e62001-10-19 01:46:21 +00001043 rf.fp = fp;
Thomas Wouters7464b432006-03-01 22:34:09 +00001044 rf.strings = NULL;
1045 rf.end = rf.ptr = NULL;
Guido van Rossumb8cf3e62001-10-19 01:46:21 +00001046 return r_short(&rf);
1047}
1048
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001049long
Thomas Woutersf70ef4f2000-07-22 18:47:25 +00001050PyMarshal_ReadLongFromFile(FILE *fp)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001051{
1052 RFILE rf;
1053 rf.fp = fp;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001054 rf.strings = NULL;
Guido van Rossum8ce8a782007-11-01 19:42:39 +00001055 rf.ptr = rf.end = NULL;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001056 return r_long(&rf);
1057}
1058
Tim Peters691e0e92001-01-18 04:39:16 +00001059#ifdef HAVE_FSTAT
1060/* Return size of file in bytes; < 0 if unknown. */
1061static off_t
1062getfilesize(FILE *fp)
1063{
1064 struct stat st;
1065 if (fstat(fileno(fp), &st) != 0)
1066 return -1;
1067 else
1068 return st.st_size;
1069}
1070#endif
Tim Petersd9b9ac82001-01-28 00:27:39 +00001071
Tim Peters691e0e92001-01-18 04:39:16 +00001072/* If we can get the size of the file up-front, and it's reasonably small,
1073 * read it in one gulp and delegate to ...FromString() instead. Much quicker
1074 * than reading a byte at a time from file; speeds .pyc imports.
Tim Petersd9b9ac82001-01-28 00:27:39 +00001075 * CAUTION: since this may read the entire remainder of the file, don't
1076 * call it unless you know you're done with the file.
Tim Peters691e0e92001-01-18 04:39:16 +00001077 */
Guido van Rossum79f25d91997-04-29 20:08:16 +00001078PyObject *
Tim Petersd9b9ac82001-01-28 00:27:39 +00001079PyMarshal_ReadLastObjectFromFile(FILE *fp)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001080{
Tim Peters691e0e92001-01-18 04:39:16 +00001081/* 75% of 2.1's .pyc files can exploit SMALL_FILE_LIMIT.
1082 * REASONABLE_FILE_LIMIT is by defn something big enough for Tkinter.pyc.
1083 */
1084#define SMALL_FILE_LIMIT (1L << 14)
1085#define REASONABLE_FILE_LIMIT (1L << 18)
Tim Peters691e0e92001-01-18 04:39:16 +00001086#ifdef HAVE_FSTAT
1087 off_t filesize;
1088#endif
Tim Peters691e0e92001-01-18 04:39:16 +00001089#ifdef HAVE_FSTAT
1090 filesize = getfilesize(fp);
1091 if (filesize > 0) {
1092 char buf[SMALL_FILE_LIMIT];
1093 char* pBuf = NULL;
1094 if (filesize <= SMALL_FILE_LIMIT)
1095 pBuf = buf;
1096 else if (filesize <= REASONABLE_FILE_LIMIT)
1097 pBuf = (char *)PyMem_MALLOC(filesize);
1098 if (pBuf != NULL) {
1099 PyObject* v;
Martin v. Löwis18e16552006-02-15 17:27:45 +00001100 size_t n;
1101 /* filesize must fit into an int, because it
1102 is smaller than REASONABLE_FILE_LIMIT */
1103 n = fread(pBuf, 1, (int)filesize, fp);
Tim Peters691e0e92001-01-18 04:39:16 +00001104 v = PyMarshal_ReadObjectFromString(pBuf, n);
1105 if (pBuf != buf)
1106 PyMem_FREE(pBuf);
1107 return v;
1108 }
Tim Petersd9b9ac82001-01-28 00:27:39 +00001109
Tim Peters691e0e92001-01-18 04:39:16 +00001110 }
1111#endif
Tim Petersd9b9ac82001-01-28 00:27:39 +00001112 /* We don't have fstat, or we do but the file is larger than
1113 * REASONABLE_FILE_LIMIT or malloc failed -- read a byte at a time.
1114 */
1115 return PyMarshal_ReadObjectFromFile(fp);
1116
Tim Peters691e0e92001-01-18 04:39:16 +00001117#undef SMALL_FILE_LIMIT
1118#undef REASONABLE_FILE_LIMIT
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001119}
1120
Guido van Rossum79f25d91997-04-29 20:08:16 +00001121PyObject *
Tim Petersd9b9ac82001-01-28 00:27:39 +00001122PyMarshal_ReadObjectFromFile(FILE *fp)
1123{
1124 RFILE rf;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001125 PyObject *result;
Tim Petersd9b9ac82001-01-28 00:27:39 +00001126 rf.fp = fp;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001127 rf.strings = PyList_New(0);
Guido van Rossumd59da4b2007-05-22 18:11:13 +00001128 rf.depth = 0;
Guido van Rossum8ce8a782007-11-01 19:42:39 +00001129 rf.ptr = rf.end = NULL;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001130 result = r_object(&rf);
1131 Py_DECREF(rf.strings);
1132 return result;
Tim Petersd9b9ac82001-01-28 00:27:39 +00001133}
1134
1135PyObject *
Martin v. Löwis18e16552006-02-15 17:27:45 +00001136PyMarshal_ReadObjectFromString(char *str, Py_ssize_t len)
Guido van Rossumf56e3db1993-04-01 20:59:32 +00001137{
1138 RFILE rf;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001139 PyObject *result;
Guido van Rossumf56e3db1993-04-01 20:59:32 +00001140 rf.fp = NULL;
Guido van Rossumf56e3db1993-04-01 20:59:32 +00001141 rf.ptr = str;
1142 rf.end = str + len;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001143 rf.strings = PyList_New(0);
Guido van Rossumd59da4b2007-05-22 18:11:13 +00001144 rf.depth = 0;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001145 result = r_object(&rf);
1146 Py_DECREF(rf.strings);
1147 return result;
Guido van Rossumf56e3db1993-04-01 20:59:32 +00001148}
1149
Guido van Rossum79f25d91997-04-29 20:08:16 +00001150PyObject *
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001151PyMarshal_WriteObjectToString(PyObject *x, int version)
Guido van Rossum3f3bb3d1996-08-19 22:07:17 +00001152{
1153 WFILE wf;
Guido van Rossume6d39042007-05-09 00:01:30 +00001154 PyObject *res = NULL;
1155
Guido van Rossum3f3bb3d1996-08-19 22:07:17 +00001156 wf.fp = NULL;
Christian Heimes72b710a2008-05-26 13:28:38 +00001157 wf.str = PyBytes_FromStringAndSize((char *)NULL, 50);
Guido van Rossum3f3bb3d1996-08-19 22:07:17 +00001158 if (wf.str == NULL)
1159 return NULL;
Christian Heimes72b710a2008-05-26 13:28:38 +00001160 wf.ptr = PyBytes_AS_STRING((PyBytesObject *)wf.str);
1161 wf.end = wf.ptr + PyBytes_Size(wf.str);
Eric Smithb1a03cf2009-04-21 11:57:38 +00001162 wf.error = WFERR_OK;
Fred Drake6da0b912000-06-28 18:47:56 +00001163 wf.depth = 0;
Michael W. Hudsondf888462005-06-03 14:41:55 +00001164 wf.version = version;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001165 wf.strings = (version > 0) ? PyDict_New() : NULL;
Guido van Rossum3f3bb3d1996-08-19 22:07:17 +00001166 w_object(x, &wf);
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001167 Py_XDECREF(wf.strings);
Thomas Wouters89f507f2006-12-13 04:49:30 +00001168 if (wf.str != NULL) {
Christian Heimes72b710a2008-05-26 13:28:38 +00001169 char *base = PyBytes_AS_STRING((PyBytesObject *)wf.str);
Thomas Wouters89f507f2006-12-13 04:49:30 +00001170 if (wf.ptr - base > PY_SSIZE_T_MAX) {
1171 Py_DECREF(wf.str);
1172 PyErr_SetString(PyExc_OverflowError,
Guido van Rossumf15a29f2007-05-04 00:41:39 +00001173 "too much marshal data for a string");
Thomas Wouters89f507f2006-12-13 04:49:30 +00001174 return NULL;
1175 }
Christian Heimes72b710a2008-05-26 13:28:38 +00001176 if (_PyBytes_Resize(&wf.str, (Py_ssize_t)(wf.ptr - base)) < 0)
Guido van Rossume6d39042007-05-09 00:01:30 +00001177 return NULL;
Thomas Wouters89f507f2006-12-13 04:49:30 +00001178 }
Eric Smithb1a03cf2009-04-21 11:57:38 +00001179 if (wf.error != WFERR_OK) {
Guido van Rossum79f25d91997-04-29 20:08:16 +00001180 Py_XDECREF(wf.str);
Eric Smithb1a03cf2009-04-21 11:57:38 +00001181 if (wf.error == WFERR_NOMEMORY)
1182 PyErr_NoMemory();
1183 else
1184 PyErr_SetString(PyExc_ValueError,
1185 (wf.error==WFERR_UNMARSHALLABLE)?"unmarshallable object"
1186 :"object too deeply nested to marshal");
Guido van Rossum3f3bb3d1996-08-19 22:07:17 +00001187 return NULL;
1188 }
Guido van Rossume6d39042007-05-09 00:01:30 +00001189 if (wf.str != NULL) {
1190 /* XXX Quick hack -- need to do this differently */
Gregory P. Smith0a608fd2008-09-06 21:34:51 +00001191 res = PyBytes_FromObject(wf.str);
Guido van Rossume6d39042007-05-09 00:01:30 +00001192 Py_DECREF(wf.str);
1193 }
1194 return res;
Guido van Rossum3f3bb3d1996-08-19 22:07:17 +00001195}
1196
Guido van Rossum64b45521991-06-07 13:58:22 +00001197/* And an interface for Python programs... */
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001198
Guido van Rossum79f25d91997-04-29 20:08:16 +00001199static PyObject *
Thomas Woutersf70ef4f2000-07-22 18:47:25 +00001200marshal_dump(PyObject *self, PyObject *args)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001201{
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001202 /* XXX Quick hack -- need to do this differently */
Guido van Rossum79f25d91997-04-29 20:08:16 +00001203 PyObject *x;
1204 PyObject *f;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001205 int version = Py_MARSHAL_VERSION;
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001206 PyObject *s;
1207 PyObject *res;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001208 if (!PyArg_ParseTuple(args, "OO|i:dump", &x, &f, &version))
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001209 return NULL;
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001210 s = PyMarshal_WriteObjectToString(x, version);
1211 if (s == NULL)
Guido van Rossumf2150601996-06-26 20:41:23 +00001212 return NULL;
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001213 res = PyObject_CallMethod(f, "write", "O", s);
1214 Py_DECREF(s);
1215 return res;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001216}
1217
R. David Murraydd226ea2009-05-13 12:27:21 +00001218PyDoc_STRVAR(dump_doc,
1219"dump(value, file[, version])\n\
1220\n\
1221Write the value on the open file. The value must be a supported type.\n\
1222The file must be an open file object such as sys.stdout or returned by\n\
1223open() or os.popen(). It must be opened in binary mode ('wb' or 'w+b').\n\
1224\n\
1225If the value has (or contains an object that has) an unsupported type, a\n\
1226ValueError exception is raised but garbage data will also be written\n\
1227to the file. The object will not be properly read back by load()\n\
1228\n\
1229The version argument indicates the data format that dump should use.");
1230
Guido van Rossum79f25d91997-04-29 20:08:16 +00001231static PyObject *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001232marshal_load(PyObject *self, PyObject *f)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001233{
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001234 /* XXX Quick hack -- need to do this differently */
1235 PyObject *data, *result;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001236 RFILE rf;
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001237 data = PyObject_CallMethod(f, "read", "");
1238 if (data == NULL)
1239 return NULL;
1240 rf.fp = NULL;
Christian Heimes72b710a2008-05-26 13:28:38 +00001241 if (PyBytes_Check(data)) {
1242 rf.ptr = PyBytes_AS_STRING(data);
1243 rf.end = rf.ptr + PyBytes_GET_SIZE(data);
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001244 }
Gregory P. Smith0a608fd2008-09-06 21:34:51 +00001245 else if (PyBytes_Check(data)) {
1246 rf.ptr = PyBytes_AS_STRING(data);
1247 rf.end = rf.ptr + PyBytes_GET_SIZE(data);
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001248 }
1249 else {
1250 PyErr_Format(PyExc_TypeError,
1251 "f.read() returned neither string "
1252 "nor bytes but %.100s",
1253 data->ob_type->tp_name);
1254 Py_DECREF(data);
1255 return NULL;
1256 }
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001257 rf.strings = PyList_New(0);
Guido van Rossum7a265342007-07-30 00:04:35 +00001258 rf.depth = 0;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001259 result = read_object(&rf);
1260 Py_DECREF(rf.strings);
Guido van Rossumda5b8f22007-06-12 23:30:11 +00001261 Py_DECREF(data);
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001262 return result;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001263}
1264
R. David Murraydd226ea2009-05-13 12:27:21 +00001265PyDoc_STRVAR(load_doc,
1266"load(file)\n\
1267\n\
1268Read one value from the open file and return it. If no valid value is\n\
1269read (e.g. because the data has a different Python versions\n\
1270incompatible marshal format), raise EOFError, ValueError or TypeError.\n\
1271The file must be an open file object opened in binary mode ('rb' or\n\
1272'r+b').\n\
1273\n\
1274Note: If an object containing an unsupported type was marshalled with\n\
1275dump(), load() will substitute None for the unmarshallable type.");
1276
1277
Guido van Rossum79f25d91997-04-29 20:08:16 +00001278static PyObject *
Thomas Woutersf70ef4f2000-07-22 18:47:25 +00001279marshal_dumps(PyObject *self, PyObject *args)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001280{
Guido van Rossum79f25d91997-04-29 20:08:16 +00001281 PyObject *x;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001282 int version = Py_MARSHAL_VERSION;
Armin Rigo2ccea172004-12-20 12:25:57 +00001283 if (!PyArg_ParseTuple(args, "O|i:dumps", &x, &version))
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001284 return NULL;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001285 return PyMarshal_WriteObjectToString(x, version);
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001286}
1287
R. David Murraydd226ea2009-05-13 12:27:21 +00001288PyDoc_STRVAR(dumps_doc,
1289"dumps(value[, version])\n\
1290\n\
1291Return the string that would be written to a file by dump(value, file).\n\
1292The value must be a supported type. Raise a ValueError exception if\n\
1293value has (or contains an object that has) an unsupported type.\n\
1294\n\
1295The version argument indicates the data format that dumps should use.");
1296
1297
Guido van Rossum79f25d91997-04-29 20:08:16 +00001298static PyObject *
Thomas Woutersf70ef4f2000-07-22 18:47:25 +00001299marshal_loads(PyObject *self, PyObject *args)
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001300{
1301 RFILE rf;
Martin v. Löwis423be952008-08-13 15:53:07 +00001302 Py_buffer p;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001303 char *s;
Thomas Wouters695934a2006-03-01 23:49:13 +00001304 Py_ssize_t n;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001305 PyObject* result;
Martin v. Löwis423be952008-08-13 15:53:07 +00001306 if (!PyArg_ParseTuple(args, "s*:loads", &p))
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001307 return NULL;
Martin v. Löwis423be952008-08-13 15:53:07 +00001308 s = p.buf;
1309 n = p.len;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001310 rf.fp = NULL;
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001311 rf.ptr = s;
1312 rf.end = s + n;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001313 rf.strings = PyList_New(0);
Guido van Rossumd59da4b2007-05-22 18:11:13 +00001314 rf.depth = 0;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001315 result = read_object(&rf);
1316 Py_DECREF(rf.strings);
Martin v. Löwis423be952008-08-13 15:53:07 +00001317 PyBuffer_Release(&p);
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001318 return result;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001319}
1320
R. David Murraydd226ea2009-05-13 12:27:21 +00001321PyDoc_STRVAR(loads_doc,
1322"loads(string)\n\
1323\n\
1324Convert the string to a value. If no valid value is found, raise\n\
1325EOFError, ValueError or TypeError. Extra characters in the string are\n\
1326ignored.");
1327
Guido van Rossum79f25d91997-04-29 20:08:16 +00001328static PyMethodDef marshal_methods[] = {
R. David Murraydd226ea2009-05-13 12:27:21 +00001329 {"dump", marshal_dump, METH_VARARGS, dump_doc},
1330 {"load", marshal_load, METH_O, load_doc},
1331 {"dumps", marshal_dumps, METH_VARARGS, dumps_doc},
1332 {"loads", marshal_loads, METH_VARARGS, loads_doc},
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001333 {NULL, NULL} /* sentinel */
1334};
1335
R. David Murraydd226ea2009-05-13 12:27:21 +00001336
1337PyDoc_STRVAR(module_doc,
1338"This module contains functions that can read and write Python values in\n\
1339a binary format. The format is specific to Python, but independent of\n\
1340machine architecture issues.\n\
1341\n\
1342Not all Python object types are supported; in general, only objects\n\
1343whose value is independent from a particular invocation of Python can be\n\
1344written and read by this module. The following types are supported:\n\
1345None, integers, floating point numbers, strings, bytes, bytearrays,\n\
1346tuples, lists, sets, dictionaries, and code objects, where it\n\
1347should be understood that tuples, lists and dictionaries are only\n\
1348supported as long as the values contained therein are themselves\n\
1349supported; and recursive lists and dictionaries should not be written\n\
1350(they will cause infinite loops).\n\
1351\n\
1352Variables:\n\
1353\n\
1354version -- indicates the format that the module uses. Version 0 is the\n\
1355 historical format, version 1 shares interned strings and version 2\n\
1356 uses a binary format for floating point numbers.\n\
1357\n\
1358Functions:\n\
1359\n\
1360dump() -- write value to a file\n\
1361load() -- read value from a file\n\
1362dumps() -- write value to a string\n\
1363loads() -- read value from a string");
1364
1365
1366
Brett Cannon429ef652008-06-27 00:35:35 +00001367static struct PyModuleDef marshalmodule = {
Martin v. Löwis1a214512008-06-11 05:26:20 +00001368 PyModuleDef_HEAD_INIT,
1369 "marshal",
R. David Murraydd226ea2009-05-13 12:27:21 +00001370 module_doc,
Martin v. Löwis1a214512008-06-11 05:26:20 +00001371 0,
1372 marshal_methods,
1373 NULL,
1374 NULL,
1375 NULL,
1376 NULL
1377};
1378
Jason Tishler6bc06ec2003-09-04 11:59:50 +00001379PyMODINIT_FUNC
Thomas Woutersf70ef4f2000-07-22 18:47:25 +00001380PyMarshal_Init(void)
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001381{
Brett Cannon429ef652008-06-27 00:35:35 +00001382 PyObject *mod = PyModule_Create(&marshalmodule);
Neal Norwitz1ac754f2006-01-19 06:09:39 +00001383 if (mod == NULL)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001384 return NULL;
Martin v. Löwisef82d2f2004-06-27 16:51:46 +00001385 PyModule_AddIntConstant(mod, "version", Py_MARSHAL_VERSION);
Martin v. Löwis1a214512008-06-11 05:26:20 +00001386 return mod;
Guido van Rossumdce2e3d1991-06-04 19:42:30 +00001387}