04a4f5c4781ee3bf6771b1fb644cb1c84b5892c7
[openwrt/svn-archive/archive.git] / lang / python / patches / 050-add_signal_set_wakeup_fd.patch
1 diff -urN Python-2.5.1.orig/Include/pyerrors.h Python-2.5.1/Include/pyerrors.h
2 --- Python-2.5.1.orig/Include/pyerrors.h 2008-08-10 13:46:48.000000000 +0200
3 +++ Python-2.5.1/Include/pyerrors.h 2008-08-10 13:51:05.000000000 +0200
4 @@ -239,6 +239,9 @@
5 PyAPI_FUNC(int) PyErr_CheckSignals(void);
6 PyAPI_FUNC(void) PyErr_SetInterrupt(void);
7
8 +/* In signalmodule.c */
9 +int PySignal_SetWakeupFd(int fd);
10 +
11 /* Support for adding program text to SyntaxErrors */
12 PyAPI_FUNC(void) PyErr_SyntaxLocation(const char *, int);
13 PyAPI_FUNC(PyObject *) PyErr_ProgramText(const char *, int);
14 diff -urN Python-2.5.1.orig/Modules/signalmodule.c Python-2.5.1/Modules/signalmodule.c
15 --- Python-2.5.1.orig/Modules/signalmodule.c 2008-08-10 13:46:48.000000000 +0200
16 +++ Python-2.5.1/Modules/signalmodule.c 2008-08-10 13:50:02.000000000 +0200
17 @@ -12,6 +12,8 @@
18
19 #include <signal.h>
20
21 +#include <sys/stat.h>
22 +
23 #ifndef SIG_ERR
24 #define SIG_ERR ((PyOS_sighandler_t)(-1))
25 #endif
26 @@ -75,6 +77,8 @@
27 PyObject *func;
28 } Handlers[NSIG];
29
30 +static int wakeup_fd = -1;
31 +
32 static int is_tripped = 0; /* Speed up sigcheck() when none tripped */
33
34 static PyObject *DefaultHandler;
35 @@ -112,6 +116,7 @@
36 static void
37 signal_handler(int sig_num)
38 {
39 + const char dummy_byte = '\0';
40 #ifdef WITH_THREAD
41 #ifdef WITH_PTH
42 if (PyThread_get_thread_ident() != main_thread) {
43 @@ -125,6 +130,8 @@
44 is_tripped++;
45 Handlers[sig_num].tripped = 1;
46 Py_AddPendingCall(checksignals_witharg, NULL);
47 + if (wakeup_fd != -1)
48 + write(wakeup_fd, &dummy_byte, 1);
49 #ifdef WITH_THREAD
50 }
51 #endif
52 @@ -264,6 +271,50 @@
53 anything else -- the callable Python object used as a handler");
54
55
56 +static PyObject *
57 +signal_set_wakeup_fd(PyObject *self, PyObject *args)
58 +{
59 + struct stat buf;
60 + int fd, old_fd;
61 + if (!PyArg_ParseTuple(args, "i:set_wakeup_fd", &fd))
62 + return NULL;
63 +#ifdef WITH_THREAD
64 + if (PyThread_get_thread_ident() != main_thread) {
65 + PyErr_SetString(PyExc_ValueError,
66 + "set_wakeup_fd only works in main thread");
67 + return NULL;
68 + }
69 +#endif
70 + if (fd != -1 && fstat(fd, &buf) != 0) {
71 + PyErr_SetString(PyExc_ValueError, "invalid fd");
72 + return NULL;
73 + }
74 + old_fd = wakeup_fd;
75 + wakeup_fd = fd;
76 + return PyLong_FromLong(old_fd);
77 +}
78 +
79 +PyDoc_STRVAR(set_wakeup_fd_doc,
80 +"set_wakeup_fd(fd) -> fd\n\
81 +\n\
82 +Sets the fd to be written to (with '\\0') when a signal\n\
83 +comes in. A library can use this to wakeup select or poll.\n\
84 +The previous fd is returned.\n\
85 +\n\
86 +The fd must be non-blocking.");
87 +
88 +/* C API for the same, without all the error checking */
89 +int
90 +PySignal_SetWakeupFd(int fd)
91 +{
92 + int old_fd = wakeup_fd;
93 + if (fd < 0)
94 + fd = -1;
95 + wakeup_fd = fd;
96 + return old_fd;
97 +}
98 +
99 +
100 /* List of functions defined in the module */
101 static PyMethodDef signal_methods[] = {
102 #ifdef HAVE_ALARM
103 @@ -271,6 +322,7 @@
104 #endif
105 {"signal", signal_signal, METH_VARARGS, signal_doc},
106 {"getsignal", signal_getsignal, METH_VARARGS, getsignal_doc},
107 + {"set_wakeup_fd", signal_set_wakeup_fd, METH_VARARGS, set_wakeup_fd_doc},
108 #ifdef HAVE_PAUSE
109 {"pause", (PyCFunction)signal_pause,
110 METH_NOARGS,pause_doc},