Branch data Line data Source code
1 : : /*
2 : : An implementation of the I/O abstract base classes hierarchy
3 : : as defined by PEP 3116 - "New I/O"
4 : :
5 : : Classes defined here: IOBase, RawIOBase.
6 : :
7 : : Written by Amaury Forgeot d'Arc and Antoine Pitrou
8 : : */
9 : :
10 : :
11 : : #define PY_SSIZE_T_CLEAN
12 : : #include "Python.h"
13 : : #include "pycore_long.h" // _PyLong_GetOne()
14 : : #include "pycore_object.h"
15 : : #include <stddef.h> // offsetof()
16 : : #include "_iomodule.h"
17 : :
18 : : /*[clinic input]
19 : : module _io
20 : : class _io._IOBase "PyObject *" "&PyIOBase_Type"
21 : : class _io._RawIOBase "PyObject *" "&PyRawIOBase_Type"
22 : : [clinic start generated code]*/
23 : : /*[clinic end generated code: output=da39a3ee5e6b4b0d input=d29a4d076c2b211c]*/
24 : :
25 : : /*
26 : : * IOBase class, an abstract class
27 : : */
28 : :
29 : : typedef struct {
30 : : PyObject_HEAD
31 : :
32 : : PyObject *dict;
33 : : PyObject *weakreflist;
34 : : } iobase;
35 : :
36 : : PyDoc_STRVAR(iobase_doc,
37 : : "The abstract base class for all I/O classes.\n"
38 : : "\n"
39 : : "This class provides dummy implementations for many methods that\n"
40 : : "derived classes can override selectively; the default implementations\n"
41 : : "represent a file that cannot be read, written or seeked.\n"
42 : : "\n"
43 : : "Even though IOBase does not declare read, readinto, or write because\n"
44 : : "their signatures will vary, implementations and clients should\n"
45 : : "consider those methods part of the interface. Also, implementations\n"
46 : : "may raise UnsupportedOperation when operations they do not support are\n"
47 : : "called.\n"
48 : : "\n"
49 : : "The basic type used for binary data read from or written to a file is\n"
50 : : "bytes. Other bytes-like objects are accepted as method arguments too.\n"
51 : : "In some cases (such as readinto), a writable object is required. Text\n"
52 : : "I/O classes work with str data.\n"
53 : : "\n"
54 : : "Note that calling any method (except additional calls to close(),\n"
55 : : "which are ignored) on a closed stream should raise a ValueError.\n"
56 : : "\n"
57 : : "IOBase (and its subclasses) support the iterator protocol, meaning\n"
58 : : "that an IOBase object can be iterated over yielding the lines in a\n"
59 : : "stream.\n"
60 : : "\n"
61 : : "IOBase also supports the :keyword:`with` statement. In this example,\n"
62 : : "fp is closed after the suite of the with statement is complete:\n"
63 : : "\n"
64 : : "with open('spam.txt', 'r') as fp:\n"
65 : : " fp.write('Spam and eggs!')\n");
66 : :
67 : : /* Use this macro whenever you want to check the internal `closed` status
68 : : of the IOBase object rather than the virtual `closed` attribute as returned
69 : : by whatever subclass. */
70 : :
71 : :
72 : : /* Internal methods */
73 : : static PyObject *
74 : 1423 : iobase_unsupported(const char *message)
75 : : {
76 : 1423 : _PyIO_State *state = IO_STATE();
77 [ + - ]: 1423 : if (state != NULL)
78 : 1423 : PyErr_SetString(state->unsupported_operation, message);
79 : 1423 : return NULL;
80 : : }
81 : :
82 : : /* Positioning */
83 : :
84 : : PyDoc_STRVAR(iobase_seek_doc,
85 : : "Change stream position.\n"
86 : : "\n"
87 : : "Change the stream position to the given byte offset. The offset is\n"
88 : : "interpreted relative to the position indicated by whence. Values\n"
89 : : "for whence are:\n"
90 : : "\n"
91 : : "* 0 -- start of stream (the default); offset should be zero or positive\n"
92 : : "* 1 -- current stream position; offset may be negative\n"
93 : : "* 2 -- end of stream; offset is usually negative\n"
94 : : "\n"
95 : : "Return the new absolute position.");
96 : :
97 : : static PyObject *
98 : 1393 : iobase_seek(PyObject *self, PyObject *args)
99 : : {
100 : 1393 : return iobase_unsupported("seek");
101 : : }
102 : :
103 : : /*[clinic input]
104 : : _io._IOBase.tell
105 : :
106 : : Return current stream position.
107 : : [clinic start generated code]*/
108 : :
109 : : static PyObject *
110 : 7939 : _io__IOBase_tell_impl(PyObject *self)
111 : : /*[clinic end generated code: output=89a1c0807935abe2 input=04e615fec128801f]*/
112 : : {
113 : 7939 : return _PyObject_CallMethod(self, &_Py_ID(seek), "ii", 0, 1);
114 : : }
115 : :
116 : : PyDoc_STRVAR(iobase_truncate_doc,
117 : : "Truncate file to size bytes.\n"
118 : : "\n"
119 : : "File pointer is left unchanged. Size defaults to the current IO\n"
120 : : "position as reported by tell(). Returns the new size.");
121 : :
122 : : static PyObject *
123 : 2 : iobase_truncate(PyObject *self, PyObject *args)
124 : : {
125 : 2 : return iobase_unsupported("truncate");
126 : : }
127 : :
128 : : static int
129 : 1455758 : iobase_is_closed(PyObject *self)
130 : : {
131 : : PyObject *res;
132 : : int ret;
133 : : /* This gets the derived attribute, which is *not* __IOBase_closed
134 : : in most cases! */
135 : 1455758 : ret = _PyObject_LookupAttr(self, &_Py_ID(__IOBase_closed), &res);
136 : 1455758 : Py_XDECREF(res);
137 : 1455758 : return ret;
138 : : }
139 : :
140 : : /* Flush and close methods */
141 : :
142 : : /*[clinic input]
143 : : _io._IOBase.flush
144 : :
145 : : Flush write buffers, if applicable.
146 : :
147 : : This is not implemented for read-only and non-blocking streams.
148 : : [clinic start generated code]*/
149 : :
150 : : static PyObject *
151 : 626357 : _io__IOBase_flush_impl(PyObject *self)
152 : : /*[clinic end generated code: output=7cef4b4d54656a3b input=773be121abe270aa]*/
153 : : {
154 : : /* XXX Should this return the number of bytes written??? */
155 : 626357 : int closed = iobase_is_closed(self);
156 : :
157 [ + + ]: 626357 : if (!closed) {
158 : 626350 : Py_RETURN_NONE;
159 : : }
160 [ + - ]: 7 : if (closed > 0) {
161 : 7 : PyErr_SetString(PyExc_ValueError, "I/O operation on closed file.");
162 : : }
163 : 7 : return NULL;
164 : : }
165 : :
166 : : static PyObject *
167 : 489108 : iobase_closed_get(PyObject *self, void *context)
168 : : {
169 : 489108 : int closed = iobase_is_closed(self);
170 [ - + ]: 489108 : if (closed < 0) {
171 : 0 : return NULL;
172 : : }
173 : 489108 : return PyBool_FromLong(closed);
174 : : }
175 : :
176 : : static int
177 : 465365 : iobase_check_closed(PyObject *self)
178 : : {
179 : : PyObject *res;
180 : : int closed;
181 : : /* This gets the derived attribute, which is *not* __IOBase_closed
182 : : in most cases! */
183 : 465365 : closed = _PyObject_LookupAttr(self, &_Py_ID(closed), &res);
184 [ + - ]: 465365 : if (closed > 0) {
185 : 465365 : closed = PyObject_IsTrue(res);
186 : 465365 : Py_DECREF(res);
187 [ + + ]: 465365 : if (closed > 0) {
188 : 82 : PyErr_SetString(PyExc_ValueError, "I/O operation on closed file.");
189 : 82 : return -1;
190 : : }
191 : : }
192 : 465283 : return closed;
193 : : }
194 : :
195 : : PyObject *
196 : 25956 : _PyIOBase_check_closed(PyObject *self, PyObject *args)
197 : : {
198 [ + + ]: 25956 : if (iobase_check_closed(self)) {
199 : 7 : return NULL;
200 : : }
201 [ + + ]: 25949 : if (args == Py_True) {
202 : 17970 : return Py_None;
203 : : }
204 : 7979 : Py_RETURN_NONE;
205 : : }
206 : :
207 : : /* XXX: IOBase thinks it has to maintain its own internal state in
208 : : `__IOBase_closed` and call flush() by itself, but it is redundant with
209 : : whatever behaviour a non-trivial derived class will implement. */
210 : :
211 : : /*[clinic input]
212 : : _io._IOBase.close
213 : :
214 : : Flush and close the IO object.
215 : :
216 : : This method has no effect if the file is already closed.
217 : : [clinic start generated code]*/
218 : :
219 : : static PyObject *
220 : 340293 : _io__IOBase_close_impl(PyObject *self)
221 : : /*[clinic end generated code: output=63c6a6f57d783d6d input=f4494d5c31dbc6b7]*/
222 : : {
223 : : PyObject *res, *exc, *val, *tb;
224 : 340293 : int rc, closed = iobase_is_closed(self);
225 : :
226 [ - + ]: 340293 : if (closed < 0) {
227 : 0 : return NULL;
228 : : }
229 [ + + ]: 340293 : if (closed) {
230 : 87 : Py_RETURN_NONE;
231 : : }
232 : :
233 : 340206 : res = PyObject_CallMethodNoArgs(self, &_Py_ID(flush));
234 : :
235 : 340206 : PyErr_Fetch(&exc, &val, &tb);
236 : 340206 : rc = PyObject_SetAttr(self, &_Py_ID(__IOBase_closed), Py_True);
237 : 340206 : _PyErr_ChainExceptions(exc, val, tb);
238 [ - + ]: 340206 : if (rc < 0) {
239 [ # # ]: 0 : Py_CLEAR(res);
240 : : }
241 : :
242 [ + + ]: 340206 : if (res == NULL)
243 : 9 : return NULL;
244 : :
245 : 340197 : Py_DECREF(res);
246 : 340197 : Py_RETURN_NONE;
247 : : }
248 : :
249 : : /* Finalization and garbage collection support */
250 : :
251 : : static void
252 : 726226 : iobase_finalize(PyObject *self)
253 : : {
254 : : PyObject *res;
255 : : PyObject *error_type, *error_value, *error_traceback;
256 : : int closed;
257 : :
258 : : /* Save the current exception, if any. */
259 : 726226 : PyErr_Fetch(&error_type, &error_value, &error_traceback);
260 : :
261 : : /* If `closed` doesn't exist or can't be evaluated as bool, then the
262 : : object is probably in an unusable state, so ignore. */
263 [ + + ]: 726226 : if (_PyObject_LookupAttr(self, &_Py_ID(closed), &res) <= 0) {
264 : 608 : PyErr_Clear();
265 : 608 : closed = -1;
266 : : }
267 : : else {
268 : 725618 : closed = PyObject_IsTrue(res);
269 : 725618 : Py_DECREF(res);
270 [ - + ]: 725618 : if (closed == -1)
271 : 0 : PyErr_Clear();
272 : : }
273 [ + + ]: 726226 : if (closed == 0) {
274 : : /* Signal close() that it was called as part of the object
275 : : finalization process. */
276 [ - + ]: 33782 : if (PyObject_SetAttr(self, &_Py_ID(_finalizing), Py_True))
277 : 0 : PyErr_Clear();
278 : 33782 : res = PyObject_CallMethodNoArgs((PyObject *)self, &_Py_ID(close));
279 : : /* Silencing I/O errors is bad, but printing spurious tracebacks is
280 : : equally as bad, and potentially more frequent (because of
281 : : shutdown issues). */
282 [ + + ]: 33782 : if (res == NULL) {
283 : : #ifndef Py_DEBUG
284 [ - + ]: 8 : if (_Py_GetConfig()->dev_mode) {
285 : 0 : PyErr_WriteUnraisable(self);
286 : : }
287 : : else {
288 : 8 : PyErr_Clear();
289 : : }
290 : : #else
291 : : PyErr_WriteUnraisable(self);
292 : : #endif
293 : : }
294 : : else {
295 : 33774 : Py_DECREF(res);
296 : : }
297 : : }
298 : :
299 : : /* Restore the saved exception. */
300 : 726226 : PyErr_Restore(error_type, error_value, error_traceback);
301 : 726226 : }
302 : :
303 : : int
304 : 722754 : _PyIOBase_finalize(PyObject *self)
305 : : {
306 : : int is_zombie;
307 : :
308 : : /* If _PyIOBase_finalize() is called from a destructor, we need to
309 : : resurrect the object as calling close() can invoke arbitrary code. */
310 : 722754 : is_zombie = (Py_REFCNT(self) == 0);
311 [ + - ]: 722754 : if (is_zombie)
312 : 722754 : return PyObject_CallFinalizerFromDealloc(self);
313 : : else {
314 : 0 : PyObject_CallFinalizer(self);
315 : 0 : return 0;
316 : : }
317 : : }
318 : :
319 : : static int
320 : 9360 : iobase_traverse(iobase *self, visitproc visit, void *arg)
321 : : {
322 [ + + - + ]: 9360 : Py_VISIT(self->dict);
323 : 9360 : return 0;
324 : : }
325 : :
326 : : static int
327 : 133 : iobase_clear(iobase *self)
328 : : {
329 [ + - ]: 133 : Py_CLEAR(self->dict);
330 : 133 : return 0;
331 : : }
332 : :
333 : : /* Destructor */
334 : :
335 : : static void
336 : 47253 : iobase_dealloc(iobase *self)
337 : : {
338 : : /* NOTE: since IOBaseObject has its own dict, Python-defined attributes
339 : : are still available here for close() to use.
340 : : However, if the derived class declares a __slots__, those slots are
341 : : already gone.
342 : : */
343 [ - + ]: 47253 : if (_PyIOBase_finalize((PyObject *) self) < 0) {
344 : : /* When called from a heap type's dealloc, the type will be
345 : : decref'ed on return (see e.g. subtype_dealloc in typeobject.c). */
346 [ # # ]: 0 : if (_PyType_HasFeature(Py_TYPE(self), Py_TPFLAGS_HEAPTYPE)) {
347 : 0 : Py_INCREF(Py_TYPE(self));
348 : : }
349 : 0 : return;
350 : : }
351 : 47253 : _PyObject_GC_UNTRACK(self);
352 [ - + ]: 47253 : if (self->weakreflist != NULL)
353 : 0 : PyObject_ClearWeakRefs((PyObject *) self);
354 [ + + ]: 47253 : Py_CLEAR(self->dict);
355 : 47253 : Py_TYPE(self)->tp_free((PyObject *) self);
356 : : }
357 : :
358 : : /* Inquiry methods */
359 : :
360 : : /*[clinic input]
361 : : _io._IOBase.seekable
362 : :
363 : : Return whether object supports random access.
364 : :
365 : : If False, seek(), tell() and truncate() will raise OSError.
366 : : This method may need to do a test seek().
367 : : [clinic start generated code]*/
368 : :
369 : : static PyObject *
370 : 2261 : _io__IOBase_seekable_impl(PyObject *self)
371 : : /*[clinic end generated code: output=4c24c67f5f32a43d input=b976622f7fdf3063]*/
372 : : {
373 : 2261 : Py_RETURN_FALSE;
374 : : }
375 : :
376 : : PyObject *
377 : 115310 : _PyIOBase_check_seekable(PyObject *self, PyObject *args)
378 : : {
379 : 115310 : PyObject *res = PyObject_CallMethodNoArgs(self, &_Py_ID(seekable));
380 [ - + ]: 115310 : if (res == NULL)
381 : 0 : return NULL;
382 [ + + ]: 115310 : if (res != Py_True) {
383 [ + - ]: 5 : Py_CLEAR(res);
384 : 5 : iobase_unsupported("File or stream is not seekable.");
385 : 5 : return NULL;
386 : : }
387 [ + + ]: 115305 : if (args == Py_True) {
388 : 115304 : Py_DECREF(res);
389 : : }
390 : 115305 : return res;
391 : : }
392 : :
393 : : /*[clinic input]
394 : : _io._IOBase.readable
395 : :
396 : : Return whether object was opened for reading.
397 : :
398 : : If False, read() will raise OSError.
399 : : [clinic start generated code]*/
400 : :
401 : : static PyObject *
402 : 19880 : _io__IOBase_readable_impl(PyObject *self)
403 : : /*[clinic end generated code: output=e48089250686388b input=285b3b866a0ec35f]*/
404 : : {
405 : 19880 : Py_RETURN_FALSE;
406 : : }
407 : :
408 : : /* May be called with any object */
409 : : PyObject *
410 : 277680 : _PyIOBase_check_readable(PyObject *self, PyObject *args)
411 : : {
412 : 277680 : PyObject *res = PyObject_CallMethodNoArgs(self, &_Py_ID(readable));
413 [ - + ]: 277680 : if (res == NULL)
414 : 0 : return NULL;
415 [ + + ]: 277680 : if (res != Py_True) {
416 [ + - ]: 1 : Py_CLEAR(res);
417 : 1 : iobase_unsupported("File or stream is not readable.");
418 : 1 : return NULL;
419 : : }
420 [ + + ]: 277679 : if (args == Py_True) {
421 : 269905 : Py_DECREF(res);
422 : : }
423 : 277679 : return res;
424 : : }
425 : :
426 : : /*[clinic input]
427 : : _io._IOBase.writable
428 : :
429 : : Return whether object was opened for writing.
430 : :
431 : : If False, write() will raise OSError.
432 : : [clinic start generated code]*/
433 : :
434 : : static PyObject *
435 : 12296 : _io__IOBase_writable_impl(PyObject *self)
436 : : /*[clinic end generated code: output=406001d0985be14f input=9dcac18a013a05b5]*/
437 : : {
438 : 12296 : Py_RETURN_FALSE;
439 : : }
440 : :
441 : : /* May be called with any object */
442 : : PyObject *
443 : 63086 : _PyIOBase_check_writable(PyObject *self, PyObject *args)
444 : : {
445 : 63086 : PyObject *res = PyObject_CallMethodNoArgs(self, &_Py_ID(writable));
446 [ - + ]: 63086 : if (res == NULL)
447 : 0 : return NULL;
448 [ + + ]: 63086 : if (res != Py_True) {
449 [ + - ]: 1 : Py_CLEAR(res);
450 : 1 : iobase_unsupported("File or stream is not writable.");
451 : 1 : return NULL;
452 : : }
453 [ + + ]: 63085 : if (args == Py_True) {
454 : 62908 : Py_DECREF(res);
455 : : }
456 : 63085 : return res;
457 : : }
458 : :
459 : : /* Context manager */
460 : :
461 : : static PyObject *
462 : 277880 : iobase_enter(PyObject *self, PyObject *args)
463 : : {
464 [ + + ]: 277880 : if (iobase_check_closed(self))
465 : 6 : return NULL;
466 : :
467 : 277874 : Py_INCREF(self);
468 : 277874 : return self;
469 : : }
470 : :
471 : : static PyObject *
472 : 277801 : iobase_exit(PyObject *self, PyObject *args)
473 : : {
474 : 277801 : return PyObject_CallMethodNoArgs(self, &_Py_ID(close));
475 : : }
476 : :
477 : : /* Lower-level APIs */
478 : :
479 : : /* XXX Should these be present even if unimplemented? */
480 : :
481 : : /*[clinic input]
482 : : _io._IOBase.fileno
483 : :
484 : : Returns underlying file descriptor if one exists.
485 : :
486 : : OSError is raised if the IO object does not use a file descriptor.
487 : : [clinic start generated code]*/
488 : :
489 : : static PyObject *
490 : 21 : _io__IOBase_fileno_impl(PyObject *self)
491 : : /*[clinic end generated code: output=7cc0973f0f5f3b73 input=4e37028947dc1cc8]*/
492 : : {
493 : 21 : return iobase_unsupported("fileno");
494 : : }
495 : :
496 : : /*[clinic input]
497 : : _io._IOBase.isatty
498 : :
499 : : Return whether this is an 'interactive' stream.
500 : :
501 : : Return False if it can't be determined.
502 : : [clinic start generated code]*/
503 : :
504 : : static PyObject *
505 : 3 : _io__IOBase_isatty_impl(PyObject *self)
506 : : /*[clinic end generated code: output=60cab77cede41cdd input=9ef76530d368458b]*/
507 : : {
508 [ + + ]: 3 : if (iobase_check_closed(self))
509 : 1 : return NULL;
510 : 2 : Py_RETURN_FALSE;
511 : : }
512 : :
513 : : /* Readline(s) and writelines */
514 : :
515 : : /*[clinic input]
516 : : _io._IOBase.readline
517 : : size as limit: Py_ssize_t(accept={int, NoneType}) = -1
518 : : /
519 : :
520 : : Read and return a line from the stream.
521 : :
522 : : If size is specified, at most size bytes will be read.
523 : :
524 : : The line terminator is always b'\n' for binary files; for text
525 : : files, the newlines argument to open can be used to select the line
526 : : terminator(s) recognized.
527 : : [clinic start generated code]*/
528 : :
529 : : static PyObject *
530 : 2335 : _io__IOBase_readline_impl(PyObject *self, Py_ssize_t limit)
531 : : /*[clinic end generated code: output=4479f79b58187840 input=d0c596794e877bff]*/
532 : : {
533 : : /* For backwards compatibility, a (slowish) readline(). */
534 : :
535 : : PyObject *peek, *buffer, *result;
536 : 2335 : Py_ssize_t old_size = -1;
537 : :
538 [ - + ]: 2335 : if (_PyObject_LookupAttr(self, &_Py_ID(peek), &peek) < 0) {
539 : 0 : return NULL;
540 : : }
541 : :
542 : 2335 : buffer = PyByteArray_FromStringAndSize(NULL, 0);
543 [ - + ]: 2335 : if (buffer == NULL) {
544 : 0 : Py_XDECREF(peek);
545 : 0 : return NULL;
546 : : }
547 : :
548 [ + + + + ]: 4318 : while (limit < 0 || PyByteArray_GET_SIZE(buffer) < limit) {
549 : 4307 : Py_ssize_t nreadahead = 1;
550 : : PyObject *b;
551 : :
552 [ + + ]: 4307 : if (peek != NULL) {
553 : 2482 : PyObject *readahead = PyObject_CallOneArg(peek, _PyLong_GetOne());
554 [ - + ]: 2482 : if (readahead == NULL) {
555 : : /* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
556 : : when EINTR occurs so we needn't do it ourselves. */
557 [ # # ]: 0 : if (_PyIO_trap_eintr()) {
558 : 0 : continue;
559 : : }
560 : 0 : goto fail;
561 : : }
562 [ - + ]: 2482 : if (!PyBytes_Check(readahead)) {
563 : 0 : PyErr_Format(PyExc_OSError,
564 : : "peek() should have returned a bytes object, "
565 : 0 : "not '%.200s'", Py_TYPE(readahead)->tp_name);
566 : 0 : Py_DECREF(readahead);
567 : 0 : goto fail;
568 : : }
569 [ + + ]: 2482 : if (PyBytes_GET_SIZE(readahead) > 0) {
570 : 2464 : Py_ssize_t n = 0;
571 : 2464 : const char *buf = PyBytes_AS_STRING(readahead);
572 [ + + ]: 2464 : if (limit >= 0) {
573 : : do {
574 [ + + + + ]: 75284 : if (n >= PyBytes_GET_SIZE(readahead) || n >= limit)
575 : : break;
576 [ + + ]: 75255 : if (buf[n++] == '\n')
577 : 1915 : break;
578 : : } while (1);
579 : : }
580 : : else {
581 : : do {
582 [ + + ]: 12800 : if (n >= PyBytes_GET_SIZE(readahead))
583 : 235 : break;
584 [ + + ]: 12565 : if (buf[n++] == '\n')
585 : 285 : break;
586 : : } while (1);
587 : : }
588 : 2464 : nreadahead = n;
589 : : }
590 : 2482 : Py_DECREF(readahead);
591 : : }
592 : :
593 : 4307 : b = _PyObject_CallMethod(self, &_Py_ID(read), "n", nreadahead);
594 [ + + ]: 4307 : if (b == NULL) {
595 : : /* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
596 : : when EINTR occurs so we needn't do it ourselves. */
597 [ - + ]: 13 : if (_PyIO_trap_eintr()) {
598 : 0 : continue;
599 : : }
600 : 13 : goto fail;
601 : : }
602 [ - + ]: 4294 : if (!PyBytes_Check(b)) {
603 : 0 : PyErr_Format(PyExc_OSError,
604 : : "read() should have returned a bytes object, "
605 : 0 : "not '%.200s'", Py_TYPE(b)->tp_name);
606 : 0 : Py_DECREF(b);
607 : 0 : goto fail;
608 : : }
609 [ + + ]: 4294 : if (PyBytes_GET_SIZE(b) == 0) {
610 : 27 : Py_DECREF(b);
611 : 27 : break;
612 : : }
613 : :
614 : 4267 : old_size = PyByteArray_GET_SIZE(buffer);
615 [ - + ]: 4267 : if (PyByteArray_Resize(buffer, old_size + PyBytes_GET_SIZE(b)) < 0) {
616 : 0 : Py_DECREF(b);
617 : 0 : goto fail;
618 : : }
619 : 4267 : memcpy(PyByteArray_AS_STRING(buffer) + old_size,
620 : 4267 : PyBytes_AS_STRING(b), PyBytes_GET_SIZE(b));
621 : :
622 : 4267 : Py_DECREF(b);
623 : :
624 [ + + ]: 4267 : if (PyByteArray_AS_STRING(buffer)[PyByteArray_GET_SIZE(buffer) - 1] == '\n')
625 : 2284 : break;
626 : : }
627 : :
628 : 2322 : result = PyBytes_FromStringAndSize(PyByteArray_AS_STRING(buffer),
629 : : PyByteArray_GET_SIZE(buffer));
630 : 2322 : Py_XDECREF(peek);
631 : 2322 : Py_DECREF(buffer);
632 : 2322 : return result;
633 : 13 : fail:
634 : 13 : Py_XDECREF(peek);
635 : 13 : Py_DECREF(buffer);
636 : 13 : return NULL;
637 : : }
638 : :
639 : : static PyObject *
640 : 10420 : iobase_iter(PyObject *self)
641 : : {
642 [ + + ]: 10420 : if (iobase_check_closed(self))
643 : 49 : return NULL;
644 : :
645 : 10371 : Py_INCREF(self);
646 : 10371 : return self;
647 : : }
648 : :
649 : : static PyObject *
650 : 25103 : iobase_iternext(PyObject *self)
651 : : {
652 : 25103 : PyObject *line = PyObject_CallMethodNoArgs(self, &_Py_ID(readline));
653 : :
654 [ + + ]: 25103 : if (line == NULL)
655 : 7 : return NULL;
656 : :
657 [ + + ]: 25096 : if (PyObject_Size(line) <= 0) {
658 : : /* Error or empty */
659 : 44 : Py_DECREF(line);
660 : 44 : return NULL;
661 : : }
662 : :
663 : 25052 : return line;
664 : : }
665 : :
666 : : /*[clinic input]
667 : : _io._IOBase.readlines
668 : : hint: Py_ssize_t(accept={int, NoneType}) = -1
669 : : /
670 : :
671 : : Return a list of lines from the stream.
672 : :
673 : : hint can be specified to control the number of lines read: no more
674 : : lines will be read if the total size (in bytes/characters) of all
675 : : lines so far exceeds hint.
676 : : [clinic start generated code]*/
677 : :
678 : : static PyObject *
679 : 7367 : _io__IOBase_readlines_impl(PyObject *self, Py_ssize_t hint)
680 : : /*[clinic end generated code: output=2f50421677fa3dea input=9400c786ea9dc416]*/
681 : : {
682 : 7367 : Py_ssize_t length = 0;
683 : 7367 : PyObject *result, *it = NULL;
684 : :
685 : 7367 : result = PyList_New(0);
686 [ - + ]: 7367 : if (result == NULL)
687 : 0 : return NULL;
688 : :
689 [ + + ]: 7367 : if (hint <= 0) {
690 : : /* XXX special-casing this made sense in the Python version in order
691 : : to remove the bytecode interpretation overhead, but it could
692 : : probably be removed here. */
693 : 7297 : PyObject *ret = PyObject_CallMethodObjArgs(result, &_Py_ID(extend),
694 : : self, NULL);
695 [ + + ]: 7293 : if (ret == NULL) {
696 : 21 : goto error;
697 : : }
698 : 7272 : Py_DECREF(ret);
699 : 7272 : return result;
700 : : }
701 : :
702 : 70 : it = PyObject_GetIter(self);
703 [ + + ]: 70 : if (it == NULL) {
704 : 15 : goto error;
705 : : }
706 : :
707 : 227 : while (1) {
708 : : Py_ssize_t line_length;
709 : 282 : PyObject *line = PyIter_Next(it);
710 [ + + ]: 282 : if (line == NULL) {
711 [ - + ]: 10 : if (PyErr_Occurred()) {
712 : 0 : goto error;
713 : : }
714 : : else
715 : 10 : break; /* StopIteration raised */
716 : : }
717 : :
718 [ - + ]: 272 : if (PyList_Append(result, line) < 0) {
719 : 0 : Py_DECREF(line);
720 : 0 : goto error;
721 : : }
722 : 272 : line_length = PyObject_Size(line);
723 : 272 : Py_DECREF(line);
724 [ + + ]: 272 : if (line_length < 0) {
725 : 1 : goto error;
726 : : }
727 [ + + ]: 271 : if (line_length > hint - length)
728 : 44 : break;
729 : 227 : length += line_length;
730 : : }
731 : :
732 : 54 : Py_DECREF(it);
733 : 54 : return result;
734 : :
735 : 37 : error:
736 : 37 : Py_XDECREF(it);
737 : 37 : Py_DECREF(result);
738 : 37 : return NULL;
739 : : }
740 : :
741 : : /*[clinic input]
742 : : _io._IOBase.writelines
743 : : lines: object
744 : : /
745 : :
746 : : Write a list of lines to stream.
747 : :
748 : : Line separators are not added, so it is usual for each of the
749 : : lines provided to have a line separator at the end.
750 : : [clinic start generated code]*/
751 : :
752 : : static PyObject *
753 : 151106 : _io__IOBase_writelines(PyObject *self, PyObject *lines)
754 : : /*[clinic end generated code: output=976eb0a9b60a6628 input=cac3fc8864183359]*/
755 : : {
756 : : PyObject *iter, *res;
757 : :
758 [ + + ]: 151106 : if (iobase_check_closed(self))
759 : 19 : return NULL;
760 : :
761 : 151087 : iter = PyObject_GetIter(lines);
762 [ + + ]: 151087 : if (iter == NULL)
763 : 8 : return NULL;
764 : :
765 : 455460 : while (1) {
766 : 606539 : PyObject *line = PyIter_Next(iter);
767 [ + + ]: 606539 : if (line == NULL) {
768 [ + + ]: 151060 : if (PyErr_Occurred()) {
769 : 1 : Py_DECREF(iter);
770 : 1 : return NULL;
771 : : }
772 : : else
773 : 151059 : break; /* Stop Iteration */
774 : : }
775 : :
776 : 455479 : res = NULL;
777 : : do {
778 : 455479 : res = PyObject_CallMethodObjArgs(self, &_Py_ID(write), line, NULL);
779 [ + + - + ]: 455479 : } while (res == NULL && _PyIO_trap_eintr());
780 : 455479 : Py_DECREF(line);
781 [ + + ]: 455479 : if (res == NULL) {
782 : 19 : Py_DECREF(iter);
783 : 19 : return NULL;
784 : : }
785 : 455460 : Py_DECREF(res);
786 : : }
787 : 151059 : Py_DECREF(iter);
788 : 151059 : Py_RETURN_NONE;
789 : : }
790 : :
791 : : #include "clinic/iobase.c.h"
792 : :
793 : : static PyMethodDef iobase_methods[] = {
794 : : {"seek", iobase_seek, METH_VARARGS, iobase_seek_doc},
795 : : _IO__IOBASE_TELL_METHODDEF
796 : : {"truncate", iobase_truncate, METH_VARARGS, iobase_truncate_doc},
797 : : _IO__IOBASE_FLUSH_METHODDEF
798 : : _IO__IOBASE_CLOSE_METHODDEF
799 : :
800 : : _IO__IOBASE_SEEKABLE_METHODDEF
801 : : _IO__IOBASE_READABLE_METHODDEF
802 : : _IO__IOBASE_WRITABLE_METHODDEF
803 : :
804 : : {"_checkClosed", _PyIOBase_check_closed, METH_NOARGS},
805 : : {"_checkSeekable", _PyIOBase_check_seekable, METH_NOARGS},
806 : : {"_checkReadable", _PyIOBase_check_readable, METH_NOARGS},
807 : : {"_checkWritable", _PyIOBase_check_writable, METH_NOARGS},
808 : :
809 : : _IO__IOBASE_FILENO_METHODDEF
810 : : _IO__IOBASE_ISATTY_METHODDEF
811 : :
812 : : {"__enter__", iobase_enter, METH_NOARGS},
813 : : {"__exit__", iobase_exit, METH_VARARGS},
814 : :
815 : : _IO__IOBASE_READLINE_METHODDEF
816 : : _IO__IOBASE_READLINES_METHODDEF
817 : : _IO__IOBASE_WRITELINES_METHODDEF
818 : :
819 : : {NULL, NULL}
820 : : };
821 : :
822 : : static PyGetSetDef iobase_getset[] = {
823 : : {"__dict__", PyObject_GenericGetDict, NULL, NULL},
824 : : {"closed", (getter)iobase_closed_get, NULL, NULL},
825 : : {NULL}
826 : : };
827 : :
828 : :
829 : : PyTypeObject PyIOBase_Type = {
830 : : PyVarObject_HEAD_INIT(NULL, 0)
831 : : "_io._IOBase", /*tp_name*/
832 : : sizeof(iobase), /*tp_basicsize*/
833 : : 0, /*tp_itemsize*/
834 : : (destructor)iobase_dealloc, /*tp_dealloc*/
835 : : 0, /*tp_vectorcall_offset*/
836 : : 0, /*tp_getattr*/
837 : : 0, /*tp_setattr*/
838 : : 0, /*tp_as_async*/
839 : : 0, /*tp_repr*/
840 : : 0, /*tp_as_number*/
841 : : 0, /*tp_as_sequence*/
842 : : 0, /*tp_as_mapping*/
843 : : 0, /*tp_hash */
844 : : 0, /*tp_call*/
845 : : 0, /*tp_str*/
846 : : 0, /*tp_getattro*/
847 : : 0, /*tp_setattro*/
848 : : 0, /*tp_as_buffer*/
849 : : Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE
850 : : | Py_TPFLAGS_HAVE_GC, /*tp_flags*/
851 : : iobase_doc, /* tp_doc */
852 : : (traverseproc)iobase_traverse, /* tp_traverse */
853 : : (inquiry)iobase_clear, /* tp_clear */
854 : : 0, /* tp_richcompare */
855 : : offsetof(iobase, weakreflist), /* tp_weaklistoffset */
856 : : iobase_iter, /* tp_iter */
857 : : iobase_iternext, /* tp_iternext */
858 : : iobase_methods, /* tp_methods */
859 : : 0, /* tp_members */
860 : : iobase_getset, /* tp_getset */
861 : : 0, /* tp_base */
862 : : 0, /* tp_dict */
863 : : 0, /* tp_descr_get */
864 : : 0, /* tp_descr_set */
865 : : offsetof(iobase, dict), /* tp_dictoffset */
866 : : 0, /* tp_init */
867 : : 0, /* tp_alloc */
868 : : PyType_GenericNew, /* tp_new */
869 : : 0, /* tp_free */
870 : : 0, /* tp_is_gc */
871 : : 0, /* tp_bases */
872 : : 0, /* tp_mro */
873 : : 0, /* tp_cache */
874 : : 0, /* tp_subclasses */
875 : : 0, /* tp_weaklist */
876 : : 0, /* tp_del */
877 : : 0, /* tp_version_tag */
878 : : iobase_finalize, /* tp_finalize */
879 : : };
880 : :
881 : :
882 : : /*
883 : : * RawIOBase class, Inherits from IOBase.
884 : : */
885 : : PyDoc_STRVAR(rawiobase_doc,
886 : : "Base class for raw binary I/O.");
887 : :
888 : : /*
889 : : * The read() method is implemented by calling readinto(); derived classes
890 : : * that want to support read() only need to implement readinto() as a
891 : : * primitive operation. In general, readinto() can be more efficient than
892 : : * read().
893 : : *
894 : : * (It would be tempting to also provide an implementation of readinto() in
895 : : * terms of read(), in case the latter is a more suitable primitive operation,
896 : : * but that would lead to nasty recursion in case a subclass doesn't implement
897 : : * either.)
898 : : */
899 : :
900 : : /*[clinic input]
901 : : _io._RawIOBase.read
902 : : size as n: Py_ssize_t = -1
903 : : /
904 : : [clinic start generated code]*/
905 : :
906 : : static PyObject *
907 : 3814 : _io__RawIOBase_read_impl(PyObject *self, Py_ssize_t n)
908 : : /*[clinic end generated code: output=6cdeb731e3c9f13c input=b6d0dcf6417d1374]*/
909 : : {
910 : : PyObject *b, *res;
911 : :
912 [ + + ]: 3814 : if (n < 0) {
913 : 3 : return PyObject_CallMethodNoArgs(self, &_Py_ID(readall));
914 : : }
915 : :
916 : : /* TODO: allocate a bytes object directly instead and manually construct
917 : : a writable memoryview pointing to it. */
918 : 3811 : b = PyByteArray_FromStringAndSize(NULL, n);
919 [ - + ]: 3811 : if (b == NULL)
920 : 0 : return NULL;
921 : :
922 : 3811 : res = PyObject_CallMethodObjArgs(self, &_Py_ID(readinto), b, NULL);
923 [ + + + + ]: 3811 : if (res == NULL || res == Py_None) {
924 : 6 : Py_DECREF(b);
925 : 6 : return res;
926 : : }
927 : :
928 : 3805 : n = PyNumber_AsSsize_t(res, PyExc_ValueError);
929 : 3805 : Py_DECREF(res);
930 [ - + - - ]: 3805 : if (n == -1 && PyErr_Occurred()) {
931 : 0 : Py_DECREF(b);
932 : 0 : return NULL;
933 : : }
934 : :
935 : 3805 : res = PyBytes_FromStringAndSize(PyByteArray_AsString(b), n);
936 : 3805 : Py_DECREF(b);
937 : 3805 : return res;
938 : : }
939 : :
940 : :
941 : : /*[clinic input]
942 : : _io._RawIOBase.readall
943 : :
944 : : Read until EOF, using multiple read() call.
945 : : [clinic start generated code]*/
946 : :
947 : : static PyObject *
948 : 59 : _io__RawIOBase_readall_impl(PyObject *self)
949 : : /*[clinic end generated code: output=1987b9ce929425a0 input=688874141213622a]*/
950 : : {
951 : : int r;
952 : 59 : PyObject *chunks = PyList_New(0);
953 : : PyObject *result;
954 : :
955 [ + - ]: 59 : if (chunks == NULL)
956 : 0 : return NULL;
957 : :
958 : 2089 : while (1) {
959 : 2148 : PyObject *data = _PyObject_CallMethod(self, &_Py_ID(read),
960 : : "i", DEFAULT_BUFFER_SIZE);
961 [ - + ]: 2148 : if (!data) {
962 : : /* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
963 : : when EINTR occurs so we needn't do it ourselves. */
964 [ # # ]: 0 : if (_PyIO_trap_eintr()) {
965 : 0 : continue;
966 : : }
967 : 0 : Py_DECREF(chunks);
968 : 0 : return NULL;
969 : : }
970 [ + + ]: 2148 : if (data == Py_None) {
971 [ + + ]: 8 : if (PyList_GET_SIZE(chunks) == 0) {
972 : 6 : Py_DECREF(chunks);
973 : 6 : return data;
974 : : }
975 : 2 : Py_DECREF(data);
976 : 2 : break;
977 : : }
978 [ - + ]: 2140 : if (!PyBytes_Check(data)) {
979 : 0 : Py_DECREF(chunks);
980 : 0 : Py_DECREF(data);
981 : 0 : PyErr_SetString(PyExc_TypeError, "read() should return bytes");
982 : 0 : return NULL;
983 : : }
984 [ + + ]: 2140 : if (PyBytes_GET_SIZE(data) == 0) {
985 : : /* EOF */
986 : 51 : Py_DECREF(data);
987 : 51 : break;
988 : : }
989 : 2089 : r = PyList_Append(chunks, data);
990 : 2089 : Py_DECREF(data);
991 [ - + ]: 2089 : if (r < 0) {
992 : 0 : Py_DECREF(chunks);
993 : 0 : return NULL;
994 : : }
995 : : }
996 : 53 : result = _PyBytes_Join((PyObject *)&_Py_SINGLETON(bytes_empty), chunks);
997 : 53 : Py_DECREF(chunks);
998 : 53 : return result;
999 : : }
1000 : :
1001 : : static PyObject *
1002 : 0 : rawiobase_readinto(PyObject *self, PyObject *args)
1003 : : {
1004 : 0 : PyErr_SetNone(PyExc_NotImplementedError);
1005 : 0 : return NULL;
1006 : : }
1007 : :
1008 : : static PyObject *
1009 : 0 : rawiobase_write(PyObject *self, PyObject *args)
1010 : : {
1011 : 0 : PyErr_SetNone(PyExc_NotImplementedError);
1012 : 0 : return NULL;
1013 : : }
1014 : :
1015 : : static PyMethodDef rawiobase_methods[] = {
1016 : : _IO__RAWIOBASE_READ_METHODDEF
1017 : : _IO__RAWIOBASE_READALL_METHODDEF
1018 : : {"readinto", rawiobase_readinto, METH_VARARGS},
1019 : : {"write", rawiobase_write, METH_VARARGS},
1020 : : {NULL, NULL}
1021 : : };
1022 : :
1023 : : PyTypeObject PyRawIOBase_Type = {
1024 : : PyVarObject_HEAD_INIT(NULL, 0)
1025 : : "_io._RawIOBase", /*tp_name*/
1026 : : 0, /*tp_basicsize*/
1027 : : 0, /*tp_itemsize*/
1028 : : 0, /*tp_dealloc*/
1029 : : 0, /*tp_vectorcall_offset*/
1030 : : 0, /*tp_getattr*/
1031 : : 0, /*tp_setattr*/
1032 : : 0, /*tp_as_async*/
1033 : : 0, /*tp_repr*/
1034 : : 0, /*tp_as_number*/
1035 : : 0, /*tp_as_sequence*/
1036 : : 0, /*tp_as_mapping*/
1037 : : 0, /*tp_hash */
1038 : : 0, /*tp_call*/
1039 : : 0, /*tp_str*/
1040 : : 0, /*tp_getattro*/
1041 : : 0, /*tp_setattro*/
1042 : : 0, /*tp_as_buffer*/
1043 : : Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /*tp_flags*/
1044 : : rawiobase_doc, /* tp_doc */
1045 : : 0, /* tp_traverse */
1046 : : 0, /* tp_clear */
1047 : : 0, /* tp_richcompare */
1048 : : 0, /* tp_weaklistoffset */
1049 : : 0, /* tp_iter */
1050 : : 0, /* tp_iternext */
1051 : : rawiobase_methods, /* tp_methods */
1052 : : 0, /* tp_members */
1053 : : 0, /* tp_getset */
1054 : : &PyIOBase_Type, /* tp_base */
1055 : : 0, /* tp_dict */
1056 : : 0, /* tp_descr_get */
1057 : : 0, /* tp_descr_set */
1058 : : 0, /* tp_dictoffset */
1059 : : 0, /* tp_init */
1060 : : 0, /* tp_alloc */
1061 : : 0, /* tp_new */
1062 : : 0, /* tp_free */
1063 : : 0, /* tp_is_gc */
1064 : : 0, /* tp_bases */
1065 : : 0, /* tp_mro */
1066 : : 0, /* tp_cache */
1067 : : 0, /* tp_subclasses */
1068 : : 0, /* tp_weaklist */
1069 : : 0, /* tp_del */
1070 : : 0, /* tp_version_tag */
1071 : : 0, /* tp_finalize */
1072 : : };
|