3232/* Initial buffer size. */
3333#define DEF_BUF_SIZE (16*1024)
3434
35- static PyTypeObject Comptype ;
36- static PyTypeObject Decomptype ;
35+ static PyModuleDef zlibmodule ;
3736
38- static PyObject * ZlibError ;
37+ typedef struct {
38+ PyTypeObject * Comptype ;
39+ PyTypeObject * Decomptype ;
40+ PyObject * ZlibError ;
41+ } _zlibstate ;
42+
43+ #define _zlibstate (o ) ((_zlibstate *)PyModule_GetState(o))
44+ #define _zlibstate_global ((_zlibstate *)PyModule_GetState(PyState_FindModule(&zlibmodule)))
3945
4046typedef struct
4147{
@@ -73,9 +79,9 @@ zlib_error(z_stream zst, int err, const char *msg)
7379 }
7480 }
7581 if (zmsg == Z_NULL )
76- PyErr_Format (ZlibError , "Error %d %s" , err , msg );
82+ PyErr_Format (_zlibstate_global -> ZlibError , "Error %d %s" , err , msg );
7783 else
78- PyErr_Format (ZlibError , "Error %d %s: %.200s" , err , msg , zmsg );
84+ PyErr_Format (_zlibstate_global -> ZlibError , "Error %d %s: %.200s" , err , msg , zmsg );
7985}
8086
8187/*[clinic input]
@@ -226,7 +232,7 @@ zlib_compress_impl(PyObject *module, Py_buffer *data, int level)
226232 "Out of memory while compressing data" );
227233 goto error ;
228234 case Z_STREAM_ERROR :
229- PyErr_SetString (ZlibError , "Bad compression level" );
235+ PyErr_SetString (_zlibstate_global -> ZlibError , "Bad compression level" );
230236 goto error ;
231237 default :
232238 deflateEnd (& zst );
@@ -462,7 +468,7 @@ zlib_compressobj_impl(PyObject *module, int level, int method, int wbits,
462468 goto error ;
463469 }
464470
465- self = newcompobject (& Comptype );
471+ self = newcompobject (_zlibstate_global -> Comptype );
466472 if (self == NULL )
467473 goto error ;
468474 self -> zst .opaque = NULL ;
@@ -558,7 +564,7 @@ zlib_decompressobj_impl(PyObject *module, int wbits, PyObject *zdict)
558564 return NULL ;
559565 }
560566
561- self = newcompobject (& Decomptype );
567+ self = newcompobject (_zlibstate_global -> Decomptype );
562568 if (self == NULL )
563569 return NULL ;
564570 self -> zst .opaque = NULL ;
@@ -581,7 +587,7 @@ zlib_decompressobj_impl(PyObject *module, int wbits, PyObject *zdict)
581587 return NULL ;
582588 }
583589#else
584- PyErr_Format (ZlibError ,
590+ PyErr_Format (_zlibstate_global -> ZlibError ,
585591 "zlib version %s does not allow raw inflate with dictionary" ,
586592 ZLIB_VERSION );
587593 Py_DECREF (self );
@@ -608,11 +614,13 @@ zlib_decompressobj_impl(PyObject *module, int wbits, PyObject *zdict)
608614static void
609615Dealloc (compobject * self )
610616{
617+ PyObject * type = (PyObject * )Py_TYPE (self );
611618 PyThread_free_lock (self -> lock );
612619 Py_XDECREF (self -> unused_data );
613620 Py_XDECREF (self -> unconsumed_tail );
614621 Py_XDECREF (self -> zdict );
615622 PyObject_Del (self );
623+ Py_DECREF (type );
616624}
617625
618626static void
@@ -944,7 +952,7 @@ zlib_Compress_copy_impl(compobject *self)
944952 compobject * retval = NULL ;
945953 int err ;
946954
947- retval = newcompobject (& Comptype );
955+ retval = newcompobject (_zlibstate_global -> Comptype );
948956 if (!retval ) return NULL ;
949957
950958 /* Copy the zstream state
@@ -1025,7 +1033,7 @@ zlib_Decompress_copy_impl(compobject *self)
10251033 compobject * retval = NULL ;
10261034 int err ;
10271035
1028- retval = newcompobject (& Decomptype );
1036+ retval = newcompobject (_zlibstate_global -> Decomptype );
10291037 if (!retval ) return NULL ;
10301038
10311039 /* Copy the zstream state
@@ -1309,67 +1317,33 @@ static PyMethodDef zlib_methods[] =
13091317 {NULL , NULL }
13101318};
13111319
1312- static PyTypeObject Comptype = {
1313- PyVarObject_HEAD_INIT (0 , 0 )
1320+ static PyType_Slot Comptype_slots [] = {
1321+ {Py_tp_dealloc , Comp_dealloc },
1322+ {Py_tp_methods , comp_methods },
1323+ {0 , 0 },
1324+ };
1325+
1326+ static PyType_Spec Comptype_spec = {
13141327 "zlib.Compress" ,
13151328 sizeof (compobject ),
13161329 0 ,
1317- (destructor )Comp_dealloc , /*tp_dealloc*/
1318- 0 , /*tp_vectorcall_offset*/
1319- 0 , /*tp_getattr*/
1320- 0 , /*tp_setattr*/
1321- 0 , /*tp_as_async*/
1322- 0 , /*tp_repr*/
1323- 0 , /*tp_as_number*/
1324- 0 , /*tp_as_sequence*/
1325- 0 , /*tp_as_mapping*/
1326- 0 , /*tp_hash*/
1327- 0 , /*tp_call*/
1328- 0 , /*tp_str*/
1329- 0 , /*tp_getattro*/
1330- 0 , /*tp_setattro*/
1331- 0 , /*tp_as_buffer*/
1332- Py_TPFLAGS_DEFAULT , /*tp_flags*/
1333- 0 , /*tp_doc*/
1334- 0 , /*tp_traverse*/
1335- 0 , /*tp_clear*/
1336- 0 , /*tp_richcompare*/
1337- 0 , /*tp_weaklistoffset*/
1338- 0 , /*tp_iter*/
1339- 0 , /*tp_iternext*/
1340- comp_methods , /*tp_methods*/
1330+ Py_TPFLAGS_DEFAULT ,
1331+ Comptype_slots
13411332};
13421333
1343- static PyTypeObject Decomptype = {
1344- PyVarObject_HEAD_INIT (0 , 0 )
1334+ static PyType_Slot Decomptype_slots [] = {
1335+ {Py_tp_dealloc , Decomp_dealloc },
1336+ {Py_tp_methods , Decomp_methods },
1337+ {Py_tp_members , Decomp_members },
1338+ {0 , 0 },
1339+ };
1340+
1341+ static PyType_Spec Decomptype_spec = {
13451342 "zlib.Decompress" ,
13461343 sizeof (compobject ),
13471344 0 ,
1348- (destructor )Decomp_dealloc , /*tp_dealloc*/
1349- 0 , /*tp_vectorcall_offset*/
1350- 0 , /*tp_getattr*/
1351- 0 , /*tp_setattr*/
1352- 0 , /*tp_as_async*/
1353- 0 , /*tp_repr*/
1354- 0 , /*tp_as_number*/
1355- 0 , /*tp_as_sequence*/
1356- 0 , /*tp_as_mapping*/
1357- 0 , /*tp_hash*/
1358- 0 , /*tp_call*/
1359- 0 , /*tp_str*/
1360- 0 , /*tp_getattro*/
1361- 0 , /*tp_setattro*/
1362- 0 , /*tp_as_buffer*/
1363- Py_TPFLAGS_DEFAULT , /*tp_flags*/
1364- 0 , /*tp_doc*/
1365- 0 , /*tp_traverse*/
1366- 0 , /*tp_clear*/
1367- 0 , /*tp_richcompare*/
1368- 0 , /*tp_weaklistoffset*/
1369- 0 , /*tp_iter*/
1370- 0 , /*tp_iternext*/
1371- Decomp_methods , /*tp_methods*/
1372- Decomp_members , /*tp_members*/
1345+ Py_TPFLAGS_DEFAULT ,
1346+ Decomptype_slots
13731347};
13741348
13751349PyDoc_STRVAR (zlib_module_documentation ,
@@ -1387,34 +1361,72 @@ PyDoc_STRVAR(zlib_module_documentation,
13871361"Compressor objects support compress() and flush() methods; decompressor\n"
13881362"objects support decompress() and flush()." );
13891363
1364+ static int
1365+ zlib_clear (PyObject * m )
1366+ {
1367+ _zlibstate * state = _zlibstate (m );
1368+ Py_CLEAR (state -> Comptype );
1369+ Py_CLEAR (state -> Decomptype );
1370+ Py_CLEAR (state -> ZlibError );
1371+ return 0 ;
1372+ }
1373+
1374+ static int
1375+ zlib_traverse (PyObject * m , visitproc visit , void * arg )
1376+ {
1377+ _zlibstate * state = _zlibstate (m );
1378+ Py_VISIT (state -> Comptype );
1379+ Py_VISIT (state -> Decomptype );
1380+ Py_VISIT (state -> ZlibError );
1381+ return 0 ;
1382+ }
1383+
1384+ static void
1385+ zlib_free (void * m )
1386+ {
1387+ zlib_clear ((PyObject * )m );
1388+ }
1389+
13901390static struct PyModuleDef zlibmodule = {
13911391 PyModuleDef_HEAD_INIT ,
13921392 "zlib" ,
13931393 zlib_module_documentation ,
1394- -1 ,
1394+ sizeof ( _zlibstate ) ,
13951395 zlib_methods ,
13961396 NULL ,
1397- NULL ,
1398- NULL ,
1399- NULL
1397+ zlib_traverse ,
1398+ zlib_clear ,
1399+ zlib_free ,
14001400};
14011401
14021402PyMODINIT_FUNC
14031403PyInit_zlib (void )
14041404{
14051405 PyObject * m , * ver ;
1406- if (PyType_Ready (& Comptype ) < 0 )
1407- return NULL ;
1408- if (PyType_Ready (& Decomptype ) < 0 )
1409- return NULL ;
1406+ m = PyState_FindModule (& zlibmodule );
1407+ if (m != NULL ) {
1408+ Py_INCREF (m );
1409+ return m ;
1410+ }
14101411 m = PyModule_Create (& zlibmodule );
14111412 if (m == NULL )
14121413 return NULL ;
14131414
1414- ZlibError = PyErr_NewException ("zlib.error" , NULL , NULL );
1415+ PyTypeObject * Comptype = (PyTypeObject * )PyType_FromSpec (& Comptype_spec );
1416+ if (Comptype == NULL )
1417+ return NULL ;
1418+ _zlibstate (m )-> Comptype = Comptype ;
1419+
1420+ PyTypeObject * Decomptype = (PyTypeObject * )PyType_FromSpec (& Decomptype_spec );
1421+ if (Decomptype == NULL )
1422+ return NULL ;
1423+ _zlibstate (m )-> Decomptype = Decomptype ;
1424+
1425+ PyObject * ZlibError = PyErr_NewException ("zlib.error" , NULL , NULL );
14151426 if (ZlibError != NULL ) {
14161427 Py_INCREF (ZlibError );
14171428 PyModule_AddObject (m , "error" , ZlibError );
1429+ _zlibstate (m )-> ZlibError = ZlibError ;
14181430 }
14191431 PyModule_AddIntMacro (m , MAX_WBITS );
14201432 PyModule_AddIntMacro (m , DEFLATED );
@@ -1457,5 +1469,6 @@ PyInit_zlib(void)
14571469
14581470 PyModule_AddStringConstant (m , "__version__" , "1.0" );
14591471
1472+ PyState_AddModule (m , & zlibmodule );
14601473 return m ;
14611474}
0 commit comments