blob: 6071996a2d6088da983b1d7209319af1d0579111 [file] [log] [blame]
Guido van Rossum4f0fbf81996-06-12 04:22:53 +00001/* select - Module containing unix select(2) call.
Barry Warsawe4ac0aa1996-12-12 00:04:35 +00002 Under Unix, the file descriptors are small integers.
3 Under Win32, select only exists for sockets, and sockets may
4 have any value except INVALID_SOCKET.
Guido van Rossumbcc20741998-08-04 22:53:56 +00005 Under BeOS, we suffer the same dichotomy as Win32; sockets can be anything
6 >= 0.
Guido van Rossum4f0fbf81996-06-12 04:22:53 +00007*/
Guido van Rossumed233a51992-06-23 09:07:03 +00008
Barry Warsawe4ac0aa1996-12-12 00:04:35 +00009#include "Python.h"
Christian Heimes0e9ab5f2008-03-21 23:49:44 +000010#include <structmember.h>
Guido van Rossumed233a51992-06-23 09:07:03 +000011
Ronald Oussoren32fd16e2006-04-23 12:36:23 +000012#ifdef __APPLE__
13 /* Perform runtime testing for a broken poll on OSX to make it easier
14 * to use the same binary on multiple releases of the OS.
15 */
16#undef HAVE_BROKEN_POLL
17#endif
18
Tim Petersd92dfe02000-12-12 01:18:41 +000019/* Windows #defines FD_SETSIZE to 64 if FD_SETSIZE isn't already defined.
20 64 is too small (too many people have bumped into that limit).
21 Here we boost it.
22 Users who want even more than the boosted limit should #define
23 FD_SETSIZE higher before this; e.g., via compiler /D switch.
24*/
25#if defined(MS_WINDOWS) && !defined(FD_SETSIZE)
26#define FD_SETSIZE 512
Antoine Pitrouc83ea132010-05-09 14:46:46 +000027#endif
Tim Petersd92dfe02000-12-12 01:18:41 +000028
Andrew M. Kuchling737fbb32001-07-14 20:54:37 +000029#if defined(HAVE_POLL_H)
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +000030#include <poll.h>
Andrew M. Kuchling737fbb32001-07-14 20:54:37 +000031#elif defined(HAVE_SYS_POLL_H)
32#include <sys/poll.h>
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +000033#endif
Guido van Rossuma376cc51996-12-05 23:43:35 +000034
Guido van Rossum37273171996-12-09 18:47:43 +000035#ifdef __sgi
36/* This is missing from unistd.h */
Thomas Woutersbd4bc4e2000-07-22 23:57:55 +000037extern void bzero(void *, int);
Guido van Rossum37273171996-12-09 18:47:43 +000038#endif
39
Martin v. Löwis0e8bd7e2006-06-10 12:23:46 +000040#ifdef HAVE_SYS_TYPES_H
Guido van Rossumb6775db1994-08-01 11:34:53 +000041#include <sys/types.h>
Guido van Rossumff7e83d1999-08-27 20:39:37 +000042#endif
Guido van Rossum4f0fbf81996-06-12 04:22:53 +000043
Andrew MacIntyre7bf68332002-03-03 02:59:16 +000044#if defined(PYOS_OS2) && !defined(PYCC_GCC)
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000045#include <sys/time.h>
46#include <utils.h>
47#endif
48
Guido van Rossum6f489d91996-06-28 20:15:15 +000049#ifdef MS_WINDOWS
Kristján Valur Jónssonf6f3c4a2010-11-03 13:27:33 +000050# include <winsock2.h>
Guido van Rossum4f0fbf81996-06-12 04:22:53 +000051#else
Neal Norwitz2a30cd02006-07-10 01:18:57 +000052# define SOCKET int
53# ifdef __BEOS__
54# include <net/socket.h>
55# elif defined(__VMS)
56# include <socket.h>
57# endif
Guido van Rossumbcc20741998-08-04 22:53:56 +000058#endif
Guido van Rossumed233a51992-06-23 09:07:03 +000059
Barry Warsawe4ac0aa1996-12-12 00:04:35 +000060static PyObject *SelectError;
Guido van Rossumed233a51992-06-23 09:07:03 +000061
Barry Warsawc1cb3601996-12-12 22:16:21 +000062/* list of Python objects and their file descriptor */
63typedef struct {
Antoine Pitrouc83ea132010-05-09 14:46:46 +000064 PyObject *obj; /* owned reference */
65 SOCKET fd;
66 int sentinel; /* -1 == sentinel */
Guido van Rossum4f0fbf81996-06-12 04:22:53 +000067} pylist;
68
Barry Warsawc1cb3601996-12-12 22:16:21 +000069static void
Tim Peters4b046c22001-08-16 21:59:46 +000070reap_obj(pylist fd2obj[FD_SETSIZE + 1])
Barry Warsawc1cb3601996-12-12 22:16:21 +000071{
Antoine Pitrouc83ea132010-05-09 14:46:46 +000072 int i;
73 for (i = 0; i < FD_SETSIZE + 1 && fd2obj[i].sentinel >= 0; i++) {
74 Py_XDECREF(fd2obj[i].obj);
75 fd2obj[i].obj = NULL;
76 }
77 fd2obj[0].sentinel = -1;
Barry Warsawc1cb3601996-12-12 22:16:21 +000078}
79
80
Barry Warsawe4ac0aa1996-12-12 00:04:35 +000081/* returns -1 and sets the Python exception if an error occurred, otherwise
82 returns a number >= 0
83*/
Guido van Rossum4f0fbf81996-06-12 04:22:53 +000084static int
Brett Cannon62dba4c2003-09-10 19:37:42 +000085seq2set(PyObject *seq, fd_set *set, pylist fd2obj[FD_SETSIZE + 1])
Guido van Rossumed233a51992-06-23 09:07:03 +000086{
Antoine Pitrouc83ea132010-05-09 14:46:46 +000087 int i;
88 int max = -1;
89 int index = 0;
Antoine Pitrouc83ea132010-05-09 14:46:46 +000090 PyObject* fast_seq = NULL;
91 PyObject* o = NULL;
Guido van Rossum07432c01995-03-29 16:47:45 +000092
Antoine Pitrouc83ea132010-05-09 14:46:46 +000093 fd2obj[0].obj = (PyObject*)0; /* set list to zero size */
94 FD_ZERO(set);
Barry Warsawc1cb3601996-12-12 22:16:21 +000095
Antoine Pitrouc83ea132010-05-09 14:46:46 +000096 fast_seq = PySequence_Fast(seq, "arguments 1-3 must be sequences");
97 if (!fast_seq)
98 return -1;
99
Antoine Pitrou0552fc22012-11-01 20:13:54 +0100100 for (i = 0; i < PySequence_Fast_GET_SIZE(fast_seq); i++) {
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000101 SOCKET v;
102
103 /* any intervening fileno() calls could decr this refcnt */
104 if (!(o = PySequence_Fast_GET_ITEM(fast_seq, i)))
Brett Cannon62dba4c2003-09-10 19:37:42 +0000105 return -1;
106
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000107 Py_INCREF(o);
108 v = PyObject_AsFileDescriptor( o );
109 if (v == -1) goto finally;
Barry Warsawc1cb3601996-12-12 22:16:21 +0000110
Guido van Rossum947a0fa2000-01-14 16:33:09 +0000111#if defined(_MSC_VER)
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000112 max = 0; /* not used for Win32 */
Barry Warsawc1cb3601996-12-12 22:16:21 +0000113#else /* !_MSC_VER */
Charles-François Natalifda7b372011-08-28 16:22:33 +0200114 if (!_PyIsSelectable_fd(v)) {
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000115 PyErr_SetString(PyExc_ValueError,
116 "filedescriptor out of range in select()");
117 goto finally;
118 }
119 if (v > max)
120 max = v;
Barry Warsawc1cb3601996-12-12 22:16:21 +0000121#endif /* _MSC_VER */
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000122 FD_SET(v, set);
Barry Warsawc1cb3601996-12-12 22:16:21 +0000123
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000124 /* add object and its file descriptor to the list */
125 if (index >= FD_SETSIZE) {
126 PyErr_SetString(PyExc_ValueError,
127 "too many file descriptors in select()");
128 goto finally;
129 }
130 fd2obj[index].obj = o;
131 fd2obj[index].fd = v;
132 fd2obj[index].sentinel = 0;
133 fd2obj[++index].sentinel = -1;
134 }
135 Py_DECREF(fast_seq);
136 return max+1;
Barry Warsawc1cb3601996-12-12 22:16:21 +0000137
138 finally:
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000139 Py_XDECREF(o);
140 Py_DECREF(fast_seq);
141 return -1;
Guido van Rossumed233a51992-06-23 09:07:03 +0000142}
143
Barry Warsawe4ac0aa1996-12-12 00:04:35 +0000144/* returns NULL and sets the Python exception if an error occurred */
145static PyObject *
Tim Peters4b046c22001-08-16 21:59:46 +0000146set2list(fd_set *set, pylist fd2obj[FD_SETSIZE + 1])
Guido van Rossumed233a51992-06-23 09:07:03 +0000147{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000148 int i, j, count=0;
149 PyObject *list, *o;
150 SOCKET fd;
Guido van Rossumed233a51992-06-23 09:07:03 +0000151
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000152 for (j = 0; fd2obj[j].sentinel >= 0; j++) {
153 if (FD_ISSET(fd2obj[j].fd, set))
154 count++;
155 }
156 list = PyList_New(count);
157 if (!list)
158 return NULL;
Barry Warsawe4ac0aa1996-12-12 00:04:35 +0000159
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000160 i = 0;
161 for (j = 0; fd2obj[j].sentinel >= 0; j++) {
162 fd = fd2obj[j].fd;
163 if (FD_ISSET(fd, set)) {
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000164 o = fd2obj[j].obj;
165 fd2obj[j].obj = NULL;
166 /* transfer ownership */
167 if (PyList_SetItem(list, i, o) < 0)
168 goto finally;
Barry Warsawc1cb3601996-12-12 22:16:21 +0000169
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000170 i++;
171 }
172 }
173 return list;
Barry Warsawc1cb3601996-12-12 22:16:21 +0000174 finally:
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000175 Py_DECREF(list);
176 return NULL;
Guido van Rossumed233a51992-06-23 09:07:03 +0000177}
Barry Warsawc1cb3601996-12-12 22:16:21 +0000178
Barry Warsawb44740f2001-08-16 16:52:59 +0000179#undef SELECT_USES_HEAP
180#if FD_SETSIZE > 1024
181#define SELECT_USES_HEAP
182#endif /* FD_SETSIZE > 1024 */
183
Barry Warsawe4ac0aa1996-12-12 00:04:35 +0000184static PyObject *
Peter Schneider-Kamp41c36ff2000-07-10 12:29:26 +0000185select_select(PyObject *self, PyObject *args)
Guido van Rossumed233a51992-06-23 09:07:03 +0000186{
Barry Warsawb44740f2001-08-16 16:52:59 +0000187#ifdef SELECT_USES_HEAP
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000188 pylist *rfd2obj, *wfd2obj, *efd2obj;
Barry Warsawb44740f2001-08-16 16:52:59 +0000189#else /* !SELECT_USES_HEAP */
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000190 /* XXX: All this should probably be implemented as follows:
191 * - find the highest descriptor we're interested in
192 * - add one
193 * - that's the size
194 * See: Stevens, APitUE, $12.5.1
195 */
196 pylist rfd2obj[FD_SETSIZE + 1];
197 pylist wfd2obj[FD_SETSIZE + 1];
198 pylist efd2obj[FD_SETSIZE + 1];
Barry Warsawb44740f2001-08-16 16:52:59 +0000199#endif /* SELECT_USES_HEAP */
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000200 PyObject *ifdlist, *ofdlist, *efdlist;
201 PyObject *ret = NULL;
202 PyObject *tout = Py_None;
203 fd_set ifdset, ofdset, efdset;
204 double timeout;
205 struct timeval tv, *tvp;
206 long seconds;
207 int imax, omax, emax, max;
208 int n;
Guido van Rossumed233a51992-06-23 09:07:03 +0000209
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000210 /* convert arguments */
211 if (!PyArg_UnpackTuple(args, "select", 3, 4,
212 &ifdlist, &ofdlist, &efdlist, &tout))
213 return NULL;
Guido van Rossumed233a51992-06-23 09:07:03 +0000214
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000215 if (tout == Py_None)
216 tvp = (struct timeval *)0;
217 else if (!PyNumber_Check(tout)) {
218 PyErr_SetString(PyExc_TypeError,
219 "timeout must be a float or None");
220 return NULL;
221 }
222 else {
223 timeout = PyFloat_AsDouble(tout);
224 if (timeout == -1 && PyErr_Occurred())
225 return NULL;
226 if (timeout > (double)LONG_MAX) {
227 PyErr_SetString(PyExc_OverflowError,
228 "timeout period too long");
229 return NULL;
230 }
231 seconds = (long)timeout;
232 timeout = timeout - (double)seconds;
233 tv.tv_sec = seconds;
234 tv.tv_usec = (long)(timeout * 1E6);
235 tvp = &tv;
236 }
Guido van Rossumed233a51992-06-23 09:07:03 +0000237
Guido van Rossumed233a51992-06-23 09:07:03 +0000238
Barry Warsawb44740f2001-08-16 16:52:59 +0000239#ifdef SELECT_USES_HEAP
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000240 /* Allocate memory for the lists */
241 rfd2obj = PyMem_NEW(pylist, FD_SETSIZE + 1);
242 wfd2obj = PyMem_NEW(pylist, FD_SETSIZE + 1);
243 efd2obj = PyMem_NEW(pylist, FD_SETSIZE + 1);
244 if (rfd2obj == NULL || wfd2obj == NULL || efd2obj == NULL) {
245 if (rfd2obj) PyMem_DEL(rfd2obj);
246 if (wfd2obj) PyMem_DEL(wfd2obj);
247 if (efd2obj) PyMem_DEL(efd2obj);
248 return PyErr_NoMemory();
249 }
Barry Warsawb44740f2001-08-16 16:52:59 +0000250#endif /* SELECT_USES_HEAP */
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000251 /* Convert sequences to fd_sets, and get maximum fd number
252 * propagates the Python exception set in seq2set()
253 */
254 rfd2obj[0].sentinel = -1;
255 wfd2obj[0].sentinel = -1;
256 efd2obj[0].sentinel = -1;
257 if ((imax=seq2set(ifdlist, &ifdset, rfd2obj)) < 0)
258 goto finally;
259 if ((omax=seq2set(ofdlist, &ofdset, wfd2obj)) < 0)
260 goto finally;
261 if ((emax=seq2set(efdlist, &efdset, efd2obj)) < 0)
262 goto finally;
263 max = imax;
264 if (omax > max) max = omax;
265 if (emax > max) max = emax;
Guido van Rossumed233a51992-06-23 09:07:03 +0000266
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000267 Py_BEGIN_ALLOW_THREADS
268 n = select(max, &ifdset, &ofdset, &efdset, tvp);
269 Py_END_ALLOW_THREADS
Guido van Rossumed233a51992-06-23 09:07:03 +0000270
Thomas Heller106f4c72002-09-24 16:51:00 +0000271#ifdef MS_WINDOWS
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000272 if (n == SOCKET_ERROR) {
273 PyErr_SetExcFromWindowsErr(SelectError, WSAGetLastError());
274 }
Thomas Heller106f4c72002-09-24 16:51:00 +0000275#else
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000276 if (n < 0) {
277 PyErr_SetFromErrno(SelectError);
278 }
Thomas Heller106f4c72002-09-24 16:51:00 +0000279#endif
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000280 else {
281 /* any of these three calls can raise an exception. it's more
282 convenient to test for this after all three calls... but
283 is that acceptable?
284 */
285 ifdlist = set2list(&ifdset, rfd2obj);
286 ofdlist = set2list(&ofdset, wfd2obj);
287 efdlist = set2list(&efdset, efd2obj);
288 if (PyErr_Occurred())
289 ret = NULL;
290 else
291 ret = PyTuple_Pack(3, ifdlist, ofdlist, efdlist);
Barry Warsawe4ac0aa1996-12-12 00:04:35 +0000292
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000293 Py_DECREF(ifdlist);
294 Py_DECREF(ofdlist);
295 Py_DECREF(efdlist);
296 }
297
Barry Warsawc1cb3601996-12-12 22:16:21 +0000298 finally:
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000299 reap_obj(rfd2obj);
300 reap_obj(wfd2obj);
301 reap_obj(efd2obj);
Barry Warsawb44740f2001-08-16 16:52:59 +0000302#ifdef SELECT_USES_HEAP
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000303 PyMem_DEL(rfd2obj);
304 PyMem_DEL(wfd2obj);
305 PyMem_DEL(efd2obj);
Barry Warsawb44740f2001-08-16 16:52:59 +0000306#endif /* SELECT_USES_HEAP */
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000307 return ret;
Guido van Rossumed233a51992-06-23 09:07:03 +0000308}
309
Nicholas Bastine62c5c82004-03-21 23:45:42 +0000310#if defined(HAVE_POLL) && !defined(HAVE_BROKEN_POLL)
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000311/*
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000312 * poll() support
313 */
314
315typedef struct {
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000316 PyObject_HEAD
317 PyObject *dict;
318 int ufd_uptodate;
319 int ufd_len;
320 struct pollfd *ufds;
Serhiy Storchakac3603892013-08-20 20:38:21 +0300321 int poll_running;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000322} pollObject;
323
Jeremy Hylton938ace62002-07-17 16:30:39 +0000324static PyTypeObject poll_Type;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000325
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000326/* Update the malloc'ed array of pollfds to match the dictionary
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000327 contained within a pollObject. Return 1 on success, 0 on an error.
328*/
329
330static int
331update_ufd_array(pollObject *self)
332{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000333 Py_ssize_t i, pos;
334 PyObject *key, *value;
335 struct pollfd *old_ufds = self->ufds;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000336
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000337 self->ufd_len = PyDict_Size(self->dict);
338 PyMem_RESIZE(self->ufds, struct pollfd, self->ufd_len);
339 if (self->ufds == NULL) {
340 self->ufds = old_ufds;
341 PyErr_NoMemory();
342 return 0;
343 }
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000344
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000345 i = pos = 0;
346 while (PyDict_Next(self->dict, &pos, &key, &value)) {
Serhiy Storchaka74f49ab2013-01-19 12:55:39 +0200347 assert(i < self->ufd_len);
348 /* Never overflow */
349 self->ufds[i].fd = (int)PyInt_AsLong(key);
Serhiy Storchakaa92cc912013-12-14 19:11:04 +0200350 self->ufds[i].events = (short)(unsigned short)PyInt_AsLong(value);
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000351 i++;
352 }
Serhiy Storchaka74f49ab2013-01-19 12:55:39 +0200353 assert(i == self->ufd_len);
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000354 self->ufd_uptodate = 1;
355 return 1;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000356}
357
Serhiy Storchakaa92cc912013-12-14 19:11:04 +0200358static int
359ushort_converter(PyObject *obj, void *ptr)
360{
361 unsigned long uval;
362
363 uval = PyLong_AsUnsignedLong(obj);
364 if (uval == (unsigned long)-1 && PyErr_Occurred())
365 return 0;
366 if (uval > USHRT_MAX) {
367 PyErr_SetString(PyExc_OverflowError,
368 "Python int too large for C unsigned short");
369 return 0;
370 }
371
372 *(unsigned short *)ptr = Py_SAFE_DOWNCAST(uval, unsigned long, unsigned short);
373 return 1;
374}
375
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000376PyDoc_STRVAR(poll_register_doc,
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000377"register(fd [, eventmask] ) -> None\n\n\
378Register a file descriptor with the polling object.\n\
Barry Warsaw2f704552001-08-16 16:55:10 +0000379fd -- either an integer, or an object with a fileno() method returning an\n\
380 int.\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000381events -- an optional bitmask describing the type of events to check for");
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000382
383static PyObject *
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000384poll_register(pollObject *self, PyObject *args)
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000385{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000386 PyObject *o, *key, *value;
Serhiy Storchakaa92cc912013-12-14 19:11:04 +0200387 int fd;
388 unsigned short events = POLLIN | POLLPRI | POLLOUT;
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000389 int err;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000390
Serhiy Storchakaa92cc912013-12-14 19:11:04 +0200391 if (!PyArg_ParseTuple(args, "O|O&:register", &o, ushort_converter, &events))
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000392 return NULL;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000393
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000394 fd = PyObject_AsFileDescriptor(o);
395 if (fd == -1) return NULL;
Guido van Rossuma0dfc852001-10-25 20:18:35 +0000396
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000397 /* Add entry to the internal dictionary: the key is the
398 file descriptor, and the value is the event mask. */
399 key = PyInt_FromLong(fd);
400 if (key == NULL)
401 return NULL;
402 value = PyInt_FromLong(events);
403 if (value == NULL) {
404 Py_DECREF(key);
405 return NULL;
406 }
407 err = PyDict_SetItem(self->dict, key, value);
408 Py_DECREF(key);
409 Py_DECREF(value);
410 if (err < 0)
411 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000412
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000413 self->ufd_uptodate = 0;
414
415 Py_INCREF(Py_None);
416 return Py_None;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000417}
418
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000419PyDoc_STRVAR(poll_modify_doc,
420"modify(fd, eventmask) -> None\n\n\
Andrew M. Kuchlinga8c3f2b2008-03-26 00:16:50 +0000421Modify an already registered file descriptor.\n\
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000422fd -- either an integer, or an object with a fileno() method returning an\n\
423 int.\n\
424events -- an optional bitmask describing the type of events to check for");
425
426static PyObject *
427poll_modify(pollObject *self, PyObject *args)
428{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000429 PyObject *o, *key, *value;
Serhiy Storchakaa92cc912013-12-14 19:11:04 +0200430 int fd;
431 unsigned short events;
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000432 int err;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000433
Serhiy Storchakaa92cc912013-12-14 19:11:04 +0200434 if (!PyArg_ParseTuple(args, "OO&:modify", &o, ushort_converter, &events))
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000435 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000436
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000437 fd = PyObject_AsFileDescriptor(o);
438 if (fd == -1) return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000439
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000440 /* Modify registered fd */
441 key = PyInt_FromLong(fd);
442 if (key == NULL)
443 return NULL;
444 if (PyDict_GetItem(self->dict, key) == NULL) {
445 errno = ENOENT;
446 PyErr_SetFromErrno(PyExc_IOError);
447 return NULL;
448 }
449 value = PyInt_FromLong(events);
450 if (value == NULL) {
451 Py_DECREF(key);
452 return NULL;
453 }
454 err = PyDict_SetItem(self->dict, key, value);
455 Py_DECREF(key);
456 Py_DECREF(value);
457 if (err < 0)
458 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000459
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000460 self->ufd_uptodate = 0;
461
462 Py_INCREF(Py_None);
463 return Py_None;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000464}
465
466
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000467PyDoc_STRVAR(poll_unregister_doc,
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000468"unregister(fd) -> None\n\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000469Remove a file descriptor being tracked by the polling object.");
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000470
471static PyObject *
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000472poll_unregister(pollObject *self, PyObject *o)
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000473{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000474 PyObject *key;
475 int fd;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000476
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000477 fd = PyObject_AsFileDescriptor( o );
478 if (fd == -1)
479 return NULL;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000480
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000481 /* Check whether the fd is already in the array */
482 key = PyInt_FromLong(fd);
483 if (key == NULL)
484 return NULL;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000485
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000486 if (PyDict_DelItem(self->dict, key) == -1) {
487 Py_DECREF(key);
488 /* This will simply raise the KeyError set by PyDict_DelItem
489 if the file descriptor isn't registered. */
490 return NULL;
491 }
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000492
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000493 Py_DECREF(key);
494 self->ufd_uptodate = 0;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000495
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000496 Py_INCREF(Py_None);
497 return Py_None;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000498}
499
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000500PyDoc_STRVAR(poll_poll_doc,
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000501"poll( [timeout] ) -> list of (fd, event) 2-tuples\n\n\
502Polls the set of registered file descriptors, returning a list containing \n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000503any descriptors that have events or errors to report.");
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000504
505static PyObject *
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000506poll_poll(pollObject *self, PyObject *args)
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000507{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000508 PyObject *result_list = NULL, *tout = NULL;
509 int timeout = 0, poll_result, i, j;
510 PyObject *value = NULL, *num = NULL;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000511
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000512 if (!PyArg_UnpackTuple(args, "poll", 0, 1, &tout)) {
513 return NULL;
514 }
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000515
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000516 /* Check values for timeout */
517 if (tout == NULL || tout == Py_None)
518 timeout = -1;
519 else if (!PyNumber_Check(tout)) {
520 PyErr_SetString(PyExc_TypeError,
521 "timeout must be an integer or None");
522 return NULL;
523 }
524 else {
525 tout = PyNumber_Int(tout);
526 if (!tout)
527 return NULL;
Serhiy Storchaka74f49ab2013-01-19 12:55:39 +0200528 timeout = _PyInt_AsInt(tout);
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000529 Py_DECREF(tout);
530 if (timeout == -1 && PyErr_Occurred())
531 return NULL;
532 }
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000533
Serhiy Storchakac3603892013-08-20 20:38:21 +0300534 /* Avoid concurrent poll() invocation, issue 8865 */
535 if (self->poll_running) {
536 PyErr_SetString(PyExc_RuntimeError,
537 "concurrent poll() invocation");
538 return NULL;
539 }
540
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000541 /* Ensure the ufd array is up to date */
542 if (!self->ufd_uptodate)
543 if (update_ufd_array(self) == 0)
544 return NULL;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000545
Serhiy Storchakac3603892013-08-20 20:38:21 +0300546 self->poll_running = 1;
547
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000548 /* call poll() */
549 Py_BEGIN_ALLOW_THREADS
550 poll_result = poll(self->ufds, self->ufd_len, timeout);
551 Py_END_ALLOW_THREADS
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000552
Serhiy Storchakac3603892013-08-20 20:38:21 +0300553 self->poll_running = 0;
554
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000555 if (poll_result < 0) {
556 PyErr_SetFromErrno(SelectError);
557 return NULL;
558 }
559
560 /* build the result list */
561
562 result_list = PyList_New(poll_result);
563 if (!result_list)
564 return NULL;
565 else {
566 for (i = 0, j = 0; j < poll_result; j++) {
567 /* skip to the next fired descriptor */
568 while (!self->ufds[i].revents) {
569 i++;
570 }
571 /* if we hit a NULL return, set value to NULL
572 and break out of loop; code at end will
573 clean up result_list */
574 value = PyTuple_New(2);
575 if (value == NULL)
576 goto error;
577 num = PyInt_FromLong(self->ufds[i].fd);
578 if (num == NULL) {
579 Py_DECREF(value);
580 goto error;
581 }
582 PyTuple_SET_ITEM(value, 0, num);
583
584 /* The &0xffff is a workaround for AIX. 'revents'
585 is a 16-bit short, and IBM assigned POLLNVAL
586 to be 0x8000, so the conversion to int results
587 in a negative number. See SF bug #923315. */
588 num = PyInt_FromLong(self->ufds[i].revents & 0xffff);
589 if (num == NULL) {
590 Py_DECREF(value);
591 goto error;
592 }
593 PyTuple_SET_ITEM(value, 1, num);
594 if ((PyList_SetItem(result_list, j, value)) == -1) {
595 Py_DECREF(value);
596 goto error;
597 }
598 i++;
599 }
600 }
601 return result_list;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000602
603 error:
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000604 Py_DECREF(result_list);
605 return NULL;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000606}
607
608static PyMethodDef poll_methods[] = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000609 {"register", (PyCFunction)poll_register,
610 METH_VARARGS, poll_register_doc},
611 {"modify", (PyCFunction)poll_modify,
612 METH_VARARGS, poll_modify_doc},
613 {"unregister", (PyCFunction)poll_unregister,
614 METH_O, poll_unregister_doc},
615 {"poll", (PyCFunction)poll_poll,
616 METH_VARARGS, poll_poll_doc},
617 {NULL, NULL} /* sentinel */
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000618};
619
620static pollObject *
Fred Drake8ce159a2000-08-31 05:18:54 +0000621newPollObject(void)
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000622{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000623 pollObject *self;
624 self = PyObject_New(pollObject, &poll_Type);
625 if (self == NULL)
626 return NULL;
627 /* ufd_uptodate is a Boolean, denoting whether the
628 array pointed to by ufds matches the contents of the dictionary. */
629 self->ufd_uptodate = 0;
630 self->ufds = NULL;
Serhiy Storchakac3603892013-08-20 20:38:21 +0300631 self->poll_running = 0;
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000632 self->dict = PyDict_New();
633 if (self->dict == NULL) {
634 Py_DECREF(self);
635 return NULL;
636 }
637 return self;
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000638}
639
640static void
641poll_dealloc(pollObject *self)
642{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000643 if (self->ufds != NULL)
644 PyMem_DEL(self->ufds);
645 Py_XDECREF(self->dict);
646 PyObject_Del(self);
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000647}
648
649static PyObject *
650poll_getattr(pollObject *self, char *name)
651{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000652 return Py_FindMethod(poll_methods, (PyObject *)self, name);
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000653}
654
Tim Peters0c322792002-07-17 16:49:03 +0000655static PyTypeObject poll_Type = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000656 /* The ob_type field must be initialized in the module init function
657 * to be portable to Windows without using C++. */
658 PyVarObject_HEAD_INIT(NULL, 0)
659 "select.poll", /*tp_name*/
660 sizeof(pollObject), /*tp_basicsize*/
661 0, /*tp_itemsize*/
662 /* methods */
663 (destructor)poll_dealloc, /*tp_dealloc*/
664 0, /*tp_print*/
665 (getattrfunc)poll_getattr, /*tp_getattr*/
666 0, /*tp_setattr*/
667 0, /*tp_compare*/
668 0, /*tp_repr*/
669 0, /*tp_as_number*/
670 0, /*tp_as_sequence*/
671 0, /*tp_as_mapping*/
672 0, /*tp_hash*/
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000673};
674
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000675PyDoc_STRVAR(poll_doc,
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000676"Returns a polling object, which supports registering and\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000677unregistering file descriptors, and then polling them for I/O events.");
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000678
679static PyObject *
Georg Brandl96a8c392006-05-29 21:04:52 +0000680select_poll(PyObject *self, PyObject *unused)
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000681{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000682 return (PyObject *)newPollObject();
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000683}
Ronald Oussoren32fd16e2006-04-23 12:36:23 +0000684
685#ifdef __APPLE__
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000686/*
Ronald Oussoren32fd16e2006-04-23 12:36:23 +0000687 * On some systems poll() sets errno on invalid file descriptors. We test
688 * for this at runtime because this bug may be fixed or introduced between
689 * OS releases.
690 */
691static int select_have_broken_poll(void)
692{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000693 int poll_test;
694 int filedes[2];
Ronald Oussoren32fd16e2006-04-23 12:36:23 +0000695
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000696 struct pollfd poll_struct = { 0, POLLIN|POLLPRI|POLLOUT, 0 };
Ronald Oussoren32fd16e2006-04-23 12:36:23 +0000697
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000698 /* Create a file descriptor to make invalid */
699 if (pipe(filedes) < 0) {
700 return 1;
701 }
702 poll_struct.fd = filedes[0];
703 close(filedes[0]);
704 close(filedes[1]);
705 poll_test = poll(&poll_struct, 1, 0);
706 if (poll_test < 0) {
707 return 1;
708 } else if (poll_test == 0 && poll_struct.revents != POLLNVAL) {
709 return 1;
710 }
711 return 0;
Ronald Oussoren32fd16e2006-04-23 12:36:23 +0000712}
713#endif /* __APPLE__ */
714
715#endif /* HAVE_POLL */
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +0000716
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000717#ifdef HAVE_EPOLL
718/* **************************************************************************
719 * epoll interface for Linux 2.6
720 *
721 * Written by Christian Heimes
722 * Inspired by Twisted's _epoll.pyx and select.poll()
723 */
724
725#ifdef HAVE_SYS_EPOLL_H
726#include <sys/epoll.h>
727#endif
728
729typedef struct {
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000730 PyObject_HEAD
731 SOCKET epfd; /* epoll control file descriptor */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000732} pyEpoll_Object;
733
734static PyTypeObject pyEpoll_Type;
735#define pyepoll_CHECK(op) (PyObject_TypeCheck((op), &pyEpoll_Type))
736
737static PyObject *
738pyepoll_err_closed(void)
739{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000740 PyErr_SetString(PyExc_ValueError, "I/O operation on closed epoll fd");
741 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000742}
743
744static int
745pyepoll_internal_close(pyEpoll_Object *self)
746{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000747 int save_errno = 0;
748 if (self->epfd >= 0) {
749 int epfd = self->epfd;
750 self->epfd = -1;
751 Py_BEGIN_ALLOW_THREADS
752 if (close(epfd) < 0)
753 save_errno = errno;
754 Py_END_ALLOW_THREADS
755 }
756 return save_errno;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000757}
758
759static PyObject *
760newPyEpoll_Object(PyTypeObject *type, int sizehint, SOCKET fd)
761{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000762 pyEpoll_Object *self;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000763
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000764 if (sizehint == -1) {
765 sizehint = FD_SETSIZE-1;
766 }
767 else if (sizehint < 1) {
768 PyErr_Format(PyExc_ValueError,
769 "sizehint must be greater zero, got %d",
770 sizehint);
771 return NULL;
772 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000773
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000774 assert(type != NULL && type->tp_alloc != NULL);
775 self = (pyEpoll_Object *) type->tp_alloc(type, 0);
776 if (self == NULL)
777 return NULL;
778
779 if (fd == -1) {
780 Py_BEGIN_ALLOW_THREADS
781 self->epfd = epoll_create(sizehint);
782 Py_END_ALLOW_THREADS
783 }
784 else {
785 self->epfd = fd;
786 }
787 if (self->epfd < 0) {
788 Py_DECREF(self);
789 PyErr_SetFromErrno(PyExc_IOError);
790 return NULL;
791 }
792 return (PyObject *)self;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000793}
794
795
796static PyObject *
797pyepoll_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
798{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000799 int sizehint = -1;
800 static char *kwlist[] = {"sizehint", NULL};
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000801
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000802 if (!PyArg_ParseTupleAndKeywords(args, kwds, "|i:epoll", kwlist,
803 &sizehint))
804 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000805
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000806 return newPyEpoll_Object(type, sizehint, -1);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000807}
808
809
810static void
811pyepoll_dealloc(pyEpoll_Object *self)
812{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000813 (void)pyepoll_internal_close(self);
814 Py_TYPE(self)->tp_free(self);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000815}
816
817static PyObject*
818pyepoll_close(pyEpoll_Object *self)
819{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000820 errno = pyepoll_internal_close(self);
821 if (errno < 0) {
822 PyErr_SetFromErrno(PyExc_IOError);
823 return NULL;
824 }
825 Py_RETURN_NONE;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000826}
827
828PyDoc_STRVAR(pyepoll_close_doc,
829"close() -> None\n\
830\n\
831Close the epoll control file descriptor. Further operations on the epoll\n\
832object will raise an exception.");
833
834static PyObject*
835pyepoll_get_closed(pyEpoll_Object *self)
836{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000837 if (self->epfd < 0)
838 Py_RETURN_TRUE;
839 else
840 Py_RETURN_FALSE;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000841}
842
843static PyObject*
844pyepoll_fileno(pyEpoll_Object *self)
845{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000846 if (self->epfd < 0)
847 return pyepoll_err_closed();
848 return PyInt_FromLong(self->epfd);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000849}
850
851PyDoc_STRVAR(pyepoll_fileno_doc,
852"fileno() -> int\n\
853\n\
854Return the epoll control file descriptor.");
855
856static PyObject*
857pyepoll_fromfd(PyObject *cls, PyObject *args)
858{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000859 SOCKET fd;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000860
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000861 if (!PyArg_ParseTuple(args, "i:fromfd", &fd))
862 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000863
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000864 return newPyEpoll_Object((PyTypeObject*)cls, -1, fd);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000865}
866
867PyDoc_STRVAR(pyepoll_fromfd_doc,
868"fromfd(fd) -> epoll\n\
869\n\
870Create an epoll object from a given control fd.");
871
872static PyObject *
873pyepoll_internal_ctl(int epfd, int op, PyObject *pfd, unsigned int events)
874{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000875 struct epoll_event ev;
876 int result;
877 int fd;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000878
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000879 if (epfd < 0)
880 return pyepoll_err_closed();
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000881
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000882 fd = PyObject_AsFileDescriptor(pfd);
883 if (fd == -1) {
884 return NULL;
885 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000886
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000887 switch(op) {
888 case EPOLL_CTL_ADD:
889 case EPOLL_CTL_MOD:
890 ev.events = events;
891 ev.data.fd = fd;
892 Py_BEGIN_ALLOW_THREADS
893 result = epoll_ctl(epfd, op, fd, &ev);
894 Py_END_ALLOW_THREADS
895 break;
896 case EPOLL_CTL_DEL:
897 /* In kernel versions before 2.6.9, the EPOLL_CTL_DEL
898 * operation required a non-NULL pointer in event, even
899 * though this argument is ignored. */
900 Py_BEGIN_ALLOW_THREADS
901 result = epoll_ctl(epfd, op, fd, &ev);
902 if (errno == EBADF) {
903 /* fd already closed */
904 result = 0;
905 errno = 0;
906 }
907 Py_END_ALLOW_THREADS
908 break;
909 default:
910 result = -1;
911 errno = EINVAL;
912 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000913
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000914 if (result < 0) {
915 PyErr_SetFromErrno(PyExc_IOError);
916 return NULL;
917 }
918 Py_RETURN_NONE;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000919}
920
921static PyObject *
922pyepoll_register(pyEpoll_Object *self, PyObject *args, PyObject *kwds)
923{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000924 PyObject *pfd;
925 unsigned int events = EPOLLIN | EPOLLOUT | EPOLLPRI;
926 static char *kwlist[] = {"fd", "eventmask", NULL};
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000927
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000928 if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|I:register", kwlist,
929 &pfd, &events)) {
930 return NULL;
931 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000932
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000933 return pyepoll_internal_ctl(self->epfd, EPOLL_CTL_ADD, pfd, events);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000934}
935
936PyDoc_STRVAR(pyepoll_register_doc,
Georg Brandl7d4bfb32010-08-02 21:44:25 +0000937"register(fd[, eventmask]) -> None\n\
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000938\n\
Senthil Kumaran2bd91002011-06-26 23:50:35 -0700939Registers a new fd or raises an IOError if the fd is already registered.\n\
Andrew M. Kuchlinga8c3f2b2008-03-26 00:16:50 +0000940fd is the target file descriptor of the operation.\n\
941events is a bit set composed of the various EPOLL constants; the default\n\
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000942is EPOLL_IN | EPOLL_OUT | EPOLL_PRI.\n\
943\n\
944The epoll interface supports all file descriptors that support poll.");
945
946static PyObject *
947pyepoll_modify(pyEpoll_Object *self, PyObject *args, PyObject *kwds)
948{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000949 PyObject *pfd;
950 unsigned int events;
951 static char *kwlist[] = {"fd", "eventmask", NULL};
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000952
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000953 if (!PyArg_ParseTupleAndKeywords(args, kwds, "OI:modify", kwlist,
954 &pfd, &events)) {
955 return NULL;
956 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000957
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000958 return pyepoll_internal_ctl(self->epfd, EPOLL_CTL_MOD, pfd, events);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000959}
960
961PyDoc_STRVAR(pyepoll_modify_doc,
962"modify(fd, eventmask) -> None\n\
963\n\
964fd is the target file descriptor of the operation\n\
965events is a bit set composed of the various EPOLL constants");
966
967static PyObject *
968pyepoll_unregister(pyEpoll_Object *self, PyObject *args, PyObject *kwds)
969{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000970 PyObject *pfd;
971 static char *kwlist[] = {"fd", NULL};
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000972
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000973 if (!PyArg_ParseTupleAndKeywords(args, kwds, "O:unregister", kwlist,
974 &pfd)) {
975 return NULL;
976 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000977
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000978 return pyepoll_internal_ctl(self->epfd, EPOLL_CTL_DEL, pfd, 0);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000979}
980
981PyDoc_STRVAR(pyepoll_unregister_doc,
982"unregister(fd) -> None\n\
983\n\
984fd is the target file descriptor of the operation.");
985
986static PyObject *
987pyepoll_poll(pyEpoll_Object *self, PyObject *args, PyObject *kwds)
988{
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000989 double dtimeout = -1.;
990 int timeout;
991 int maxevents = -1;
992 int nfds, i;
993 PyObject *elist = NULL, *etuple = NULL;
994 struct epoll_event *evs = NULL;
995 static char *kwlist[] = {"timeout", "maxevents", NULL};
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000996
Antoine Pitrouc83ea132010-05-09 14:46:46 +0000997 if (self->epfd < 0)
998 return pyepoll_err_closed();
Christian Heimes0e9ab5f2008-03-21 23:49:44 +0000999
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001000 if (!PyArg_ParseTupleAndKeywords(args, kwds, "|di:poll", kwlist,
1001 &dtimeout, &maxevents)) {
1002 return NULL;
1003 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001004
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001005 if (dtimeout < 0) {
1006 timeout = -1;
1007 }
1008 else if (dtimeout * 1000.0 > INT_MAX) {
1009 PyErr_SetString(PyExc_OverflowError,
1010 "timeout is too large");
1011 return NULL;
1012 }
1013 else {
1014 timeout = (int)(dtimeout * 1000.0);
1015 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001016
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001017 if (maxevents == -1) {
1018 maxevents = FD_SETSIZE-1;
1019 }
1020 else if (maxevents < 1) {
1021 PyErr_Format(PyExc_ValueError,
1022 "maxevents must be greater than 0, got %d",
1023 maxevents);
1024 return NULL;
1025 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001026
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001027 evs = PyMem_New(struct epoll_event, maxevents);
1028 if (evs == NULL) {
1029 Py_DECREF(self);
1030 PyErr_NoMemory();
1031 return NULL;
1032 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001033
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001034 Py_BEGIN_ALLOW_THREADS
1035 nfds = epoll_wait(self->epfd, evs, maxevents, timeout);
1036 Py_END_ALLOW_THREADS
1037 if (nfds < 0) {
1038 PyErr_SetFromErrno(PyExc_IOError);
1039 goto error;
1040 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001041
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001042 elist = PyList_New(nfds);
1043 if (elist == NULL) {
1044 goto error;
1045 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001046
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001047 for (i = 0; i < nfds; i++) {
1048 etuple = Py_BuildValue("iI", evs[i].data.fd, evs[i].events);
1049 if (etuple == NULL) {
1050 Py_CLEAR(elist);
1051 goto error;
1052 }
1053 PyList_SET_ITEM(elist, i, etuple);
1054 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001055
Georg Brandl018a3622008-03-26 12:57:47 +00001056 error:
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001057 PyMem_Free(evs);
1058 return elist;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001059}
1060
1061PyDoc_STRVAR(pyepoll_poll_doc,
1062"poll([timeout=-1[, maxevents=-1]]) -> [(fd, events), (...)]\n\
1063\n\
1064Wait for events on the epoll file descriptor for a maximum time of timeout\n\
1065in seconds (as float). -1 makes poll wait indefinitely.\n\
1066Up to maxevents are returned to the caller.");
1067
1068static PyMethodDef pyepoll_methods[] = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001069 {"fromfd", (PyCFunction)pyepoll_fromfd,
1070 METH_VARARGS | METH_CLASS, pyepoll_fromfd_doc},
1071 {"close", (PyCFunction)pyepoll_close, METH_NOARGS,
1072 pyepoll_close_doc},
1073 {"fileno", (PyCFunction)pyepoll_fileno, METH_NOARGS,
1074 pyepoll_fileno_doc},
1075 {"modify", (PyCFunction)pyepoll_modify,
1076 METH_VARARGS | METH_KEYWORDS, pyepoll_modify_doc},
1077 {"register", (PyCFunction)pyepoll_register,
1078 METH_VARARGS | METH_KEYWORDS, pyepoll_register_doc},
1079 {"unregister", (PyCFunction)pyepoll_unregister,
1080 METH_VARARGS | METH_KEYWORDS, pyepoll_unregister_doc},
1081 {"poll", (PyCFunction)pyepoll_poll,
1082 METH_VARARGS | METH_KEYWORDS, pyepoll_poll_doc},
1083 {NULL, NULL},
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001084};
1085
1086static PyGetSetDef pyepoll_getsetlist[] = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001087 {"closed", (getter)pyepoll_get_closed, NULL,
1088 "True if the epoll handler is closed"},
1089 {0},
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001090};
1091
1092PyDoc_STRVAR(pyepoll_doc,
1093"select.epoll([sizehint=-1])\n\
1094\n\
1095Returns an epolling object\n\
1096\n\
1097sizehint must be a positive integer or -1 for the default size. The\n\
1098sizehint is used to optimize internal data structures. It doesn't limit\n\
1099the maximum number of monitored events.");
1100
1101static PyTypeObject pyEpoll_Type = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001102 PyVarObject_HEAD_INIT(NULL, 0)
1103 "select.epoll", /* tp_name */
1104 sizeof(pyEpoll_Object), /* tp_basicsize */
1105 0, /* tp_itemsize */
1106 (destructor)pyepoll_dealloc, /* tp_dealloc */
1107 0, /* tp_print */
1108 0, /* tp_getattr */
1109 0, /* tp_setattr */
1110 0, /* tp_compare */
1111 0, /* tp_repr */
1112 0, /* tp_as_number */
1113 0, /* tp_as_sequence */
1114 0, /* tp_as_mapping */
1115 0, /* tp_hash */
1116 0, /* tp_call */
1117 0, /* tp_str */
1118 PyObject_GenericGetAttr, /* tp_getattro */
1119 0, /* tp_setattro */
1120 0, /* tp_as_buffer */
1121 Py_TPFLAGS_DEFAULT, /* tp_flags */
1122 pyepoll_doc, /* tp_doc */
1123 0, /* tp_traverse */
1124 0, /* tp_clear */
1125 0, /* tp_richcompare */
1126 0, /* tp_weaklistoffset */
1127 0, /* tp_iter */
1128 0, /* tp_iternext */
1129 pyepoll_methods, /* tp_methods */
1130 0, /* tp_members */
1131 pyepoll_getsetlist, /* tp_getset */
1132 0, /* tp_base */
1133 0, /* tp_dict */
1134 0, /* tp_descr_get */
1135 0, /* tp_descr_set */
1136 0, /* tp_dictoffset */
1137 0, /* tp_init */
1138 0, /* tp_alloc */
1139 pyepoll_new, /* tp_new */
1140 0, /* tp_free */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001141};
1142
1143#endif /* HAVE_EPOLL */
1144
1145#ifdef HAVE_KQUEUE
1146/* **************************************************************************
1147 * kqueue interface for BSD
1148 *
1149 * Copyright (c) 2000 Doug White, 2006 James Knight, 2007 Christian Heimes
1150 * All rights reserved.
1151 *
1152 * Redistribution and use in source and binary forms, with or without
1153 * modification, are permitted provided that the following conditions
1154 * are met:
1155 * 1. Redistributions of source code must retain the above copyright
1156 * notice, this list of conditions and the following disclaimer.
1157 * 2. Redistributions in binary form must reproduce the above copyright
1158 * notice, this list of conditions and the following disclaimer in the
1159 * documentation and/or other materials provided with the distribution.
1160 *
1161 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
1162 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
1163 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
1164 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
1165 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
1166 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
1167 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
1168 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
1169 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
1170 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
1171 * SUCH DAMAGE.
1172 */
1173
1174#ifdef HAVE_SYS_EVENT_H
1175#include <sys/event.h>
1176#endif
1177
1178PyDoc_STRVAR(kqueue_event_doc,
Georg Brandlfa1ffb62009-12-29 21:09:17 +00001179"kevent(ident, filter=KQ_FILTER_READ, flags=KQ_EV_ADD, fflags=0, data=0, udata=0)\n\
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001180\n\
1181This object is the equivalent of the struct kevent for the C API.\n\
1182\n\
1183See the kqueue manpage for more detailed information about the meaning\n\
1184of the arguments.\n\
1185\n\
1186One minor note: while you might hope that udata could store a\n\
1187reference to a python object, it cannot, because it is impossible to\n\
1188keep a proper reference count of the object once it's passed into the\n\
1189kernel. Therefore, I have restricted it to only storing an integer. I\n\
1190recommend ignoring it and simply using the 'ident' field to key off\n\
1191of. You could also set up a dictionary on the python side to store a\n\
1192udata->object mapping.");
1193
1194typedef struct {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001195 PyObject_HEAD
1196 struct kevent e;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001197} kqueue_event_Object;
1198
1199static PyTypeObject kqueue_event_Type;
1200
1201#define kqueue_event_Check(op) (PyObject_TypeCheck((op), &kqueue_event_Type))
1202
1203typedef struct {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001204 PyObject_HEAD
1205 SOCKET kqfd; /* kqueue control fd */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001206} kqueue_queue_Object;
1207
1208static PyTypeObject kqueue_queue_Type;
1209
1210#define kqueue_queue_Check(op) (PyObject_TypeCheck((op), &kqueue_queue_Type))
1211
Antoine Pitrou323b9da2009-11-04 19:25:14 +00001212#if (SIZEOF_UINTPTR_T != SIZEOF_VOID_P)
1213# error uintptr_t does not match void *!
1214#elif (SIZEOF_UINTPTR_T == SIZEOF_LONG_LONG)
1215# define T_UINTPTRT T_ULONGLONG
1216# define T_INTPTRT T_LONGLONG
1217# define PyLong_AsUintptr_t PyLong_AsUnsignedLongLong
1218# define UINTPTRT_FMT_UNIT "K"
1219# define INTPTRT_FMT_UNIT "L"
1220#elif (SIZEOF_UINTPTR_T == SIZEOF_LONG)
1221# define T_UINTPTRT T_ULONG
1222# define T_INTPTRT T_LONG
1223# define PyLong_AsUintptr_t PyLong_AsUnsignedLong
1224# define UINTPTRT_FMT_UNIT "k"
1225# define INTPTRT_FMT_UNIT "l"
1226#elif (SIZEOF_UINTPTR_T == SIZEOF_INT)
1227# define T_UINTPTRT T_UINT
1228# define T_INTPTRT T_INT
1229# define PyLong_AsUintptr_t PyLong_AsUnsignedLong
1230# define UINTPTRT_FMT_UNIT "I"
1231# define INTPTRT_FMT_UNIT "i"
1232#else
1233# error uintptr_t does not match int, long, or long long!
1234#endif
1235
Charles-Francois Natali880359c2013-05-06 21:21:57 +02001236/*
1237 * kevent is not standard and its members vary across BSDs.
1238 */
1239#if !defined(__OpenBSD__)
1240# define IDENT_TYPE T_UINTPTRT
1241# define IDENT_CAST Py_intptr_t
1242# define DATA_TYPE T_INTPTRT
1243# define DATA_FMT_UNIT INTPTRT_FMT_UNIT
1244# define IDENT_AsType PyLong_AsUintptr_t
1245#else
1246# define IDENT_TYPE T_UINT
1247# define IDENT_CAST int
1248# define DATA_TYPE T_INT
1249# define DATA_FMT_UNIT "i"
1250# define IDENT_AsType PyLong_AsUnsignedLong
1251#endif
1252
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001253/* Unfortunately, we can't store python objects in udata, because
1254 * kevents in the kernel can be removed without warning, which would
1255 * forever lose the refcount on the object stored with it.
1256 */
1257
1258#define KQ_OFF(x) offsetof(kqueue_event_Object, x)
1259static struct PyMemberDef kqueue_event_members[] = {
Charles-Francois Natali880359c2013-05-06 21:21:57 +02001260 {"ident", IDENT_TYPE, KQ_OFF(e.ident)},
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001261 {"filter", T_SHORT, KQ_OFF(e.filter)},
1262 {"flags", T_USHORT, KQ_OFF(e.flags)},
1263 {"fflags", T_UINT, KQ_OFF(e.fflags)},
Charles-Francois Natali880359c2013-05-06 21:21:57 +02001264 {"data", DATA_TYPE, KQ_OFF(e.data)},
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001265 {"udata", T_UINTPTRT, KQ_OFF(e.udata)},
1266 {NULL} /* Sentinel */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001267};
1268#undef KQ_OFF
1269
1270static PyObject *
Georg Brandlea370a92010-02-23 21:48:57 +00001271
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001272kqueue_event_repr(kqueue_event_Object *s)
1273{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001274 char buf[1024];
1275 PyOS_snprintf(
1276 buf, sizeof(buf),
1277 "<select.kevent ident=%zu filter=%d flags=0x%x fflags=0x%x "
1278 "data=0x%zd udata=%p>",
1279 (size_t)(s->e.ident), s->e.filter, s->e.flags,
1280 s->e.fflags, (Py_ssize_t)(s->e.data), s->e.udata);
1281 return PyString_FromString(buf);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001282}
1283
1284static int
1285kqueue_event_init(kqueue_event_Object *self, PyObject *args, PyObject *kwds)
1286{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001287 PyObject *pfd;
1288 static char *kwlist[] = {"ident", "filter", "flags", "fflags",
1289 "data", "udata", NULL};
Christian Heimes42831fe2013-08-25 14:57:00 +02001290 static char *fmt = "O|hHI" DATA_FMT_UNIT UINTPTRT_FMT_UNIT ":kevent";
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001291
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001292 EV_SET(&(self->e), 0, EVFILT_READ, EV_ADD, 0, 0, 0); /* defaults */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001293
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001294 if (!PyArg_ParseTupleAndKeywords(args, kwds, fmt, kwlist,
1295 &pfd, &(self->e.filter), &(self->e.flags),
1296 &(self->e.fflags), &(self->e.data), &(self->e.udata))) {
1297 return -1;
1298 }
1299
Charles-Francois Natali880359c2013-05-06 21:21:57 +02001300 if (PyLong_Check(pfd)
1301#if IDENT_TYPE == T_UINT
1302 && PyLong_AsUnsignedLong(pfd) <= UINT_MAX
1303#endif
1304 ) {
1305 self->e.ident = IDENT_AsType(pfd);
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001306 }
1307 else {
1308 self->e.ident = PyObject_AsFileDescriptor(pfd);
1309 }
1310 if (PyErr_Occurred()) {
1311 return -1;
1312 }
1313 return 0;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001314}
1315
1316static PyObject *
1317kqueue_event_richcompare(kqueue_event_Object *s, kqueue_event_Object *o,
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001318 int op)
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001319{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001320 Py_intptr_t result = 0;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001321
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001322 if (!kqueue_event_Check(o)) {
1323 if (op == Py_EQ || op == Py_NE) {
1324 PyObject *res = op == Py_EQ ? Py_False : Py_True;
1325 Py_INCREF(res);
1326 return res;
1327 }
1328 PyErr_Format(PyExc_TypeError,
1329 "can't compare %.200s to %.200s",
1330 Py_TYPE(s)->tp_name, Py_TYPE(o)->tp_name);
1331 return NULL;
1332 }
Charles-Francois Natali880359c2013-05-06 21:21:57 +02001333 if (((result = (IDENT_CAST)(s->e.ident - o->e.ident)) == 0) &&
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001334 ((result = s->e.filter - o->e.filter) == 0) &&
1335 ((result = s->e.flags - o->e.flags) == 0) &&
Charles-Francois Natali880359c2013-05-06 21:21:57 +02001336 ((result = (int)(s->e.fflags - o->e.fflags)) == 0) &&
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001337 ((result = s->e.data - o->e.data) == 0) &&
1338 ((result = s->e.udata - o->e.udata) == 0)
1339 ) {
1340 result = 0;
1341 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001342
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001343 switch (op) {
1344 case Py_EQ:
1345 result = (result == 0);
1346 break;
1347 case Py_NE:
1348 result = (result != 0);
1349 break;
1350 case Py_LE:
1351 result = (result <= 0);
1352 break;
1353 case Py_GE:
1354 result = (result >= 0);
1355 break;
1356 case Py_LT:
1357 result = (result < 0);
1358 break;
1359 case Py_GT:
1360 result = (result > 0);
1361 break;
1362 }
1363 return PyBool_FromLong((long)result);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001364}
1365
1366static PyTypeObject kqueue_event_Type = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001367 PyVarObject_HEAD_INIT(NULL, 0)
1368 "select.kevent", /* tp_name */
1369 sizeof(kqueue_event_Object), /* tp_basicsize */
1370 0, /* tp_itemsize */
1371 0, /* tp_dealloc */
1372 0, /* tp_print */
1373 0, /* tp_getattr */
1374 0, /* tp_setattr */
1375 0, /* tp_compare */
1376 (reprfunc)kqueue_event_repr, /* tp_repr */
1377 0, /* tp_as_number */
1378 0, /* tp_as_sequence */
1379 0, /* tp_as_mapping */
1380 0, /* tp_hash */
1381 0, /* tp_call */
1382 0, /* tp_str */
1383 0, /* tp_getattro */
1384 0, /* tp_setattro */
1385 0, /* tp_as_buffer */
1386 Py_TPFLAGS_DEFAULT, /* tp_flags */
1387 kqueue_event_doc, /* tp_doc */
1388 0, /* tp_traverse */
1389 0, /* tp_clear */
1390 (richcmpfunc)kqueue_event_richcompare, /* tp_richcompare */
1391 0, /* tp_weaklistoffset */
1392 0, /* tp_iter */
1393 0, /* tp_iternext */
1394 0, /* tp_methods */
1395 kqueue_event_members, /* tp_members */
1396 0, /* tp_getset */
1397 0, /* tp_base */
1398 0, /* tp_dict */
1399 0, /* tp_descr_get */
1400 0, /* tp_descr_set */
1401 0, /* tp_dictoffset */
1402 (initproc)kqueue_event_init, /* tp_init */
1403 0, /* tp_alloc */
1404 0, /* tp_new */
1405 0, /* tp_free */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001406};
1407
1408static PyObject *
1409kqueue_queue_err_closed(void)
1410{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001411 PyErr_SetString(PyExc_ValueError, "I/O operation on closed kqueue fd");
1412 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001413}
1414
1415static int
1416kqueue_queue_internal_close(kqueue_queue_Object *self)
1417{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001418 int save_errno = 0;
1419 if (self->kqfd >= 0) {
1420 int kqfd = self->kqfd;
1421 self->kqfd = -1;
1422 Py_BEGIN_ALLOW_THREADS
1423 if (close(kqfd) < 0)
1424 save_errno = errno;
1425 Py_END_ALLOW_THREADS
1426 }
1427 return save_errno;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001428}
1429
1430static PyObject *
1431newKqueue_Object(PyTypeObject *type, SOCKET fd)
1432{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001433 kqueue_queue_Object *self;
1434 assert(type != NULL && type->tp_alloc != NULL);
1435 self = (kqueue_queue_Object *) type->tp_alloc(type, 0);
1436 if (self == NULL) {
1437 return NULL;
1438 }
1439
1440 if (fd == -1) {
1441 Py_BEGIN_ALLOW_THREADS
1442 self->kqfd = kqueue();
1443 Py_END_ALLOW_THREADS
1444 }
1445 else {
1446 self->kqfd = fd;
1447 }
1448 if (self->kqfd < 0) {
1449 Py_DECREF(self);
1450 PyErr_SetFromErrno(PyExc_IOError);
1451 return NULL;
1452 }
1453 return (PyObject *)self;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001454}
1455
1456static PyObject *
1457kqueue_queue_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
1458{
1459
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001460 if ((args != NULL && PyObject_Size(args)) ||
1461 (kwds != NULL && PyObject_Size(kwds))) {
1462 PyErr_SetString(PyExc_ValueError,
1463 "select.kqueue doesn't accept arguments");
1464 return NULL;
1465 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001466
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001467 return newKqueue_Object(type, -1);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001468}
1469
1470static void
1471kqueue_queue_dealloc(kqueue_queue_Object *self)
1472{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001473 kqueue_queue_internal_close(self);
1474 Py_TYPE(self)->tp_free(self);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001475}
1476
1477static PyObject*
1478kqueue_queue_close(kqueue_queue_Object *self)
1479{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001480 errno = kqueue_queue_internal_close(self);
1481 if (errno < 0) {
1482 PyErr_SetFromErrno(PyExc_IOError);
1483 return NULL;
1484 }
1485 Py_RETURN_NONE;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001486}
1487
1488PyDoc_STRVAR(kqueue_queue_close_doc,
1489"close() -> None\n\
1490\n\
1491Close the kqueue control file descriptor. Further operations on the kqueue\n\
1492object will raise an exception.");
1493
1494static PyObject*
1495kqueue_queue_get_closed(kqueue_queue_Object *self)
1496{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001497 if (self->kqfd < 0)
1498 Py_RETURN_TRUE;
1499 else
1500 Py_RETURN_FALSE;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001501}
1502
1503static PyObject*
1504kqueue_queue_fileno(kqueue_queue_Object *self)
1505{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001506 if (self->kqfd < 0)
1507 return kqueue_queue_err_closed();
1508 return PyInt_FromLong(self->kqfd);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001509}
1510
1511PyDoc_STRVAR(kqueue_queue_fileno_doc,
1512"fileno() -> int\n\
1513\n\
1514Return the kqueue control file descriptor.");
1515
1516static PyObject*
1517kqueue_queue_fromfd(PyObject *cls, PyObject *args)
1518{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001519 SOCKET fd;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001520
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001521 if (!PyArg_ParseTuple(args, "i:fromfd", &fd))
1522 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001523
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001524 return newKqueue_Object((PyTypeObject*)cls, fd);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001525}
1526
1527PyDoc_STRVAR(kqueue_queue_fromfd_doc,
1528"fromfd(fd) -> kqueue\n\
1529\n\
1530Create a kqueue object from a given control fd.");
1531
1532static PyObject *
1533kqueue_queue_control(kqueue_queue_Object *self, PyObject *args)
1534{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001535 int nevents = 0;
1536 int gotevents = 0;
1537 int nchanges = 0;
1538 int i = 0;
1539 PyObject *otimeout = NULL;
1540 PyObject *ch = NULL;
1541 PyObject *it = NULL, *ei = NULL;
1542 PyObject *result = NULL;
1543 struct kevent *evl = NULL;
1544 struct kevent *chl = NULL;
1545 struct timespec timeoutspec;
1546 struct timespec *ptimeoutspec;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001547
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001548 if (self->kqfd < 0)
1549 return kqueue_queue_err_closed();
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001550
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001551 if (!PyArg_ParseTuple(args, "Oi|O:control", &ch, &nevents, &otimeout))
1552 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001553
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001554 if (nevents < 0) {
1555 PyErr_Format(PyExc_ValueError,
1556 "Length of eventlist must be 0 or positive, got %d",
1557 nevents);
1558 return NULL;
1559 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001560
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001561 if (otimeout == Py_None || otimeout == NULL) {
1562 ptimeoutspec = NULL;
1563 }
1564 else if (PyNumber_Check(otimeout)) {
1565 double timeout;
1566 long seconds;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001567
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001568 timeout = PyFloat_AsDouble(otimeout);
1569 if (timeout == -1 && PyErr_Occurred())
1570 return NULL;
1571 if (timeout > (double)LONG_MAX) {
1572 PyErr_SetString(PyExc_OverflowError,
1573 "timeout period too long");
1574 return NULL;
1575 }
1576 if (timeout < 0) {
1577 PyErr_SetString(PyExc_ValueError,
1578 "timeout must be positive or None");
1579 return NULL;
1580 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001581
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001582 seconds = (long)timeout;
1583 timeout = timeout - (double)seconds;
1584 timeoutspec.tv_sec = seconds;
1585 timeoutspec.tv_nsec = (long)(timeout * 1E9);
1586 ptimeoutspec = &timeoutspec;
1587 }
1588 else {
1589 PyErr_Format(PyExc_TypeError,
1590 "timeout argument must be an number "
1591 "or None, got %.200s",
1592 Py_TYPE(otimeout)->tp_name);
1593 return NULL;
1594 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001595
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001596 if (ch != NULL && ch != Py_None) {
1597 it = PyObject_GetIter(ch);
1598 if (it == NULL) {
1599 PyErr_SetString(PyExc_TypeError,
1600 "changelist is not iterable");
1601 return NULL;
1602 }
1603 nchanges = PyObject_Size(ch);
1604 if (nchanges < 0) {
1605 goto error;
1606 }
Georg Brandlea370a92010-02-23 21:48:57 +00001607
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001608 chl = PyMem_New(struct kevent, nchanges);
1609 if (chl == NULL) {
1610 PyErr_NoMemory();
1611 goto error;
1612 }
1613 i = 0;
1614 while ((ei = PyIter_Next(it)) != NULL) {
1615 if (!kqueue_event_Check(ei)) {
1616 Py_DECREF(ei);
1617 PyErr_SetString(PyExc_TypeError,
1618 "changelist must be an iterable of "
1619 "select.kevent objects");
1620 goto error;
1621 } else {
1622 chl[i++] = ((kqueue_event_Object *)ei)->e;
1623 }
1624 Py_DECREF(ei);
1625 }
1626 }
1627 Py_CLEAR(it);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001628
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001629 /* event list */
1630 if (nevents) {
1631 evl = PyMem_New(struct kevent, nevents);
1632 if (evl == NULL) {
1633 PyErr_NoMemory();
1634 goto error;
1635 }
1636 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001637
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001638 Py_BEGIN_ALLOW_THREADS
1639 gotevents = kevent(self->kqfd, chl, nchanges,
1640 evl, nevents, ptimeoutspec);
1641 Py_END_ALLOW_THREADS
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001642
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001643 if (gotevents == -1) {
1644 PyErr_SetFromErrno(PyExc_OSError);
1645 goto error;
1646 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001647
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001648 result = PyList_New(gotevents);
1649 if (result == NULL) {
1650 goto error;
1651 }
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001652
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001653 for (i = 0; i < gotevents; i++) {
1654 kqueue_event_Object *ch;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001655
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001656 ch = PyObject_New(kqueue_event_Object, &kqueue_event_Type);
1657 if (ch == NULL) {
1658 goto error;
1659 }
1660 ch->e = evl[i];
1661 PyList_SET_ITEM(result, i, (PyObject *)ch);
1662 }
1663 PyMem_Free(chl);
1664 PyMem_Free(evl);
1665 return result;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001666
1667 error:
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001668 PyMem_Free(chl);
1669 PyMem_Free(evl);
1670 Py_XDECREF(result);
1671 Py_XDECREF(it);
1672 return NULL;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001673}
1674
1675PyDoc_STRVAR(kqueue_queue_control_doc,
Georg Brandl2f3bd832008-09-21 07:14:44 +00001676"control(changelist, max_events[, timeout=None]) -> eventlist\n\
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001677\n\
1678Calls the kernel kevent function.\n\
1679- changelist must be a list of kevent objects describing the changes\n\
1680 to be made to the kernel's watch list or None.\n\
1681- max_events lets you specify the maximum number of events that the\n\
1682 kernel will return.\n\
1683- timeout is the maximum time to wait in seconds, or else None,\n\
1684 to wait forever. timeout accepts floats for smaller timeouts, too.");
1685
1686
1687static PyMethodDef kqueue_queue_methods[] = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001688 {"fromfd", (PyCFunction)kqueue_queue_fromfd,
1689 METH_VARARGS | METH_CLASS, kqueue_queue_fromfd_doc},
1690 {"close", (PyCFunction)kqueue_queue_close, METH_NOARGS,
1691 kqueue_queue_close_doc},
1692 {"fileno", (PyCFunction)kqueue_queue_fileno, METH_NOARGS,
1693 kqueue_queue_fileno_doc},
1694 {"control", (PyCFunction)kqueue_queue_control,
1695 METH_VARARGS , kqueue_queue_control_doc},
1696 {NULL, NULL},
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001697};
1698
1699static PyGetSetDef kqueue_queue_getsetlist[] = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001700 {"closed", (getter)kqueue_queue_get_closed, NULL,
1701 "True if the kqueue handler is closed"},
1702 {0},
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001703};
1704
1705PyDoc_STRVAR(kqueue_queue_doc,
1706"Kqueue syscall wrapper.\n\
1707\n\
1708For example, to start watching a socket for input:\n\
1709>>> kq = kqueue()\n\
1710>>> sock = socket()\n\
1711>>> sock.connect((host, port))\n\
1712>>> kq.control([kevent(sock, KQ_FILTER_WRITE, KQ_EV_ADD)], 0)\n\
1713\n\
1714To wait one second for it to become writeable:\n\
1715>>> kq.control(None, 1, 1000)\n\
1716\n\
1717To stop listening:\n\
1718>>> kq.control([kevent(sock, KQ_FILTER_WRITE, KQ_EV_DELETE)], 0)");
1719
1720static PyTypeObject kqueue_queue_Type = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001721 PyVarObject_HEAD_INIT(NULL, 0)
1722 "select.kqueue", /* tp_name */
1723 sizeof(kqueue_queue_Object), /* tp_basicsize */
1724 0, /* tp_itemsize */
1725 (destructor)kqueue_queue_dealloc, /* tp_dealloc */
1726 0, /* tp_print */
1727 0, /* tp_getattr */
1728 0, /* tp_setattr */
1729 0, /* tp_compare */
1730 0, /* tp_repr */
1731 0, /* tp_as_number */
1732 0, /* tp_as_sequence */
1733 0, /* tp_as_mapping */
1734 0, /* tp_hash */
1735 0, /* tp_call */
1736 0, /* tp_str */
1737 0, /* tp_getattro */
1738 0, /* tp_setattro */
1739 0, /* tp_as_buffer */
1740 Py_TPFLAGS_DEFAULT, /* tp_flags */
1741 kqueue_queue_doc, /* tp_doc */
1742 0, /* tp_traverse */
1743 0, /* tp_clear */
1744 0, /* tp_richcompare */
1745 0, /* tp_weaklistoffset */
1746 0, /* tp_iter */
1747 0, /* tp_iternext */
1748 kqueue_queue_methods, /* tp_methods */
1749 0, /* tp_members */
1750 kqueue_queue_getsetlist, /* tp_getset */
1751 0, /* tp_base */
1752 0, /* tp_dict */
1753 0, /* tp_descr_get */
1754 0, /* tp_descr_set */
1755 0, /* tp_dictoffset */
1756 0, /* tp_init */
1757 0, /* tp_alloc */
1758 kqueue_queue_new, /* tp_new */
1759 0, /* tp_free */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001760};
1761
1762#endif /* HAVE_KQUEUE */
1763/* ************************************************************************ */
1764
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001765PyDoc_STRVAR(select_doc,
Guido van Rossum1d8fb2d1998-06-28 16:54:49 +00001766"select(rlist, wlist, xlist[, timeout]) -> (rlist, wlist, xlist)\n\
1767\n\
1768Wait until one or more file descriptors are ready for some kind of I/O.\n\
Brett Cannon62dba4c2003-09-10 19:37:42 +00001769The first three arguments are sequences of file descriptors to be waited for:\n\
Guido van Rossum1d8fb2d1998-06-28 16:54:49 +00001770rlist -- wait until ready for reading\n\
1771wlist -- wait until ready for writing\n\
1772xlist -- wait for an ``exceptional condition''\n\
1773If only one kind of condition is required, pass [] for the other lists.\n\
1774A file descriptor is either a socket or file object, or a small integer\n\
1775gotten from a fileno() method call on one of those.\n\
1776\n\
1777The optional 4th argument specifies a timeout in seconds; it may be\n\
1778a floating point number to specify fractions of seconds. If it is absent\n\
1779or None, the call will never time out.\n\
1780\n\
1781The return value is a tuple of three lists corresponding to the first three\n\
1782arguments; each contains the subset of the corresponding file descriptors\n\
1783that are ready.\n\
1784\n\
1785*** IMPORTANT NOTICE ***\n\
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001786On Windows and OpenVMS, only sockets are supported; on Unix, all file\n\
Andrew M. Kuchlinga8c3f2b2008-03-26 00:16:50 +00001787descriptors can be used.");
Guido van Rossum1d8fb2d1998-06-28 16:54:49 +00001788
Barry Warsawe4ac0aa1996-12-12 00:04:35 +00001789static PyMethodDef select_methods[] = {
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001790 {"select", select_select, METH_VARARGS, select_doc},
Charles-François Natalia41cf292013-01-19 12:15:56 +01001791#if defined(HAVE_POLL) && !defined(HAVE_BROKEN_POLL)
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001792 {"poll", select_poll, METH_NOARGS, poll_doc},
Ronald Oussoren32fd16e2006-04-23 12:36:23 +00001793#endif /* HAVE_POLL */
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001794 {0, 0}, /* sentinel */
Guido van Rossumed233a51992-06-23 09:07:03 +00001795};
1796
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001797PyDoc_STRVAR(module_doc,
Guido van Rossum1d8fb2d1998-06-28 16:54:49 +00001798"This module supports asynchronous I/O on multiple file descriptors.\n\
1799\n\
1800*** IMPORTANT NOTICE ***\n\
Neal Norwitz2a30cd02006-07-10 01:18:57 +00001801On Windows and OpenVMS, only sockets are supported; on Unix, all file descriptors.");
Guido van Rossumed233a51992-06-23 09:07:03 +00001802
Mark Hammond62b1ab12002-07-23 06:31:15 +00001803PyMODINIT_FUNC
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001804initselect(void)
Guido van Rossumed233a51992-06-23 09:07:03 +00001805{
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001806 PyObject *m;
1807 m = Py_InitModule3("select", select_methods, module_doc);
1808 if (m == NULL)
1809 return;
Fred Drake4baedc12002-04-01 14:53:37 +00001810
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001811 SelectError = PyErr_NewException("select.error", NULL, NULL);
1812 Py_INCREF(SelectError);
1813 PyModule_AddObject(m, "error", SelectError);
Ronald Oussoren32fd16e2006-04-23 12:36:23 +00001814
Amaury Forgeot d'Arcce32eb72009-07-09 22:37:22 +00001815#ifdef PIPE_BUF
R. David Murray1d9d16e2010-10-16 00:43:13 +00001816#ifdef HAVE_BROKEN_PIPE_BUF
1817#undef PIPE_BUF
1818#define PIPE_BUF 512
1819#endif
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001820 PyModule_AddIntConstant(m, "PIPE_BUF", PIPE_BUF);
Amaury Forgeot d'Arcce32eb72009-07-09 22:37:22 +00001821#endif
Gregory P. Smith9d36fd22009-07-03 20:48:31 +00001822
Charles-François Natalia41cf292013-01-19 12:15:56 +01001823#if defined(HAVE_POLL) && !defined(HAVE_BROKEN_POLL)
Ronald Oussoren32fd16e2006-04-23 12:36:23 +00001824#ifdef __APPLE__
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001825 if (select_have_broken_poll()) {
1826 if (PyObject_DelAttrString(m, "poll") == -1) {
1827 PyErr_Clear();
1828 }
1829 } else {
Ronald Oussoren32fd16e2006-04-23 12:36:23 +00001830#else
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001831 {
Ronald Oussoren32fd16e2006-04-23 12:36:23 +00001832#endif
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001833 Py_TYPE(&poll_Type) = &PyType_Type;
1834 PyModule_AddIntConstant(m, "POLLIN", POLLIN);
1835 PyModule_AddIntConstant(m, "POLLPRI", POLLPRI);
1836 PyModule_AddIntConstant(m, "POLLOUT", POLLOUT);
1837 PyModule_AddIntConstant(m, "POLLERR", POLLERR);
1838 PyModule_AddIntConstant(m, "POLLHUP", POLLHUP);
1839 PyModule_AddIntConstant(m, "POLLNVAL", POLLNVAL);
Andrew M. Kuchlingcf96dc82000-08-25 01:15:33 +00001840
Andrew M. Kuchling36d97eb2000-09-28 21:33:44 +00001841#ifdef POLLRDNORM
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001842 PyModule_AddIntConstant(m, "POLLRDNORM", POLLRDNORM);
Andrew M. Kuchling36d97eb2000-09-28 21:33:44 +00001843#endif
1844#ifdef POLLRDBAND
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001845 PyModule_AddIntConstant(m, "POLLRDBAND", POLLRDBAND);
Andrew M. Kuchling36d97eb2000-09-28 21:33:44 +00001846#endif
1847#ifdef POLLWRNORM
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001848 PyModule_AddIntConstant(m, "POLLWRNORM", POLLWRNORM);
Andrew M. Kuchling36d97eb2000-09-28 21:33:44 +00001849#endif
1850#ifdef POLLWRBAND
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001851 PyModule_AddIntConstant(m, "POLLWRBAND", POLLWRBAND);
Andrew M. Kuchling36d97eb2000-09-28 21:33:44 +00001852#endif
Sjoerd Mullender239f8362000-08-25 13:59:18 +00001853#ifdef POLLMSG
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001854 PyModule_AddIntConstant(m, "POLLMSG", POLLMSG);
Sjoerd Mullender239f8362000-08-25 13:59:18 +00001855#endif
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001856 }
Ronald Oussoren32fd16e2006-04-23 12:36:23 +00001857#endif /* HAVE_POLL */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001858
1859#ifdef HAVE_EPOLL
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001860 Py_TYPE(&pyEpoll_Type) = &PyType_Type;
1861 if (PyType_Ready(&pyEpoll_Type) < 0)
1862 return;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001863
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001864 Py_INCREF(&pyEpoll_Type);
1865 PyModule_AddObject(m, "epoll", (PyObject *) &pyEpoll_Type);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001866
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001867 PyModule_AddIntConstant(m, "EPOLLIN", EPOLLIN);
1868 PyModule_AddIntConstant(m, "EPOLLOUT", EPOLLOUT);
1869 PyModule_AddIntConstant(m, "EPOLLPRI", EPOLLPRI);
1870 PyModule_AddIntConstant(m, "EPOLLERR", EPOLLERR);
1871 PyModule_AddIntConstant(m, "EPOLLHUP", EPOLLHUP);
1872 PyModule_AddIntConstant(m, "EPOLLET", EPOLLET);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001873#ifdef EPOLLONESHOT
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001874 /* Kernel 2.6.2+ */
1875 PyModule_AddIntConstant(m, "EPOLLONESHOT", EPOLLONESHOT);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001876#endif
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001877 /* PyModule_AddIntConstant(m, "EPOLL_RDHUP", EPOLLRDHUP); */
1878 PyModule_AddIntConstant(m, "EPOLLRDNORM", EPOLLRDNORM);
1879 PyModule_AddIntConstant(m, "EPOLLRDBAND", EPOLLRDBAND);
1880 PyModule_AddIntConstant(m, "EPOLLWRNORM", EPOLLWRNORM);
1881 PyModule_AddIntConstant(m, "EPOLLWRBAND", EPOLLWRBAND);
1882 PyModule_AddIntConstant(m, "EPOLLMSG", EPOLLMSG);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001883#endif /* HAVE_EPOLL */
1884
1885#ifdef HAVE_KQUEUE
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001886 kqueue_event_Type.tp_new = PyType_GenericNew;
1887 Py_TYPE(&kqueue_event_Type) = &PyType_Type;
1888 if(PyType_Ready(&kqueue_event_Type) < 0)
1889 return;
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001890
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001891 Py_INCREF(&kqueue_event_Type);
1892 PyModule_AddObject(m, "kevent", (PyObject *)&kqueue_event_Type);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001893
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001894 Py_TYPE(&kqueue_queue_Type) = &PyType_Type;
1895 if(PyType_Ready(&kqueue_queue_Type) < 0)
1896 return;
1897 Py_INCREF(&kqueue_queue_Type);
1898 PyModule_AddObject(m, "kqueue", (PyObject *)&kqueue_queue_Type);
1899
1900 /* event filters */
1901 PyModule_AddIntConstant(m, "KQ_FILTER_READ", EVFILT_READ);
1902 PyModule_AddIntConstant(m, "KQ_FILTER_WRITE", EVFILT_WRITE);
1903 PyModule_AddIntConstant(m, "KQ_FILTER_AIO", EVFILT_AIO);
1904 PyModule_AddIntConstant(m, "KQ_FILTER_VNODE", EVFILT_VNODE);
1905 PyModule_AddIntConstant(m, "KQ_FILTER_PROC", EVFILT_PROC);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001906#ifdef EVFILT_NETDEV
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001907 PyModule_AddIntConstant(m, "KQ_FILTER_NETDEV", EVFILT_NETDEV);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001908#endif
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001909 PyModule_AddIntConstant(m, "KQ_FILTER_SIGNAL", EVFILT_SIGNAL);
1910 PyModule_AddIntConstant(m, "KQ_FILTER_TIMER", EVFILT_TIMER);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001911
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001912 /* event flags */
1913 PyModule_AddIntConstant(m, "KQ_EV_ADD", EV_ADD);
1914 PyModule_AddIntConstant(m, "KQ_EV_DELETE", EV_DELETE);
1915 PyModule_AddIntConstant(m, "KQ_EV_ENABLE", EV_ENABLE);
1916 PyModule_AddIntConstant(m, "KQ_EV_DISABLE", EV_DISABLE);
1917 PyModule_AddIntConstant(m, "KQ_EV_ONESHOT", EV_ONESHOT);
1918 PyModule_AddIntConstant(m, "KQ_EV_CLEAR", EV_CLEAR);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001919
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001920 PyModule_AddIntConstant(m, "KQ_EV_SYSFLAGS", EV_SYSFLAGS);
1921 PyModule_AddIntConstant(m, "KQ_EV_FLAG1", EV_FLAG1);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001922
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001923 PyModule_AddIntConstant(m, "KQ_EV_EOF", EV_EOF);
1924 PyModule_AddIntConstant(m, "KQ_EV_ERROR", EV_ERROR);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001925
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001926 /* READ WRITE filter flag */
1927 PyModule_AddIntConstant(m, "KQ_NOTE_LOWAT", NOTE_LOWAT);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001928
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001929 /* VNODE filter flags */
1930 PyModule_AddIntConstant(m, "KQ_NOTE_DELETE", NOTE_DELETE);
1931 PyModule_AddIntConstant(m, "KQ_NOTE_WRITE", NOTE_WRITE);
1932 PyModule_AddIntConstant(m, "KQ_NOTE_EXTEND", NOTE_EXTEND);
1933 PyModule_AddIntConstant(m, "KQ_NOTE_ATTRIB", NOTE_ATTRIB);
1934 PyModule_AddIntConstant(m, "KQ_NOTE_LINK", NOTE_LINK);
1935 PyModule_AddIntConstant(m, "KQ_NOTE_RENAME", NOTE_RENAME);
1936 PyModule_AddIntConstant(m, "KQ_NOTE_REVOKE", NOTE_REVOKE);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001937
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001938 /* PROC filter flags */
1939 PyModule_AddIntConstant(m, "KQ_NOTE_EXIT", NOTE_EXIT);
1940 PyModule_AddIntConstant(m, "KQ_NOTE_FORK", NOTE_FORK);
1941 PyModule_AddIntConstant(m, "KQ_NOTE_EXEC", NOTE_EXEC);
1942 PyModule_AddIntConstant(m, "KQ_NOTE_PCTRLMASK", NOTE_PCTRLMASK);
1943 PyModule_AddIntConstant(m, "KQ_NOTE_PDATAMASK", NOTE_PDATAMASK);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001944
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001945 PyModule_AddIntConstant(m, "KQ_NOTE_TRACK", NOTE_TRACK);
1946 PyModule_AddIntConstant(m, "KQ_NOTE_CHILD", NOTE_CHILD);
1947 PyModule_AddIntConstant(m, "KQ_NOTE_TRACKERR", NOTE_TRACKERR);
1948
1949 /* NETDEV filter flags */
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001950#ifdef EVFILT_NETDEV
Antoine Pitrouc83ea132010-05-09 14:46:46 +00001951 PyModule_AddIntConstant(m, "KQ_NOTE_LINKUP", NOTE_LINKUP);
1952 PyModule_AddIntConstant(m, "KQ_NOTE_LINKDOWN", NOTE_LINKDOWN);
1953 PyModule_AddIntConstant(m, "KQ_NOTE_LINKINV", NOTE_LINKINV);
Christian Heimes0e9ab5f2008-03-21 23:49:44 +00001954#endif
1955
1956#endif /* HAVE_KQUEUE */
Guido van Rossumed233a51992-06-23 09:07:03 +00001957}