1 /* _bz2 - Low-level Python interface to libbzip2. */
2
3 #define PY_SSIZE_T_CLEAN
4
5 #include "Python.h"
6 #include "structmember.h" // PyMemberDef
7
8 #include <bzlib.h>
9 #include <stdio.h>
10
11 // Blocks output buffer wrappers
12 #include "pycore_blocks_output_buffer.h"
13
14 #if OUTPUT_BUFFER_MAX_BLOCK_SIZE > UINT32_MAX
15 #error "The maximum block size accepted by libbzip2 is UINT32_MAX."
16 #endif
17
18 typedef struct {
19 PyTypeObject *bz2_compressor_type;
20 PyTypeObject *bz2_decompressor_type;
21 } _bz2_state;
22
23 static inline _bz2_state *
24 get_module_state(PyObject *module)
25 {
26 void *state = PyModule_GetState(module);
27 assert(state != NULL);
28 return (_bz2_state *)state;
29 }
30
31 static struct PyModuleDef _bz2module;
32
33 static inline _bz2_state *
34 find_module_state_by_def(PyTypeObject *type)
35 {
36 PyObject *module = PyType_GetModuleByDef(type, &_bz2module);
37 assert(module != NULL);
38 return get_module_state(module);
39 }
40
41 /* On success, return value >= 0
42 On failure, return -1 */
43 static inline Py_ssize_t
44 OutputBuffer_InitAndGrow(_BlocksOutputBuffer *buffer, Py_ssize_t max_length,
45 char **next_out, uint32_t *avail_out)
46 {
47 Py_ssize_t allocated;
48
49 allocated = _BlocksOutputBuffer_InitAndGrow(
50 buffer, max_length, (void**) next_out);
51 *avail_out = (uint32_t) allocated;
52 return allocated;
53 }
54
55 /* On success, return value >= 0
56 On failure, return -1 */
57 static inline Py_ssize_t
58 OutputBuffer_Grow(_BlocksOutputBuffer *buffer,
59 char **next_out, uint32_t *avail_out)
60 {
61 Py_ssize_t allocated;
62
63 allocated = _BlocksOutputBuffer_Grow(
64 buffer, (void**) next_out, (Py_ssize_t) *avail_out);
65 *avail_out = (uint32_t) allocated;
66 return allocated;
67 }
68
69 static inline Py_ssize_t
70 OutputBuffer_GetDataSize(_BlocksOutputBuffer *buffer, uint32_t avail_out)
71 {
72 return _BlocksOutputBuffer_GetDataSize(buffer, (Py_ssize_t) avail_out);
73 }
74
75 static inline PyObject *
76 OutputBuffer_Finish(_BlocksOutputBuffer *buffer, uint32_t avail_out)
77 {
78 return _BlocksOutputBuffer_Finish(buffer, (Py_ssize_t) avail_out);
79 }
80
81 static inline void
82 OutputBuffer_OnError(_BlocksOutputBuffer *buffer)
83 {
84 _BlocksOutputBuffer_OnError(buffer);
85 }
86
87
88 #ifndef BZ_CONFIG_ERROR
89 #define BZ2_bzCompress bzCompress
90 #define BZ2_bzCompressInit bzCompressInit
91 #define BZ2_bzCompressEnd bzCompressEnd
92 #define BZ2_bzDecompress bzDecompress
93 #define BZ2_bzDecompressInit bzDecompressInit
94 #define BZ2_bzDecompressEnd bzDecompressEnd
95 #endif /* ! BZ_CONFIG_ERROR */
96
97
98 #define ACQUIRE_LOCK(obj) do { \
99 if (!PyThread_acquire_lock((obj)->lock, 0)) { \
100 Py_BEGIN_ALLOW_THREADS \
101 PyThread_acquire_lock((obj)->lock, 1); \
102 Py_END_ALLOW_THREADS \
103 } } while (0)
104 #define RELEASE_LOCK(obj) PyThread_release_lock((obj)->lock)
105
106
107 typedef struct {
108 PyObject_HEAD
109 bz_stream bzs;
110 int flushed;
111 PyThread_type_lock lock;
112 } BZ2Compressor;
113
114 typedef struct {
115 PyObject_HEAD
116 bz_stream bzs;
117 char eof; /* T_BOOL expects a char */
118 PyObject *unused_data;
119 char needs_input;
120 char *input_buffer;
121 size_t input_buffer_size;
122
123 /* bzs->avail_in is only 32 bit, so we store the true length
124 separately. Conversion and looping is encapsulated in
125 decompress_buf() */
126 size_t bzs_avail_in_real;
127 PyThread_type_lock lock;
128 } BZ2Decompressor;
129
130 /* Helper functions. */
131
132 static int
133 catch_bz2_error(int bzerror)
134 {
135 switch(bzerror) {
136 case BZ_OK:
137 case BZ_RUN_OK:
138 case BZ_FLUSH_OK:
139 case BZ_FINISH_OK:
140 case BZ_STREAM_END:
141 return 0;
142
143 #ifdef BZ_CONFIG_ERROR
144 case BZ_CONFIG_ERROR:
145 PyErr_SetString(PyExc_SystemError,
146 "libbzip2 was not compiled correctly");
147 return 1;
148 #endif
149 case BZ_PARAM_ERROR:
150 PyErr_SetString(PyExc_ValueError,
151 "Internal error - "
152 "invalid parameters passed to libbzip2");
153 return 1;
154 case BZ_MEM_ERROR:
155 PyErr_NoMemory();
156 return 1;
157 case BZ_DATA_ERROR:
158 case BZ_DATA_ERROR_MAGIC:
159 PyErr_SetString(PyExc_OSError, "Invalid data stream");
160 return 1;
161 case BZ_IO_ERROR:
162 PyErr_SetString(PyExc_OSError, "Unknown I/O error");
163 return 1;
164 case BZ_UNEXPECTED_EOF:
165 PyErr_SetString(PyExc_EOFError,
166 "Compressed file ended before the logical "
167 "end-of-stream was detected");
168 return 1;
169 case BZ_SEQUENCE_ERROR:
170 PyErr_SetString(PyExc_RuntimeError,
171 "Internal error - "
172 "Invalid sequence of commands sent to libbzip2");
173 return 1;
174 default:
175 PyErr_Format(PyExc_OSError,
176 "Unrecognized error from libbzip2: %d", bzerror);
177 return 1;
178 }
179 }
180
181
182 /* BZ2Compressor class. */
183
184 static PyObject *
185 compress(BZ2Compressor *c, char *data, size_t len, int action)
186 {
187 PyObject *result;
188 _BlocksOutputBuffer buffer = {.list = NULL};
189
190 if (OutputBuffer_InitAndGrow(&buffer, -1, &c->bzs.next_out, &c->bzs.avail_out) < 0) {
191 goto error;
192 }
193 c->bzs.next_in = data;
194 c->bzs.avail_in = 0;
195
196 for (;;) {
197 int bzerror;
198
199 /* On a 64-bit system, len might not fit in avail_in (an unsigned int).
200 Do compression in chunks of no more than UINT_MAX bytes each. */
201 if (c->bzs.avail_in == 0 && len > 0) {
202 c->bzs.avail_in = (unsigned int)Py_MIN(len, UINT_MAX);
203 len -= c->bzs.avail_in;
204 }
205
206 /* In regular compression mode, stop when input data is exhausted. */
207 if (action == BZ_RUN && c->bzs.avail_in == 0)
208 break;
209
210 if (c->bzs.avail_out == 0) {
211 if (OutputBuffer_Grow(&buffer, &c->bzs.next_out, &c->bzs.avail_out) < 0) {
212 goto error;
213 }
214 }
215
216 Py_BEGIN_ALLOW_THREADS
217 bzerror = BZ2_bzCompress(&c->bzs, action);
218 Py_END_ALLOW_THREADS
219
220 if (catch_bz2_error(bzerror))
221 goto error;
222
223 /* In flushing mode, stop when all buffered data has been flushed. */
224 if (action == BZ_FINISH && bzerror == BZ_STREAM_END)
225 break;
226 }
227
228 result = OutputBuffer_Finish(&buffer, c->bzs.avail_out);
229 if (result != NULL) {
230 return result;
231 }
232
233 error:
234 OutputBuffer_OnError(&buffer);
235 return NULL;
236 }
237
238 /*[clinic input]
239 module _bz2
240 class _bz2.BZ2Compressor "BZ2Compressor *" "clinic_state()->bz2_compressor_type"
241 class _bz2.BZ2Decompressor "BZ2Decompressor *" "clinic_state()->bz2_decompressor_type"
242 [clinic start generated code]*/
243 /*[clinic end generated code: output=da39a3ee5e6b4b0d input=92348121632b94c4]*/
244
245 #define clinic_state() (find_module_state_by_def(type))
246 #include "clinic/_bz2module.c.h"
247 #undef clinic_state
248
249 /*[clinic input]
250 _bz2.BZ2Compressor.compress
251
252 data: Py_buffer
253 /
254
255 Provide data to the compressor object.
256
257 Returns a chunk of compressed data if possible, or b'' otherwise.
258
259 When you have finished providing data to the compressor, call the
260 flush() method to finish the compression process.
261 [clinic start generated code]*/
262
263 static PyObject *
264 _bz2_BZ2Compressor_compress_impl(BZ2Compressor *self, Py_buffer *data)
265 /*[clinic end generated code: output=59365426e941fbcc input=85c963218070fc4c]*/
266 {
267 PyObject *result = NULL;
268
269 ACQUIRE_LOCK(self);
270 if (self->flushed)
271 PyErr_SetString(PyExc_ValueError, "Compressor has been flushed");
272 else
273 result = compress(self, data->buf, data->len, BZ_RUN);
274 RELEASE_LOCK(self);
275 return result;
276 }
277
278 /*[clinic input]
279 _bz2.BZ2Compressor.flush
280
281 Finish the compression process.
282
283 Returns the compressed data left in internal buffers.
284
285 The compressor object may not be used after this method is called.
286 [clinic start generated code]*/
287
288 static PyObject *
289 _bz2_BZ2Compressor_flush_impl(BZ2Compressor *self)
290 /*[clinic end generated code: output=3ef03fc1b092a701 input=d64405d3c6f76691]*/
291 {
292 PyObject *result = NULL;
293
294 ACQUIRE_LOCK(self);
295 if (self->flushed)
296 PyErr_SetString(PyExc_ValueError, "Repeated call to flush()");
297 else {
298 self->flushed = 1;
299 result = compress(self, NULL, 0, BZ_FINISH);
300 }
301 RELEASE_LOCK(self);
302 return result;
303 }
304
305 static void*
306 BZ2_Malloc(void* ctx, int items, int size)
307 {
308 if (items < 0 || size < 0)
309 return NULL;
310 if (size != 0 && (size_t)items > (size_t)PY_SSIZE_T_MAX / (size_t)size)
311 return NULL;
312 /* PyMem_Malloc() cannot be used: compress() and decompress()
313 release the GIL */
314 return PyMem_RawMalloc((size_t)items * (size_t)size);
315 }
316
317 static void
318 BZ2_Free(void* ctx, void *ptr)
319 {
320 PyMem_RawFree(ptr);
321 }
322
323 /*[clinic input]
324 @classmethod
325 _bz2.BZ2Compressor.__new__
326
327 compresslevel: int = 9
328 Compression level, as a number between 1 and 9.
329 /
330
331 Create a compressor object for compressing data incrementally.
332
333 For one-shot compression, use the compress() function instead.
334 [clinic start generated code]*/
335
336 static PyObject *
337 _bz2_BZ2Compressor_impl(PyTypeObject *type, int compresslevel)
338 /*[clinic end generated code: output=83346c96beaacad7 input=d4500d2a52c8b263]*/
339 {
340 int bzerror;
341 BZ2Compressor *self;
342
343 if (!(1 <= compresslevel && compresslevel <= 9)) {
344 PyErr_SetString(PyExc_ValueError,
345 "compresslevel must be between 1 and 9");
346 return NULL;
347 }
348
349 assert(type != NULL && type->tp_alloc != NULL);
350 self = (BZ2Compressor *)type->tp_alloc(type, 0);
351 if (self == NULL) {
352 return NULL;
353 }
354
355 self->lock = PyThread_allocate_lock();
356 if (self->lock == NULL) {
357 Py_DECREF(self);
358 PyErr_SetString(PyExc_MemoryError, "Unable to allocate lock");
359 return NULL;
360 }
361
362 self->bzs.opaque = NULL;
363 self->bzs.bzalloc = BZ2_Malloc;
364 self->bzs.bzfree = BZ2_Free;
365 bzerror = BZ2_bzCompressInit(&self->bzs, compresslevel, 0, 0);
366 if (catch_bz2_error(bzerror))
367 goto error;
368
369 return (PyObject *)self;
370
371 error:
372 Py_DECREF(self);
373 return NULL;
374 }
375
376 static void
377 BZ2Compressor_dealloc(BZ2Compressor *self)
378 {
379 BZ2_bzCompressEnd(&self->bzs);
380 if (self->lock != NULL) {
381 PyThread_free_lock(self->lock);
382 }
383 PyTypeObject *tp = Py_TYPE(self);
384 tp->tp_free((PyObject *)self);
385 Py_DECREF(tp);
386 }
387
388 static int
389 BZ2Compressor_traverse(BZ2Compressor *self, visitproc visit, void *arg)
390 {
391 Py_VISIT(Py_TYPE(self));
392 return 0;
393 }
394
395 static PyMethodDef BZ2Compressor_methods[] = {
396 _BZ2_BZ2COMPRESSOR_COMPRESS_METHODDEF
397 _BZ2_BZ2COMPRESSOR_FLUSH_METHODDEF
398 {NULL}
399 };
400
401 static PyType_Slot bz2_compressor_type_slots[] = {
402 {Py_tp_dealloc, BZ2Compressor_dealloc},
403 {Py_tp_methods, BZ2Compressor_methods},
404 {Py_tp_new, _bz2_BZ2Compressor},
405 {Py_tp_doc, (char *)_bz2_BZ2Compressor__doc__},
406 {Py_tp_traverse, BZ2Compressor_traverse},
407 {0, 0}
408 };
409
410 static PyType_Spec bz2_compressor_type_spec = {
411 .name = "_bz2.BZ2Compressor",
412 .basicsize = sizeof(BZ2Compressor),
413 // Calling PyType_GetModuleState() on a subclass is not safe.
414 // bz2_compressor_type_spec does not have Py_TPFLAGS_BASETYPE flag
415 // which prevents to create a subclass.
416 // So calling PyType_GetModuleState() in this file is always safe.
417 .flags = (Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IMMUTABLETYPE),
418 .slots = bz2_compressor_type_slots,
419 };
420
421 /* BZ2Decompressor class. */
422
423 /* Decompress data of length d->bzs_avail_in_real in d->bzs.next_in. The output
424 buffer is allocated dynamically and returned. At most max_length bytes are
425 returned, so some of the input may not be consumed. d->bzs.next_in and
426 d->bzs_avail_in_real are updated to reflect the consumed input. */
427 static PyObject*
428 decompress_buf(BZ2Decompressor *d, Py_ssize_t max_length)
429 {
430 /* data_size is strictly positive, but because we repeatedly have to
431 compare against max_length and PyBytes_GET_SIZE we declare it as
432 signed */
433 PyObject *result;
434 _BlocksOutputBuffer buffer = {.list = NULL};
435 bz_stream *bzs = &d->bzs;
436
437 if (OutputBuffer_InitAndGrow(&buffer, max_length, &bzs->next_out, &bzs->avail_out) < 0) {
438 goto error;
439 }
440
441 for (;;) {
442 int bzret;
443 /* On a 64-bit system, buffer length might not fit in avail_out, so we
444 do decompression in chunks of no more than UINT_MAX bytes
445 each. Note that the expression for `avail` is guaranteed to be
446 positive, so the cast is safe. */
447 bzs->avail_in = (unsigned int)Py_MIN(d->bzs_avail_in_real, UINT_MAX);
448 d->bzs_avail_in_real -= bzs->avail_in;
449
450 Py_BEGIN_ALLOW_THREADS
451 bzret = BZ2_bzDecompress(bzs);
452 Py_END_ALLOW_THREADS
453
454 d->bzs_avail_in_real += bzs->avail_in;
455
456 if (catch_bz2_error(bzret))
457 goto error;
458 if (bzret == BZ_STREAM_END) {
459 d->eof = 1;
460 break;
461 } else if (d->bzs_avail_in_real == 0) {
462 break;
463 } else if (bzs->avail_out == 0) {
464 if (OutputBuffer_GetDataSize(&buffer, bzs->avail_out) == max_length) {
465 break;
466 }
467 if (OutputBuffer_Grow(&buffer, &bzs->next_out, &bzs->avail_out) < 0) {
468 goto error;
469 }
470 }
471 }
472
473 result = OutputBuffer_Finish(&buffer, bzs->avail_out);
474 if (result != NULL) {
475 return result;
476 }
477
478 error:
479 OutputBuffer_OnError(&buffer);
480 return NULL;
481 }
482
483
484 static PyObject *
485 decompress(BZ2Decompressor *d, char *data, size_t len, Py_ssize_t max_length)
486 {
487 char input_buffer_in_use;
488 PyObject *result;
489 bz_stream *bzs = &d->bzs;
490
491 /* Prepend unconsumed input if necessary */
492 if (bzs->next_in != NULL) {
493 size_t avail_now, avail_total;
494
495 /* Number of bytes we can append to input buffer */
496 avail_now = (d->input_buffer + d->input_buffer_size)
497 - (bzs->next_in + d->bzs_avail_in_real);
498
499 /* Number of bytes we can append if we move existing
500 contents to beginning of buffer (overwriting
501 consumed input) */
502 avail_total = d->input_buffer_size - d->bzs_avail_in_real;
503
504 if (avail_total < len) {
505 size_t offset = bzs->next_in - d->input_buffer;
506 char *tmp;
507 size_t new_size = d->input_buffer_size + len - avail_now;
508
509 /* Assign to temporary variable first, so we don't
510 lose address of allocated buffer if realloc fails */
511 tmp = PyMem_Realloc(d->input_buffer, new_size);
512 if (tmp == NULL) {
513 PyErr_SetNone(PyExc_MemoryError);
514 return NULL;
515 }
516 d->input_buffer = tmp;
517 d->input_buffer_size = new_size;
518
519 bzs->next_in = d->input_buffer + offset;
520 }
521 else if (avail_now < len) {
522 memmove(d->input_buffer, bzs->next_in,
523 d->bzs_avail_in_real);
524 bzs->next_in = d->input_buffer;
525 }
526 memcpy((void*)(bzs->next_in + d->bzs_avail_in_real), data, len);
527 d->bzs_avail_in_real += len;
528 input_buffer_in_use = 1;
529 }
530 else {
531 bzs->next_in = data;
532 d->bzs_avail_in_real = len;
533 input_buffer_in_use = 0;
534 }
535
536 result = decompress_buf(d, max_length);
537 if(result == NULL) {
538 bzs->next_in = NULL;
539 return NULL;
540 }
541
542 if (d->eof) {
543 d->needs_input = 0;
544 if (d->bzs_avail_in_real > 0) {
545 Py_XSETREF(d->unused_data,
546 PyBytes_FromStringAndSize(bzs->next_in, d->bzs_avail_in_real));
547 if (d->unused_data == NULL)
548 goto error;
549 }
550 }
551 else if (d->bzs_avail_in_real == 0) {
552 bzs->next_in = NULL;
553 d->needs_input = 1;
554 }
555 else {
556 d->needs_input = 0;
557
558 /* If we did not use the input buffer, we now have
559 to copy the tail from the caller's buffer into the
560 input buffer */
561 if (!input_buffer_in_use) {
562
563 /* Discard buffer if it's too small
564 (resizing it may needlessly copy the current contents) */
565 if (d->input_buffer != NULL &&
566 d->input_buffer_size < d->bzs_avail_in_real) {
567 PyMem_Free(d->input_buffer);
568 d->input_buffer = NULL;
569 }
570
571 /* Allocate if necessary */
572 if (d->input_buffer == NULL) {
573 d->input_buffer = PyMem_Malloc(d->bzs_avail_in_real);
574 if (d->input_buffer == NULL) {
575 PyErr_SetNone(PyExc_MemoryError);
576 goto error;
577 }
578 d->input_buffer_size = d->bzs_avail_in_real;
579 }
580
581 /* Copy tail */
582 memcpy(d->input_buffer, bzs->next_in, d->bzs_avail_in_real);
583 bzs->next_in = d->input_buffer;
584 }
585 }
586
587 return result;
588
589 error:
590 Py_XDECREF(result);
591 return NULL;
592 }
593
594 /*[clinic input]
595 _bz2.BZ2Decompressor.decompress
596
597 data: Py_buffer
598 max_length: Py_ssize_t=-1
599
600 Decompress *data*, returning uncompressed data as bytes.
601
602 If *max_length* is nonnegative, returns at most *max_length* bytes of
603 decompressed data. If this limit is reached and further output can be
604 produced, *self.needs_input* will be set to ``False``. In this case, the next
605 call to *decompress()* may provide *data* as b'' to obtain more of the output.
606
607 If all of the input data was decompressed and returned (either because this
608 was less than *max_length* bytes, or because *max_length* was negative),
609 *self.needs_input* will be set to True.
610
611 Attempting to decompress data after the end of stream is reached raises an
612 EOFError. Any data found after the end of the stream is ignored and saved in
613 the unused_data attribute.
614 [clinic start generated code]*/
615
616 static PyObject *
617 _bz2_BZ2Decompressor_decompress_impl(BZ2Decompressor *self, Py_buffer *data,
618 Py_ssize_t max_length)
619 /*[clinic end generated code: output=23e41045deb240a3 input=52e1ffc66a8ea624]*/
620 {
621 PyObject *result = NULL;
622
623 ACQUIRE_LOCK(self);
624 if (self->eof)
625 PyErr_SetString(PyExc_EOFError, "End of stream already reached");
626 else
627 result = decompress(self, data->buf, data->len, max_length);
628 RELEASE_LOCK(self);
629 return result;
630 }
631
632 /*[clinic input]
633 @classmethod
634 _bz2.BZ2Decompressor.__new__
635
636 Create a decompressor object for decompressing data incrementally.
637
638 For one-shot decompression, use the decompress() function instead.
639 [clinic start generated code]*/
640
641 static PyObject *
642 _bz2_BZ2Decompressor_impl(PyTypeObject *type)
643 /*[clinic end generated code: output=5150d51ccaab220e input=b87413ce51853528]*/
644 {
645 BZ2Decompressor *self;
646 int bzerror;
647
648 assert(type != NULL && type->tp_alloc != NULL);
649 self = (BZ2Decompressor *)type->tp_alloc(type, 0);
650 if (self == NULL) {
651 return NULL;
652 }
653
654 self->lock = PyThread_allocate_lock();
655 if (self->lock == NULL) {
656 Py_DECREF(self);
657 PyErr_SetString(PyExc_MemoryError, "Unable to allocate lock");
658 return NULL;
659 }
660
661 self->needs_input = 1;
662 self->bzs_avail_in_real = 0;
663 self->input_buffer = NULL;
664 self->input_buffer_size = 0;
665 self->unused_data = PyBytes_FromStringAndSize(NULL, 0);
666 if (self->unused_data == NULL)
667 goto error;
668
669 bzerror = BZ2_bzDecompressInit(&self->bzs, 0, 0);
670 if (catch_bz2_error(bzerror))
671 goto error;
672
673 return (PyObject *)self;
674
675 error:
676 Py_DECREF(self);
677 return NULL;
678 }
679
680 static void
681 BZ2Decompressor_dealloc(BZ2Decompressor *self)
682 {
683 if(self->input_buffer != NULL) {
684 PyMem_Free(self->input_buffer);
685 }
686 BZ2_bzDecompressEnd(&self->bzs);
687 Py_CLEAR(self->unused_data);
688 if (self->lock != NULL) {
689 PyThread_free_lock(self->lock);
690 }
691
692 PyTypeObject *tp = Py_TYPE(self);
693 tp->tp_free((PyObject *)self);
694 Py_DECREF(tp);
695 }
696
697 static int
698 BZ2Decompressor_traverse(BZ2Decompressor *self, visitproc visit, void *arg)
699 {
700 Py_VISIT(Py_TYPE(self));
701 return 0;
702 }
703
704 static PyMethodDef BZ2Decompressor_methods[] = {
705 _BZ2_BZ2DECOMPRESSOR_DECOMPRESS_METHODDEF
706 {NULL}
707 };
708
709 PyDoc_STRVAR(BZ2Decompressor_eof__doc__,
710 "True if the end-of-stream marker has been reached.");
711
712 PyDoc_STRVAR(BZ2Decompressor_unused_data__doc__,
713 "Data found after the end of the compressed stream.");
714
715 PyDoc_STRVAR(BZ2Decompressor_needs_input_doc,
716 "True if more input is needed before more decompressed data can be produced.");
717
718 static PyMemberDef BZ2Decompressor_members[] = {
719 {"eof", T_BOOL, offsetof(BZ2Decompressor, eof),
720 READONLY, BZ2Decompressor_eof__doc__},
721 {"unused_data", T_OBJECT_EX, offsetof(BZ2Decompressor, unused_data),
722 READONLY, BZ2Decompressor_unused_data__doc__},
723 {"needs_input", T_BOOL, offsetof(BZ2Decompressor, needs_input), READONLY,
724 BZ2Decompressor_needs_input_doc},
725 {NULL}
726 };
727
728 static PyType_Slot bz2_decompressor_type_slots[] = {
729 {Py_tp_dealloc, BZ2Decompressor_dealloc},
730 {Py_tp_methods, BZ2Decompressor_methods},
731 {Py_tp_doc, (char *)_bz2_BZ2Decompressor__doc__},
732 {Py_tp_members, BZ2Decompressor_members},
733 {Py_tp_new, _bz2_BZ2Decompressor},
734 {Py_tp_traverse, BZ2Decompressor_traverse},
735 {0, 0}
736 };
737
738 static PyType_Spec bz2_decompressor_type_spec = {
739 .name = "_bz2.BZ2Decompressor",
740 .basicsize = sizeof(BZ2Decompressor),
741 // Calling PyType_GetModuleState() on a subclass is not safe.
742 // bz2_decompressor_type_spec does not have Py_TPFLAGS_BASETYPE flag
743 // which prevents to create a subclass.
744 // So calling PyType_GetModuleState() in this file is always safe.
745 .flags = (Py_TPFLAGS_DEFAULT | Py_TPFLAGS_IMMUTABLETYPE),
746 .slots = bz2_decompressor_type_slots,
747 };
748
749 /* Module initialization. */
750
751 static int
752 _bz2_exec(PyObject *module)
753 {
754 _bz2_state *state = get_module_state(module);
755 state->bz2_compressor_type = (PyTypeObject *)PyType_FromModuleAndSpec(module,
756 &bz2_compressor_type_spec, NULL);
757 if (state->bz2_compressor_type == NULL) {
758 return -1;
759 }
760 if (PyModule_AddType(module, state->bz2_compressor_type) < 0) {
761 return -1;
762 }
763
764 state->bz2_decompressor_type = (PyTypeObject *)PyType_FromModuleAndSpec(module,
765 &bz2_decompressor_type_spec, NULL);
766 if (state->bz2_decompressor_type == NULL) {
767 return -1;
768 }
769 if (PyModule_AddType(module, state->bz2_decompressor_type) < 0) {
770 return -1;
771 }
772
773 return 0;
774 }
775
776 static int
777 _bz2_traverse(PyObject *module, visitproc visit, void *arg)
778 {
779 _bz2_state *state = get_module_state(module);
780 Py_VISIT(state->bz2_compressor_type);
781 Py_VISIT(state->bz2_decompressor_type);
782 return 0;
783 }
784
785 static int
786 _bz2_clear(PyObject *module)
787 {
788 _bz2_state *state = get_module_state(module);
789 Py_CLEAR(state->bz2_compressor_type);
790 Py_CLEAR(state->bz2_decompressor_type);
791 return 0;
792 }
793
794 static void
795 _bz2_free(void *module)
796 {
797 (void)_bz2_clear((PyObject *)module);
798 }
799
800 static struct PyModuleDef_Slot _bz2_slots[] = {
801 {Py_mod_exec, _bz2_exec},
802 {Py_mod_multiple_interpreters, Py_MOD_PER_INTERPRETER_GIL_SUPPORTED},
803 {0, NULL}
804 };
805
806 static struct PyModuleDef _bz2module = {
807 .m_base = PyModuleDef_HEAD_INIT,
808 .m_name = "_bz2",
809 .m_size = sizeof(_bz2_state),
810 .m_traverse = _bz2_traverse,
811 .m_clear = _bz2_clear,
812 .m_free = _bz2_free,
813 .m_slots = _bz2_slots,
814 };
815
816 PyMODINIT_FUNC
817 PyInit__bz2(void)
818 {
819 return PyModuleDef_Init(&_bz2module);
820 }