Skip to content

Commit 426d943

Browse files
committed
Use a set to track registered file descriptors
1 parent 6605e86 commit 426d943

1 file changed

Lines changed: 38 additions & 8 deletions

File tree

Modules/selectmodule.c

Lines changed: 38 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -832,7 +832,7 @@ typedef struct {
832832
int fd_devpoll;
833833
int n_fds;
834834
int out_size;
835-
int registered;
835+
PyObject *registered; // set of registered fds
836836
struct pollfd *fds;
837837
struct pollfd *out_fds;
838838
} devpollObject;
@@ -883,6 +883,17 @@ internal_devpoll_register(devpollObject *self, int fd,
883883
if (self->fd_devpoll < 0)
884884
return devpoll_err_closed();
885885

886+
// registered.add(fd)
887+
PyObject *fd_obj = PyLong_FromLong(fd);
888+
if (fd_obj == NULL) {
889+
return NULL;
890+
}
891+
int res = PySet_Add(self->registered, fd_obj);
892+
Py_DECREF(fd_obj);
893+
if (res < 0) {
894+
return NULL;
895+
}
896+
886897
if (remove) {
887898
self->fds[self->n_fds].fd = fd;
888899
self->fds[self->n_fds].events = POLLREMOVE;
@@ -891,7 +902,6 @@ internal_devpoll_register(devpollObject *self, int fd,
891902
if (devpoll_flush(self))
892903
return NULL;
893904
}
894-
self->registered -= 1;
895905
}
896906

897907
self->fds[self->n_fds].fd = fd;
@@ -902,7 +912,6 @@ internal_devpoll_register(devpollObject *self, int fd,
902912
return NULL;
903913
}
904914

905-
self->registered += 1;
906915
Py_RETURN_NONE;
907916
}
908917

@@ -967,6 +976,17 @@ select_devpoll_unregister_impl(devpollObject *self, int fd)
967976
if (self->fd_devpoll < 0)
968977
return devpoll_err_closed();
969978

979+
// registered.discard(fd)
980+
PyObject *fd_obj = PyLong_FromLong(fd);
981+
if (fd_obj == NULL) {
982+
return NULL;
983+
}
984+
int res = PySet_Discard(self->registered, fd_obj);
985+
Py_DECREF(fd_obj);
986+
if (res < 0) {
987+
return NULL;
988+
}
989+
970990
self->fds[self->n_fds].fd = fd;
971991
self->fds[self->n_fds].events = POLLREMOVE;
972992

@@ -975,7 +995,6 @@ select_devpoll_unregister_impl(devpollObject *self, int fd)
975995
return NULL;
976996
}
977997

978-
self->registered -= 1;
979998
Py_RETURN_NONE;
980999
}
9811000

@@ -1034,9 +1053,10 @@ select_devpoll_poll_impl(devpollObject *self, PyObject *timeout_obj)
10341053

10351054
/* Ensure the output buffer is large enough to potentially
10361055
* fit all registered file descriptors. */
1037-
if (self->registered > self->out_size) {
1038-
self->out_size = self->registered + 128;
1039-
self->out_fds = PyMem_Resize(self->out_fds, struct pollfd, self->out_size);
1056+
Py_ssize_t registered = PySet_GET_SIZE(self->registered);
1057+
if (registered > self->out_size) {
1058+
self->out_size = registered + 128;
1059+
PyMem_Resize(self->out_fds, struct pollfd, self->out_size);
10401060
if (self->out_fds == NULL) {
10411061
PyErr_NoMemory();
10421062
return NULL;
@@ -1225,17 +1245,26 @@ newDevPollObject(PyObject *module)
12251245
return NULL;
12261246
}
12271247

1248+
PyObject *registered = PySet_New(NULL);
1249+
if (registered == NULL) {
1250+
close(fd_devpoll);
1251+
PyMem_Free(fds);
1252+
PyMem_Free(out_fds);
1253+
return NULL;
1254+
}
1255+
12281256
self = PyObject_New(devpollObject, get_select_state(module)->devpoll_Type);
12291257
if (self == NULL) {
12301258
close(fd_devpoll);
12311259
PyMem_Free(fds);
12321260
PyMem_Free(out_fds);
1261+
Py_DECREF(registered);
12331262
return NULL;
12341263
}
12351264
self->fd_devpoll = fd_devpoll;
12361265
self->n_fds = 0;
12371266
self->fds = fds;
1238-
self->registered = 0;
1267+
self->registered = registered;
12391268
self->out_size = out_size;
12401269
self->out_fds = out_fds;
12411270

@@ -1250,6 +1279,7 @@ devpoll_dealloc(PyObject *op)
12501279
(void)devpoll_internal_close(self);
12511280
PyMem_Free(self->fds);
12521281
PyMem_Free(self->out_fds);
1282+
Py_DECREF(self->registered);
12531283
PyObject_Free(self);
12541284
Py_DECREF(type);
12551285
}

0 commit comments

Comments
 (0)