diff options
author | Serhiy Storchaka <storchaka@gmail.com> | 2013-12-14 17:18:39 (GMT) |
---|---|---|
committer | Serhiy Storchaka <storchaka@gmail.com> | 2013-12-14 17:18:39 (GMT) |
commit | 03241e801780edd967923d1cce00c2d07b208e58 (patch) | |
tree | 4b989c68d63e46df115ba53a2ed9a0b0c6314c85 /Modules | |
parent | 530a69fafce36317f1c83fe4998831f2d4284f3a (diff) | |
parent | 5da107ac7261d8359cd6e1a9a8e57f85176d1180 (diff) | |
download | cpython-03241e801780edd967923d1cce00c2d07b208e58.zip cpython-03241e801780edd967923d1cce00c2d07b208e58.tar.gz cpython-03241e801780edd967923d1cce00c2d07b208e58.tar.bz2 |
Issue #17919: Fixed integer overflow in the eventmask parameter.
Diffstat (limited to 'Modules')
-rw-r--r-- | Modules/selectmodule.c | 40 |
1 files changed, 29 insertions, 11 deletions
diff --git a/Modules/selectmodule.c b/Modules/selectmodule.c index 1e7ba4c..0293c8b 100644 --- a/Modules/selectmodule.c +++ b/Modules/selectmodule.c @@ -356,7 +356,7 @@ update_ufd_array(pollObject *self) assert(i < self->ufd_len); /* Never overflow */ self->ufds[i].fd = (int)PyLong_AsLong(key); - self->ufds[i].events = (short)PyLong_AsLong(value); + self->ufds[i].events = (short)(unsigned short)PyLong_AsLong(value); i++; } assert(i == self->ufd_len); @@ -364,6 +364,24 @@ update_ufd_array(pollObject *self) return 1; } +static int +ushort_converter(PyObject *obj, void *ptr) +{ + unsigned long uval; + + uval = PyLong_AsUnsignedLong(obj); + if (uval == (unsigned long)-1 && PyErr_Occurred()) + return 0; + if (uval > USHRT_MAX) { + PyErr_SetString(PyExc_OverflowError, + "Python int too large for C unsigned short"); + return 0; + } + + *(unsigned short *)ptr = Py_SAFE_DOWNCAST(uval, unsigned long, unsigned short); + return 1; +} + PyDoc_STRVAR(poll_register_doc, "register(fd [, eventmask] ) -> None\n\n\ Register a file descriptor with the polling object.\n\ @@ -375,12 +393,12 @@ static PyObject * poll_register(pollObject *self, PyObject *args) { PyObject *o, *key, *value; - int fd, events = POLLIN | POLLPRI | POLLOUT; + int fd; + unsigned short events = POLLIN | POLLPRI | POLLOUT; int err; - if (!PyArg_ParseTuple(args, "O|i:register", &o, &events)) { + if (!PyArg_ParseTuple(args, "O|O&:register", &o, ushort_converter, &events)) return NULL; - } fd = PyObject_AsFileDescriptor(o); if (fd == -1) return NULL; @@ -418,12 +436,12 @@ static PyObject * poll_modify(pollObject *self, PyObject *args) { PyObject *o, *key, *value; - int fd, events; + int fd; + unsigned short events; int err; - if (!PyArg_ParseTuple(args, "Oi:modify", &o, &events)) { + if (!PyArg_ParseTuple(args, "OO&:modify", &o, ushort_converter, &events)) return NULL; - } fd = PyObject_AsFileDescriptor(o); if (fd == -1) return NULL; @@ -728,14 +746,14 @@ static PyObject * internal_devpoll_register(devpollObject *self, PyObject *args, int remove) { PyObject *o; - int fd, events = POLLIN | POLLPRI | POLLOUT; + int fd; + unsigned short events = POLLIN | POLLPRI | POLLOUT; if (self->fd_devpoll < 0) return devpoll_err_closed(); - if (!PyArg_ParseTuple(args, "O|i:register", &o, &events)) { + if (!PyArg_ParseTuple(args, "O|O&:register", &o, ushort_converter, &events)) return NULL; - } fd = PyObject_AsFileDescriptor(o); if (fd == -1) return NULL; @@ -751,7 +769,7 @@ internal_devpoll_register(devpollObject *self, PyObject *args, int remove) } self->fds[self->n_fds].fd = fd; - self->fds[self->n_fds].events = events; + self->fds[self->n_fds].events = (signed short)events; if (++self->n_fds == self->max_n_fds) { if (devpoll_flush(self)) |