Skip to content

Commit d478acf

Browse files
vstinnerEclips4
andcommitted
pythongh-108240: Fix a reference cycle in _socket.CAPI capsule
_socket.CAPI capsule contains a strong reference to _socket.socket type. The garbage collector cannot visit this reference and so cannot create the reference cycle involving _socket.socket (a heap type creates a reference cycle to inside, via MRO and methods). At Python, _PyImport_ClearModules() sets _socket attributes to None which works around the issue. If the module is cleared from sys.modules manually, _PyImport_ClearModules() cannot set _socket.CAPI to None and so the issue cannot be worked around. Change _socket.CAPI to use a borrowed reference instead of a strong reference to allow clearing _socket.socket in this case. Co-authored-by: Kirill Podoprigora <[email protected]>
1 parent d63972e commit d478acf

File tree

2 files changed

+2
-3
lines changed

2 files changed

+2
-3
lines changed

Modules/socketmodule.c

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7317,7 +7317,6 @@ os_init(void)
73177317
static void
73187318
sock_free_api(PySocketModule_APIObject *capi)
73197319
{
7320-
Py_DECREF(capi->Sock_Type);
73217320
Py_DECREF(capi->error);
73227321
Py_DECREF(capi->timeout_error);
73237322
PyMem_Free(capi);
@@ -7339,7 +7338,7 @@ sock_get_api(socket_state *state)
73397338
return NULL;
73407339
}
73417340

7342-
capi->Sock_Type = (PyTypeObject *)Py_NewRef(state->sock_type);
7341+
capi->Sock_Type = state->sock_type;
73437342
capi->error = Py_NewRef(PyExc_OSError);
73447343
capi->timeout_error = Py_NewRef(PyExc_TimeoutError);
73457344
return capi;

Modules/socketmodule.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -382,7 +382,7 @@ typedef struct {
382382
/* C API for usage by other Python modules.
383383
* Always add new things to the end for binary compatibility. */
384384
typedef struct {
385-
PyTypeObject *Sock_Type;
385+
PyTypeObject *Sock_Type; // borrowed reference (gh-108240)
386386
PyObject *error;
387387
PyObject *timeout_error;
388388
} PySocketModule_APIObject;

0 commit comments

Comments
 (0)