blob: 3549af5367b9f2fab6105cf5b9302a3b5a14a2ac [file] [log] [blame]
Victor Stinner024e37a2011-03-31 01:31:06 +02001#include "Python.h"
2#include "pythread.h"
3#include <signal.h>
4#include <object.h>
5#include <frameobject.h>
6#include <signal.h>
7
Victor Stinner96994402011-04-07 11:37:19 +02008/* Allocate at maximum 100 MB of the stack to raise the stack overflow */
9#define STACK_OVERFLOW_MAX_SIZE (100*1024*1024)
10
Victor Stinner024e37a2011-03-31 01:31:06 +020011#ifdef WITH_THREAD
12# define FAULTHANDLER_LATER
13#endif
14
15#ifndef MS_WINDOWS
Victor Stinnerd727e232011-04-01 12:13:55 +020016 /* register() is useless on Windows, because only SIGSEGV, SIGABRT and
17 SIGILL can be handled by the process, and these signals can only be used
18 with enable(), not using register() */
Victor Stinner024e37a2011-03-31 01:31:06 +020019# define FAULTHANDLER_USER
20#endif
21
22#define PUTS(fd, str) write(fd, str, strlen(str))
23
24#ifdef HAVE_SIGACTION
25typedef struct sigaction _Py_sighandler_t;
26#else
27typedef PyOS_sighandler_t _Py_sighandler_t;
28#endif
29
30typedef struct {
31 int signum;
32 int enabled;
33 const char* name;
34 _Py_sighandler_t previous;
35 int all_threads;
36} fault_handler_t;
37
38static struct {
39 int enabled;
40 PyObject *file;
41 int fd;
42 int all_threads;
Victor Stinnera4de6d82011-04-09 00:47:23 +020043 PyInterpreterState *interp;
Victor Stinner024e37a2011-03-31 01:31:06 +020044} fatal_error = {0, NULL, -1, 0};
45
46#ifdef FAULTHANDLER_LATER
47static struct {
48 PyObject *file;
49 int fd;
Victor Stinner94189322011-04-08 13:00:31 +020050 PY_TIMEOUT_T timeout_us; /* timeout in microseconds */
Victor Stinner024e37a2011-03-31 01:31:06 +020051 int repeat;
Victor Stinner024e37a2011-03-31 01:31:06 +020052 PyInterpreterState *interp;
53 int exit;
Victor Stinnerc790a532011-04-08 13:39:59 +020054 char *header;
55 size_t header_len;
Victor Stinnerde10f402011-04-08 12:57:06 +020056 /* The main thread always hold this lock. It is only released when
57 faulthandler_thread() is interrupted until this thread exits, or at
58 Python exit. */
Victor Stinner024e37a2011-03-31 01:31:06 +020059 PyThread_type_lock cancel_event;
60 /* released by child thread when joined */
Victor Stinnerde10f402011-04-08 12:57:06 +020061 PyThread_type_lock running;
Victor Stinner024e37a2011-03-31 01:31:06 +020062} thread;
63#endif
64
65#ifdef FAULTHANDLER_USER
66typedef struct {
67 int enabled;
68 PyObject *file;
69 int fd;
70 int all_threads;
71 _Py_sighandler_t previous;
Victor Stinner44378d42011-04-01 15:37:12 +020072 PyInterpreterState *interp;
Victor Stinner024e37a2011-03-31 01:31:06 +020073} user_signal_t;
74
75static user_signal_t *user_signals;
76
77/* the following macros come from Python: Modules/signalmodule.c */
78#if defined(PYOS_OS2) && !defined(PYCC_GCC)
79#define NSIG 12
80#endif
81#ifndef NSIG
82# if defined(_NSIG)
83# define NSIG _NSIG /* For BSD/SysV */
84# elif defined(_SIGMAX)
85# define NSIG (_SIGMAX + 1) /* For QNX */
86# elif defined(SIGMAX)
87# define NSIG (SIGMAX + 1) /* For djgpp */
88# else
89# define NSIG 64 /* Use a reasonable default value */
90# endif
91#endif
92
93#endif /* FAULTHANDLER_USER */
94
95
96static fault_handler_t faulthandler_handlers[] = {
97#ifdef SIGBUS
98 {SIGBUS, 0, "Bus error", },
99#endif
100#ifdef SIGILL
101 {SIGILL, 0, "Illegal instruction", },
102#endif
103 {SIGFPE, 0, "Floating point exception", },
Victor Stinnerd727e232011-04-01 12:13:55 +0200104 {SIGABRT, 0, "Aborted", },
Victor Stinner024e37a2011-03-31 01:31:06 +0200105 /* define SIGSEGV at the end to make it the default choice if searching the
106 handler fails in faulthandler_fatal_error() */
107 {SIGSEGV, 0, "Segmentation fault", }
108};
109static const unsigned char faulthandler_nsignals = \
110 sizeof(faulthandler_handlers) / sizeof(faulthandler_handlers[0]);
111
112#ifdef HAVE_SIGALTSTACK
113static stack_t stack;
114#endif
115
116
117/* Get the file descriptor of a file by calling its fileno() method and then
118 call its flush() method.
119
120 If file is NULL or Py_None, use sys.stderr as the new file.
121
122 On success, return the new file and write the file descriptor into *p_fd.
123 On error, return NULL. */
124
125static PyObject*
126faulthandler_get_fileno(PyObject *file, int *p_fd)
127{
128 PyObject *result;
129 long fd_long;
130 int fd;
131
132 if (file == NULL || file == Py_None) {
133 file = PySys_GetObject("stderr");
134 if (file == NULL) {
135 PyErr_SetString(PyExc_RuntimeError, "unable to get sys.stderr");
136 return NULL;
137 }
138 }
139
140 result = PyObject_CallMethod(file, "fileno", "");
141 if (result == NULL)
142 return NULL;
143
144 fd = -1;
145 if (PyLong_Check(result)) {
146 fd_long = PyLong_AsLong(result);
147 if (0 <= fd_long && fd_long < INT_MAX)
148 fd = (int)fd_long;
149 }
150 Py_DECREF(result);
151
152 if (fd == -1) {
153 PyErr_SetString(PyExc_RuntimeError,
154 "file.fileno() is not a valid file descriptor");
155 return NULL;
156 }
157
158 result = PyObject_CallMethod(file, "flush", "");
159 if (result != NULL)
160 Py_DECREF(result);
161 else {
162 /* ignore flush() error */
163 PyErr_Clear();
164 }
165 *p_fd = fd;
166 return file;
167}
168
Victor Stinnera4de6d82011-04-09 00:47:23 +0200169/* Get the state of the current thread: only call this function if the current
170 thread holds the GIL. Raise an exception on error. */
171static PyThreadState*
172get_thread_state(void)
173{
174 PyThreadState *tstate = PyThreadState_Get();
175 if (tstate == NULL) {
176 PyErr_SetString(PyExc_RuntimeError,
177 "unable to get the current thread state");
178 return NULL;
179 }
180 return tstate;
181}
182
Victor Stinner024e37a2011-03-31 01:31:06 +0200183static PyObject*
184faulthandler_dump_traceback_py(PyObject *self,
185 PyObject *args, PyObject *kwargs)
186{
187 static char *kwlist[] = {"file", "all_threads", NULL};
188 PyObject *file = NULL;
Victor Stinner7bba62f2011-05-07 12:43:00 +0200189 int all_threads = 1;
Victor Stinner024e37a2011-03-31 01:31:06 +0200190 PyThreadState *tstate;
191 const char *errmsg;
192 int fd;
193
194 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
195 "|Oi:dump_traceback", kwlist,
196 &file, &all_threads))
197 return NULL;
198
199 file = faulthandler_get_fileno(file, &fd);
200 if (file == NULL)
201 return NULL;
202
Victor Stinnera4de6d82011-04-09 00:47:23 +0200203 tstate = get_thread_state();
204 if (tstate == NULL)
Victor Stinner024e37a2011-03-31 01:31:06 +0200205 return NULL;
Victor Stinner024e37a2011-03-31 01:31:06 +0200206
207 if (all_threads) {
208 errmsg = _Py_DumpTracebackThreads(fd, tstate->interp, tstate);
209 if (errmsg != NULL) {
210 PyErr_SetString(PyExc_RuntimeError, errmsg);
211 return NULL;
212 }
213 }
214 else {
215 _Py_DumpTraceback(fd, tstate);
216 }
217 Py_RETURN_NONE;
218}
219
220
Victor Stinnerd727e232011-04-01 12:13:55 +0200221/* Handler of SIGSEGV, SIGFPE, SIGABRT, SIGBUS and SIGILL signals.
Victor Stinner024e37a2011-03-31 01:31:06 +0200222
223 Display the current Python traceback, restore the previous handler and call
224 the previous handler.
225
226 On Windows, don't call explictly the previous handler, because Windows
227 signal handler would not be called (for an unknown reason). The execution of
228 the program continues at faulthandler_fatal_error() exit, but the same
229 instruction will raise the same fault (signal), and so the previous handler
230 will be called.
231
232 This function is signal safe and should only call signal safe functions. */
233
234static void
Victor Stinner44e31ba2011-04-07 11:39:03 +0200235faulthandler_fatal_error(int signum)
Victor Stinner024e37a2011-03-31 01:31:06 +0200236{
237 const int fd = fatal_error.fd;
238 unsigned int i;
239 fault_handler_t *handler = NULL;
240 PyThreadState *tstate;
Victor Stinnerc9256172011-05-07 12:20:11 +0200241 int save_errno = errno;
Victor Stinner024e37a2011-03-31 01:31:06 +0200242
243 if (!fatal_error.enabled)
244 return;
245
246 for (i=0; i < faulthandler_nsignals; i++) {
247 handler = &faulthandler_handlers[i];
248 if (handler->signum == signum)
249 break;
250 }
251 if (handler == NULL) {
252 /* faulthandler_nsignals == 0 (unlikely) */
253 return;
254 }
255
256 /* restore the previous handler */
257#ifdef HAVE_SIGACTION
258 (void)sigaction(handler->signum, &handler->previous, NULL);
259#else
260 (void)signal(handler->signum, handler->previous);
261#endif
262 handler->enabled = 0;
263
264 PUTS(fd, "Fatal Python error: ");
265 PUTS(fd, handler->name);
266 PUTS(fd, "\n\n");
267
Victor Stinnerff4cd882011-04-07 11:50:25 +0200268#ifdef WITH_THREAD
Victor Stinnerd727e232011-04-01 12:13:55 +0200269 /* SIGSEGV, SIGFPE, SIGABRT, SIGBUS and SIGILL are synchronous signals and
270 so are delivered to the thread that caused the fault. Get the Python
271 thread state of the current thread.
Victor Stinner024e37a2011-03-31 01:31:06 +0200272
273 PyThreadState_Get() doesn't give the state of the thread that caused the
274 fault if the thread released the GIL, and so this function cannot be
275 used. Read the thread local storage (TLS) instead: call
276 PyGILState_GetThisThreadState(). */
277 tstate = PyGILState_GetThisThreadState();
Victor Stinnerff4cd882011-04-07 11:50:25 +0200278#else
279 tstate = PyThreadState_Get();
280#endif
Victor Stinner024e37a2011-03-31 01:31:06 +0200281
282 if (fatal_error.all_threads)
Victor Stinnera4de6d82011-04-09 00:47:23 +0200283 _Py_DumpTracebackThreads(fd, fatal_error.interp, tstate);
284 else {
285 if (tstate != NULL)
286 _Py_DumpTraceback(fd, tstate);
287 }
Victor Stinner024e37a2011-03-31 01:31:06 +0200288
Victor Stinnerc9256172011-05-07 12:20:11 +0200289 errno = save_errno;
Victor Stinnerbc6a4db2011-04-01 12:08:57 +0200290#ifdef MS_WINDOWS
291 if (signum == SIGSEGV) {
292 /* don't call explictly the previous handler for SIGSEGV in this signal
293 handler, because the Windows signal handler would not be called */
294 return;
295 }
Victor Stinner024e37a2011-03-31 01:31:06 +0200296#endif
Victor Stinnerbc6a4db2011-04-01 12:08:57 +0200297 /* call the previous signal handler: it is called immediatly if we use
298 sigaction() thanks to SA_NODEFER flag, otherwise it is deferred */
299 raise(signum);
Victor Stinner024e37a2011-03-31 01:31:06 +0200300}
301
Victor Stinnerd727e232011-04-01 12:13:55 +0200302/* Install the handler for fatal signals, faulthandler_fatal_error(). */
Victor Stinner024e37a2011-03-31 01:31:06 +0200303
304static PyObject*
305faulthandler_enable(PyObject *self, PyObject *args, PyObject *kwargs)
306{
307 static char *kwlist[] = {"file", "all_threads", NULL};
308 PyObject *file = NULL;
Victor Stinner7bba62f2011-05-07 12:43:00 +0200309 int all_threads = 1;
Victor Stinner024e37a2011-03-31 01:31:06 +0200310 unsigned int i;
311 fault_handler_t *handler;
312#ifdef HAVE_SIGACTION
313 struct sigaction action;
314#endif
315 int err;
316 int fd;
Victor Stinnera4de6d82011-04-09 00:47:23 +0200317 PyThreadState *tstate;
Victor Stinner024e37a2011-03-31 01:31:06 +0200318
319 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
320 "|Oi:enable", kwlist, &file, &all_threads))
321 return NULL;
322
323 file = faulthandler_get_fileno(file, &fd);
324 if (file == NULL)
325 return NULL;
326
Victor Stinnera4de6d82011-04-09 00:47:23 +0200327 tstate = get_thread_state();
328 if (tstate == NULL)
329 return NULL;
330
Victor Stinner024e37a2011-03-31 01:31:06 +0200331 Py_XDECREF(fatal_error.file);
332 Py_INCREF(file);
333 fatal_error.file = file;
334 fatal_error.fd = fd;
335 fatal_error.all_threads = all_threads;
Victor Stinnera4de6d82011-04-09 00:47:23 +0200336 fatal_error.interp = tstate->interp;
Victor Stinner024e37a2011-03-31 01:31:06 +0200337
338 if (!fatal_error.enabled) {
339 fatal_error.enabled = 1;
340
341 for (i=0; i < faulthandler_nsignals; i++) {
342 handler = &faulthandler_handlers[i];
343#ifdef HAVE_SIGACTION
Victor Stinner44e31ba2011-04-07 11:39:03 +0200344 action.sa_handler = faulthandler_fatal_error;
Victor Stinner024e37a2011-03-31 01:31:06 +0200345 sigemptyset(&action.sa_mask);
346 /* Do not prevent the signal from being received from within
347 its own signal handler */
348 action.sa_flags = SA_NODEFER;
349#ifdef HAVE_SIGALTSTACK
350 if (stack.ss_sp != NULL) {
351 /* Call the signal handler on an alternate signal stack
352 provided by sigaltstack() */
353 action.sa_flags |= SA_ONSTACK;
354 }
355#endif
356 err = sigaction(handler->signum, &action, &handler->previous);
357#else
358 handler->previous = signal(handler->signum,
359 faulthandler_fatal_error);
360 err = (handler->previous == SIG_ERR);
361#endif
362 if (err) {
363 PyErr_SetFromErrno(PyExc_RuntimeError);
364 return NULL;
365 }
366 handler->enabled = 1;
367 }
368 }
369 Py_RETURN_NONE;
370}
371
372static void
373faulthandler_disable(void)
374{
375 unsigned int i;
376 fault_handler_t *handler;
377
378 if (fatal_error.enabled) {
379 fatal_error.enabled = 0;
380 for (i=0; i < faulthandler_nsignals; i++) {
381 handler = &faulthandler_handlers[i];
382 if (!handler->enabled)
383 continue;
384#ifdef HAVE_SIGACTION
385 (void)sigaction(handler->signum, &handler->previous, NULL);
386#else
387 (void)signal(handler->signum, handler->previous);
388#endif
389 handler->enabled = 0;
390 }
391 }
392
393 Py_CLEAR(fatal_error.file);
394}
395
396static PyObject*
397faulthandler_disable_py(PyObject *self)
398{
399 if (!fatal_error.enabled) {
400 Py_INCREF(Py_False);
401 return Py_False;
402 }
403 faulthandler_disable();
404 Py_INCREF(Py_True);
405 return Py_True;
406}
407
408static PyObject*
409faulthandler_is_enabled(PyObject *self)
410{
411 return PyBool_FromLong(fatal_error.enabled);
412}
413
414#ifdef FAULTHANDLER_LATER
415
416static void
417faulthandler_thread(void *unused)
418{
419 PyLockStatus st;
420 const char* errmsg;
421 PyThreadState *current;
422 int ok;
Victor Stinnercf2a8072011-04-19 23:30:57 +0200423#if defined(HAVE_PTHREAD_SIGMASK) && !defined(HAVE_BROKEN_PTHREAD_SIGMASK)
Victor Stinnerda9edae2011-04-04 11:05:21 +0200424 sigset_t set;
425
426 /* we don't want to receive any signal */
427 sigfillset(&set);
Victor Stinnerda9edae2011-04-04 11:05:21 +0200428 pthread_sigmask(SIG_SETMASK, &set, NULL);
Victor Stinnerda9edae2011-04-04 11:05:21 +0200429#endif
Victor Stinner024e37a2011-03-31 01:31:06 +0200430
431 do {
432 st = PyThread_acquire_lock_timed(thread.cancel_event,
Victor Stinner94189322011-04-08 13:00:31 +0200433 thread.timeout_us, 0);
Victor Stinner024e37a2011-03-31 01:31:06 +0200434 if (st == PY_LOCK_ACQUIRED) {
Victor Stinnerde10f402011-04-08 12:57:06 +0200435 PyThread_release_lock(thread.cancel_event);
Victor Stinner024e37a2011-03-31 01:31:06 +0200436 break;
437 }
438 /* Timeout => dump traceback */
439 assert(st == PY_LOCK_FAILURE);
440
441 /* get the thread holding the GIL, NULL if no thread hold the GIL */
442 current = _Py_atomic_load_relaxed(&_PyThreadState_Current);
443
Victor Stinnerc790a532011-04-08 13:39:59 +0200444 write(thread.fd, thread.header, thread.header_len);
445
Victor Stinner024e37a2011-03-31 01:31:06 +0200446 errmsg = _Py_DumpTracebackThreads(thread.fd, thread.interp, current);
447 ok = (errmsg == NULL);
448
449 if (thread.exit)
450 _exit(1);
451 } while (ok && thread.repeat);
452
453 /* The only way out */
Victor Stinnerde10f402011-04-08 12:57:06 +0200454 PyThread_release_lock(thread.running);
Victor Stinner024e37a2011-03-31 01:31:06 +0200455}
456
457static void
Victor Stinnerde10f402011-04-08 12:57:06 +0200458cancel_dump_tracebacks_later(void)
Victor Stinner024e37a2011-03-31 01:31:06 +0200459{
Victor Stinnerde10f402011-04-08 12:57:06 +0200460 /* notify cancellation */
461 PyThread_release_lock(thread.cancel_event);
462
Victor Stinnera4d4f1b2011-04-01 03:00:05 +0200463 /* Wait for thread to join */
Victor Stinnerde10f402011-04-08 12:57:06 +0200464 PyThread_acquire_lock(thread.running, 1);
465 PyThread_release_lock(thread.running);
466
467 /* The main thread should always hold the cancel_event lock */
468 PyThread_acquire_lock(thread.cancel_event, 1);
469
Victor Stinner024e37a2011-03-31 01:31:06 +0200470 Py_CLEAR(thread.file);
Victor Stinnerc790a532011-04-08 13:39:59 +0200471 if (thread.header) {
472 free(thread.header);
473 thread.header = NULL;
474 }
475}
476
477static char*
478format_timeout(double timeout)
479{
480 unsigned long us, sec, min, hour;
481 double intpart, fracpart;
482 char buffer[100];
483
484 fracpart = modf(timeout, &intpart);
485 sec = (unsigned long)intpart;
486 us = (unsigned long)(fracpart * 1e6);
487 min = sec / 60;
488 sec %= 60;
489 hour = min / 60;
490 min %= 60;
491
492 if (us != 0)
493 PyOS_snprintf(buffer, sizeof(buffer),
494 "Timeout (%lu:%02lu:%02lu.%06lu)!\n",
495 hour, min, sec, us);
496 else
497 PyOS_snprintf(buffer, sizeof(buffer),
498 "Timeout (%lu:%02lu:%02lu)!\n",
499 hour, min, sec);
500
501 return strdup(buffer);
Victor Stinner024e37a2011-03-31 01:31:06 +0200502}
503
504static PyObject*
Victor Stinner96994402011-04-07 11:37:19 +0200505faulthandler_dump_tracebacks_later(PyObject *self,
506 PyObject *args, PyObject *kwargs)
Victor Stinner024e37a2011-03-31 01:31:06 +0200507{
508 static char *kwlist[] = {"timeout", "repeat", "file", "exit", NULL};
509 double timeout;
Victor Stinner94189322011-04-08 13:00:31 +0200510 PY_TIMEOUT_T timeout_us;
Victor Stinner024e37a2011-03-31 01:31:06 +0200511 int repeat = 0;
512 PyObject *file = NULL;
513 int fd;
514 int exit = 0;
Victor Stinner96994402011-04-07 11:37:19 +0200515 PyThreadState *tstate;
Victor Stinnerc790a532011-04-08 13:39:59 +0200516 char *header;
517 size_t header_len;
Victor Stinner024e37a2011-03-31 01:31:06 +0200518
519 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
520 "d|iOi:dump_tracebacks_later", kwlist,
521 &timeout, &repeat, &file, &exit))
522 return NULL;
Victor Stinnerc790a532011-04-08 13:39:59 +0200523 if ((timeout * 1e6) >= (double) PY_TIMEOUT_MAX) {
Victor Stinner024e37a2011-03-31 01:31:06 +0200524 PyErr_SetString(PyExc_OverflowError, "timeout value is too large");
525 return NULL;
526 }
Victor Stinnerc790a532011-04-08 13:39:59 +0200527 timeout_us = (PY_TIMEOUT_T)(timeout * 1e6);
Victor Stinner94189322011-04-08 13:00:31 +0200528 if (timeout_us <= 0) {
Victor Stinner024e37a2011-03-31 01:31:06 +0200529 PyErr_SetString(PyExc_ValueError, "timeout must be greater than 0");
530 return NULL;
531 }
532
Victor Stinnera4de6d82011-04-09 00:47:23 +0200533 tstate = get_thread_state();
534 if (tstate == NULL)
Victor Stinner96994402011-04-07 11:37:19 +0200535 return NULL;
Victor Stinner96994402011-04-07 11:37:19 +0200536
Victor Stinner024e37a2011-03-31 01:31:06 +0200537 file = faulthandler_get_fileno(file, &fd);
538 if (file == NULL)
539 return NULL;
540
Victor Stinnerc790a532011-04-08 13:39:59 +0200541 /* format the timeout */
542 header = format_timeout(timeout);
543 if (header == NULL)
544 return PyErr_NoMemory();
545 header_len = strlen(header);
546
Victor Stinner024e37a2011-03-31 01:31:06 +0200547 /* Cancel previous thread, if running */
Victor Stinnerde10f402011-04-08 12:57:06 +0200548 cancel_dump_tracebacks_later();
Victor Stinner024e37a2011-03-31 01:31:06 +0200549
550 Py_XDECREF(thread.file);
551 Py_INCREF(file);
552 thread.file = file;
553 thread.fd = fd;
Victor Stinner94189322011-04-08 13:00:31 +0200554 thread.timeout_us = timeout_us;
Victor Stinner024e37a2011-03-31 01:31:06 +0200555 thread.repeat = repeat;
Victor Stinner96994402011-04-07 11:37:19 +0200556 thread.interp = tstate->interp;
Victor Stinner024e37a2011-03-31 01:31:06 +0200557 thread.exit = exit;
Victor Stinnerc790a532011-04-08 13:39:59 +0200558 thread.header = header;
559 thread.header_len = header_len;
Victor Stinner024e37a2011-03-31 01:31:06 +0200560
561 /* Arm these locks to serve as events when released */
Victor Stinnerde10f402011-04-08 12:57:06 +0200562 PyThread_acquire_lock(thread.running, 1);
Victor Stinner024e37a2011-03-31 01:31:06 +0200563
Victor Stinner024e37a2011-03-31 01:31:06 +0200564 if (PyThread_start_new_thread(faulthandler_thread, NULL) == -1) {
Victor Stinnerde10f402011-04-08 12:57:06 +0200565 PyThread_release_lock(thread.running);
Victor Stinner024e37a2011-03-31 01:31:06 +0200566 Py_CLEAR(thread.file);
Victor Stinnerc790a532011-04-08 13:39:59 +0200567 free(header);
568 thread.header = NULL;
Victor Stinner024e37a2011-03-31 01:31:06 +0200569 PyErr_SetString(PyExc_RuntimeError,
570 "unable to start watchdog thread");
571 return NULL;
572 }
573
574 Py_RETURN_NONE;
575}
576
577static PyObject*
Victor Stinner702624e2011-03-31 03:42:34 +0200578faulthandler_cancel_dump_tracebacks_later_py(PyObject *self)
Victor Stinner024e37a2011-03-31 01:31:06 +0200579{
Victor Stinnerde10f402011-04-08 12:57:06 +0200580 cancel_dump_tracebacks_later();
Victor Stinner024e37a2011-03-31 01:31:06 +0200581 Py_RETURN_NONE;
582}
583#endif /* FAULTHANDLER_LATER */
584
585#ifdef FAULTHANDLER_USER
586/* Handler of user signals (e.g. SIGUSR1).
587
588 Dump the traceback of the current thread, or of all threads if
589 thread.all_threads is true.
590
591 This function is signal safe and should only call signal safe functions. */
592
593static void
594faulthandler_user(int signum)
595{
596 user_signal_t *user;
597 PyThreadState *tstate;
Victor Stinnerc9256172011-05-07 12:20:11 +0200598 int save_errno = errno;
Victor Stinner024e37a2011-03-31 01:31:06 +0200599
600 user = &user_signals[signum];
601 if (!user->enabled)
602 return;
603
Victor Stinnerff4cd882011-04-07 11:50:25 +0200604#ifdef WITH_THREAD
Victor Stinner024e37a2011-03-31 01:31:06 +0200605 /* PyThreadState_Get() doesn't give the state of the current thread if
606 the thread doesn't hold the GIL. Read the thread local storage (TLS)
607 instead: call PyGILState_GetThisThreadState(). */
608 tstate = PyGILState_GetThisThreadState();
Victor Stinnerff4cd882011-04-07 11:50:25 +0200609#else
610 tstate = PyThreadState_Get();
611#endif
Victor Stinner024e37a2011-03-31 01:31:06 +0200612
613 if (user->all_threads)
Victor Stinner44378d42011-04-01 15:37:12 +0200614 _Py_DumpTracebackThreads(user->fd, user->interp, tstate);
615 else {
616 if (tstate == NULL)
617 return;
Victor Stinner024e37a2011-03-31 01:31:06 +0200618 _Py_DumpTraceback(user->fd, tstate);
Victor Stinner44378d42011-04-01 15:37:12 +0200619 }
Victor Stinnerc9256172011-05-07 12:20:11 +0200620 errno = save_errno;
Victor Stinner44378d42011-04-01 15:37:12 +0200621}
622
623static int
624check_signum(int signum)
625{
626 unsigned int i;
627
628 for (i=0; i < faulthandler_nsignals; i++) {
629 if (faulthandler_handlers[i].signum == signum) {
630 PyErr_Format(PyExc_RuntimeError,
631 "signal %i cannot be registered, "
632 "use enable() instead",
633 signum);
634 return 0;
635 }
636 }
637 if (signum < 1 || NSIG <= signum) {
638 PyErr_SetString(PyExc_ValueError, "signal number out of range");
639 return 0;
640 }
641 return 1;
Victor Stinner024e37a2011-03-31 01:31:06 +0200642}
643
644static PyObject*
645faulthandler_register(PyObject *self,
646 PyObject *args, PyObject *kwargs)
647{
648 static char *kwlist[] = {"signum", "file", "all_threads", NULL};
649 int signum;
650 PyObject *file = NULL;
Victor Stinner7bba62f2011-05-07 12:43:00 +0200651 int all_threads = 1;
Victor Stinner024e37a2011-03-31 01:31:06 +0200652 int fd;
Victor Stinner024e37a2011-03-31 01:31:06 +0200653 user_signal_t *user;
654 _Py_sighandler_t previous;
655#ifdef HAVE_SIGACTION
656 struct sigaction action;
657#endif
Victor Stinner44378d42011-04-01 15:37:12 +0200658 PyThreadState *tstate;
Victor Stinner024e37a2011-03-31 01:31:06 +0200659 int err;
660
661 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
662 "i|Oi:register", kwlist,
663 &signum, &file, &all_threads))
664 return NULL;
665
Victor Stinner44378d42011-04-01 15:37:12 +0200666 if (!check_signum(signum))
Victor Stinner024e37a2011-03-31 01:31:06 +0200667 return NULL;
Victor Stinner024e37a2011-03-31 01:31:06 +0200668
Victor Stinnera4de6d82011-04-09 00:47:23 +0200669 tstate = get_thread_state();
670 if (tstate == NULL)
Victor Stinner44378d42011-04-01 15:37:12 +0200671 return NULL;
Victor Stinner024e37a2011-03-31 01:31:06 +0200672
673 file = faulthandler_get_fileno(file, &fd);
674 if (file == NULL)
675 return NULL;
676
677 if (user_signals == NULL) {
678 user_signals = calloc(NSIG, sizeof(user_signal_t));
679 if (user_signals == NULL)
680 return PyErr_NoMemory();
681 }
682 user = &user_signals[signum];
683
684 if (!user->enabled) {
685#ifdef HAVE_SIGACTION
686 action.sa_handler = faulthandler_user;
687 sigemptyset(&action.sa_mask);
688 /* if the signal is received while the kernel is executing a system
689 call, try to restart the system call instead of interrupting it and
690 return EINTR */
691 action.sa_flags = SA_RESTART;
692#ifdef HAVE_SIGALTSTACK
693 if (stack.ss_sp != NULL) {
694 /* Call the signal handler on an alternate signal stack
695 provided by sigaltstack() */
696 action.sa_flags |= SA_ONSTACK;
697 }
698#endif
699 err = sigaction(signum, &action, &previous);
700#else
701 previous = signal(signum, faulthandler_user);
702 err = (previous == SIG_ERR);
703#endif
704 if (err) {
705 PyErr_SetFromErrno(PyExc_OSError);
706 return NULL;
707 }
708 }
709
710 Py_XDECREF(user->file);
711 Py_INCREF(file);
712 user->file = file;
713 user->fd = fd;
714 user->all_threads = all_threads;
715 user->previous = previous;
Victor Stinner44378d42011-04-01 15:37:12 +0200716 user->interp = tstate->interp;
Victor Stinner024e37a2011-03-31 01:31:06 +0200717 user->enabled = 1;
718
719 Py_RETURN_NONE;
720}
721
722static int
723faulthandler_unregister(user_signal_t *user, int signum)
724{
Victor Stinnera01ca122011-04-01 12:56:17 +0200725 if (!user->enabled)
Victor Stinner024e37a2011-03-31 01:31:06 +0200726 return 0;
727 user->enabled = 0;
728#ifdef HAVE_SIGACTION
729 (void)sigaction(signum, &user->previous, NULL);
730#else
731 (void)signal(signum, user->previous);
732#endif
733 Py_CLEAR(user->file);
734 user->fd = -1;
735 return 1;
736}
737
738static PyObject*
739faulthandler_unregister_py(PyObject *self, PyObject *args)
740{
741 int signum;
742 user_signal_t *user;
743 int change;
744
745 if (!PyArg_ParseTuple(args, "i:unregister", &signum))
746 return NULL;
747
Victor Stinner44378d42011-04-01 15:37:12 +0200748 if (!check_signum(signum))
Victor Stinner024e37a2011-03-31 01:31:06 +0200749 return NULL;
Victor Stinner024e37a2011-03-31 01:31:06 +0200750
Victor Stinnercfa71232011-04-08 12:48:15 +0200751 if (user_signals == NULL)
752 Py_RETURN_FALSE;
753
Victor Stinner024e37a2011-03-31 01:31:06 +0200754 user = &user_signals[signum];
755 change = faulthandler_unregister(user, signum);
756 return PyBool_FromLong(change);
757}
758#endif /* FAULTHANDLER_USER */
759
760
761static PyObject *
762faulthandler_read_null(PyObject *self, PyObject *args)
763{
764 int *x = NULL, y;
765 int release_gil = 0;
766 if (!PyArg_ParseTuple(args, "|i:_read_null", &release_gil))
767 return NULL;
768 if (release_gil) {
769 Py_BEGIN_ALLOW_THREADS
770 y = *x;
771 Py_END_ALLOW_THREADS
772 } else
773 y = *x;
774 return PyLong_FromLong(y);
775
776}
777
778static PyObject *
779faulthandler_sigsegv(PyObject *self, PyObject *args)
780{
781#if defined(MS_WINDOWS)
Victor Stinnerbc6a4db2011-04-01 12:08:57 +0200782 /* For SIGSEGV, faulthandler_fatal_error() restores the previous signal
783 handler and then gives back the execution flow to the program (without
784 calling explicitly the previous error handler). In a normal case, the
Victor Stinner024e37a2011-03-31 01:31:06 +0200785 SIGSEGV was raised by the kernel because of a fault, and so if the
786 program retries to execute the same instruction, the fault will be
787 raised again.
788
789 Here the fault is simulated by a fake SIGSEGV signal raised by the
790 application. We have to raise SIGSEGV at lease twice: once for
791 faulthandler_fatal_error(), and one more time for the previous signal
792 handler. */
793 while(1)
794 raise(SIGSEGV);
795#else
796 raise(SIGSEGV);
797#endif
798 Py_RETURN_NONE;
799}
800
801static PyObject *
802faulthandler_sigfpe(PyObject *self, PyObject *args)
803{
804 /* Do an integer division by zero: raise a SIGFPE on Intel CPU, but not on
805 PowerPC. Use volatile to disable compile-time optimizations. */
806 volatile int x = 1, y = 0, z;
807 z = x / y;
Victor Stinnere0c9a752011-05-09 14:44:26 +0200808 /* if the division by zero didn't raise a SIGFPE (e.g. on PowerPC),
809 raise it manually */
Victor Stinner024e37a2011-03-31 01:31:06 +0200810 raise(SIGFPE);
Victor Stinnere0c9a752011-05-09 14:44:26 +0200811 /* use z to make quiet a compiler warning, but this line
812 is never reached */
813 return PyLong_FromLong(z);
Victor Stinner024e37a2011-03-31 01:31:06 +0200814}
815
Victor Stinnerd727e232011-04-01 12:13:55 +0200816static PyObject *
817faulthandler_sigabrt(PyObject *self, PyObject *args)
818{
Victor Stinner00bc6cc2011-05-10 01:30:03 +0200819#ifdef _MSC_VER
820 /* Visual Studio: configure abort() to not display an error message nor
821 open a popup asking to report the fault. */
822 _set_abort_behavior(0, _WRITE_ABORT_MSG | _CALL_REPORTFAULT);
Victor Stinnerd727e232011-04-01 12:13:55 +0200823#endif
Victor Stinner00bc6cc2011-05-10 01:30:03 +0200824 abort();
Victor Stinnerd727e232011-04-01 12:13:55 +0200825 Py_RETURN_NONE;
826}
827
Victor Stinner024e37a2011-03-31 01:31:06 +0200828#ifdef SIGBUS
829static PyObject *
830faulthandler_sigbus(PyObject *self, PyObject *args)
831{
832 raise(SIGBUS);
833 Py_RETURN_NONE;
834}
835#endif
836
837#ifdef SIGILL
838static PyObject *
839faulthandler_sigill(PyObject *self, PyObject *args)
840{
Victor Stinner024e37a2011-03-31 01:31:06 +0200841 raise(SIGILL);
Victor Stinner024e37a2011-03-31 01:31:06 +0200842 Py_RETURN_NONE;
843}
844#endif
845
846static PyObject *
847faulthandler_fatal_error_py(PyObject *self, PyObject *args)
848{
849 char *message;
850 if (!PyArg_ParseTuple(args, "y:fatal_error", &message))
851 return NULL;
852 Py_FatalError(message);
853 Py_RETURN_NONE;
854}
855
856#if defined(HAVE_SIGALTSTACK) && defined(HAVE_SIGACTION)
Victor Stinnerf0480752011-03-31 11:34:08 +0200857void*
858stack_overflow(void *min_sp, void *max_sp, size_t *depth)
Victor Stinner024e37a2011-03-31 01:31:06 +0200859{
860 /* allocate 4096 bytes on the stack at each call */
861 unsigned char buffer[4096];
Victor Stinnerf0480752011-03-31 11:34:08 +0200862 void *sp = &buffer;
863 *depth += 1;
864 if (sp < min_sp || max_sp < sp)
865 return sp;
Victor Stinner024e37a2011-03-31 01:31:06 +0200866 buffer[0] = 1;
Victor Stinnerf0480752011-03-31 11:34:08 +0200867 buffer[4095] = 0;
868 return stack_overflow(min_sp, max_sp, depth);
869}
870
871static PyObject *
872faulthandler_stack_overflow(PyObject *self)
873{
874 size_t depth, size;
875 void *sp = &depth, *stop;
876
877 depth = 0;
878 stop = stack_overflow(sp - STACK_OVERFLOW_MAX_SIZE,
879 sp + STACK_OVERFLOW_MAX_SIZE,
880 &depth);
881 if (sp < stop)
882 size = stop - sp;
883 else
884 size = sp - stop;
885 PyErr_Format(PyExc_RuntimeError,
886 "unable to raise a stack overflow (allocated %zu bytes "
887 "on the stack, %zu recursive calls)",
888 size, depth);
889 return NULL;
Victor Stinner024e37a2011-03-31 01:31:06 +0200890}
891#endif
892
893
894static int
895faulthandler_traverse(PyObject *module, visitproc visit, void *arg)
896{
897#ifdef FAULTHANDLER_USER
Victor Stinner96994402011-04-07 11:37:19 +0200898 unsigned int signum;
Victor Stinner024e37a2011-03-31 01:31:06 +0200899#endif
900
901#ifdef FAULTHANDLER_LATER
902 Py_VISIT(thread.file);
903#endif
904#ifdef FAULTHANDLER_USER
905 if (user_signals != NULL) {
Victor Stinner96994402011-04-07 11:37:19 +0200906 for (signum=0; signum < NSIG; signum++)
907 Py_VISIT(user_signals[signum].file);
Victor Stinner024e37a2011-03-31 01:31:06 +0200908 }
909#endif
910 Py_VISIT(fatal_error.file);
911 return 0;
912}
913
914PyDoc_STRVAR(module_doc,
915"faulthandler module.");
916
917static PyMethodDef module_methods[] = {
918 {"enable",
919 (PyCFunction)faulthandler_enable, METH_VARARGS|METH_KEYWORDS,
Victor Stinner7bba62f2011-05-07 12:43:00 +0200920 PyDoc_STR("enable(file=sys.stderr, all_threads=True): "
Victor Stinner024e37a2011-03-31 01:31:06 +0200921 "enable the fault handler")},
922 {"disable", (PyCFunction)faulthandler_disable_py, METH_NOARGS,
923 PyDoc_STR("disable(): disable the fault handler")},
924 {"is_enabled", (PyCFunction)faulthandler_is_enabled, METH_NOARGS,
925 PyDoc_STR("is_enabled()->bool: check if the handler is enabled")},
926 {"dump_traceback",
927 (PyCFunction)faulthandler_dump_traceback_py, METH_VARARGS|METH_KEYWORDS,
Victor Stinner7bba62f2011-05-07 12:43:00 +0200928 PyDoc_STR("dump_traceback(file=sys.stderr, all_threads=True): "
Victor Stinner024e37a2011-03-31 01:31:06 +0200929 "dump the traceback of the current thread, or of all threads "
930 "if all_threads is True, into file")},
931#ifdef FAULTHANDLER_LATER
932 {"dump_tracebacks_later",
Victor Stinner96994402011-04-07 11:37:19 +0200933 (PyCFunction)faulthandler_dump_tracebacks_later, METH_VARARGS|METH_KEYWORDS,
934 PyDoc_STR("dump_tracebacks_later(timeout, repeat=False, file=sys.stderrn, exit=False):\n"
Victor Stinner024e37a2011-03-31 01:31:06 +0200935 "dump the traceback of all threads in timeout seconds,\n"
Victor Stinner96994402011-04-07 11:37:19 +0200936 "or each timeout seconds if repeat is True. If exit is True, "
937 "call _exit(1) which is not safe.")},
Victor Stinner024e37a2011-03-31 01:31:06 +0200938 {"cancel_dump_tracebacks_later",
Victor Stinner702624e2011-03-31 03:42:34 +0200939 (PyCFunction)faulthandler_cancel_dump_tracebacks_later_py, METH_NOARGS,
Victor Stinner024e37a2011-03-31 01:31:06 +0200940 PyDoc_STR("cancel_dump_tracebacks_later():\ncancel the previous call "
941 "to dump_tracebacks_later().")},
942#endif
943
944#ifdef FAULTHANDLER_USER
945 {"register",
946 (PyCFunction)faulthandler_register, METH_VARARGS|METH_KEYWORDS,
Victor Stinner7bba62f2011-05-07 12:43:00 +0200947 PyDoc_STR("register(signum, file=sys.stderr, all_threads=True): "
Victor Stinner024e37a2011-03-31 01:31:06 +0200948 "register an handler for the signal 'signum': dump the "
949 "traceback of the current thread, or of all threads if "
950 "all_threads is True, into file")},
951 {"unregister",
952 faulthandler_unregister_py, METH_VARARGS|METH_KEYWORDS,
953 PyDoc_STR("unregister(signum): unregister the handler of the signal "
954 "'signum' registered by register()")},
955#endif
956
957 {"_read_null", faulthandler_read_null, METH_VARARGS,
958 PyDoc_STR("_read_null(release_gil=False): read from NULL, raise "
959 "a SIGSEGV or SIGBUS signal depending on the platform")},
960 {"_sigsegv", faulthandler_sigsegv, METH_VARARGS,
961 PyDoc_STR("_sigsegv(): raise a SIGSEGV signal")},
Victor Stinnerd727e232011-04-01 12:13:55 +0200962 {"_sigabrt", faulthandler_sigabrt, METH_VARARGS,
963 PyDoc_STR("_sigabrt(): raise a SIGABRT signal")},
Victor Stinner024e37a2011-03-31 01:31:06 +0200964 {"_sigfpe", (PyCFunction)faulthandler_sigfpe, METH_NOARGS,
965 PyDoc_STR("_sigfpe(): raise a SIGFPE signal")},
966#ifdef SIGBUS
967 {"_sigbus", (PyCFunction)faulthandler_sigbus, METH_NOARGS,
968 PyDoc_STR("_sigbus(): raise a SIGBUS signal")},
969#endif
970#ifdef SIGILL
971 {"_sigill", (PyCFunction)faulthandler_sigill, METH_NOARGS,
972 PyDoc_STR("_sigill(): raise a SIGILL signal")},
973#endif
974 {"_fatal_error", faulthandler_fatal_error_py, METH_VARARGS,
975 PyDoc_STR("_fatal_error(message): call Py_FatalError(message)")},
976#if defined(HAVE_SIGALTSTACK) && defined(HAVE_SIGACTION)
977 {"_stack_overflow", (PyCFunction)faulthandler_stack_overflow, METH_NOARGS,
978 PyDoc_STR("_stack_overflow(): recursive call to raise a stack overflow")},
979#endif
980 {NULL, NULL} /* terminator */
981};
982
983static struct PyModuleDef module_def = {
984 PyModuleDef_HEAD_INIT,
985 "faulthandler",
986 module_doc,
987 0, /* non negative size to be able to unload the module */
988 module_methods,
989 NULL,
990 faulthandler_traverse,
991 NULL,
992 NULL
993};
994
995PyMODINIT_FUNC
996PyInit_faulthandler(void)
997{
998 return PyModule_Create(&module_def);
999}
1000
1001/* Call faulthandler.enable() if PYTHONFAULTHANDLER environment variable is
1002 defined, or if sys._xoptions has a 'faulthandler' key. */
1003
1004static int
1005faulthandler_env_options(void)
1006{
1007 PyObject *xoptions, *key, *module, *res;
1008 int enable;
1009
1010 if (!Py_GETENV("PYTHONFAULTHANDLER")) {
1011 xoptions = PySys_GetXOptions();
1012 if (xoptions == NULL)
1013 return -1;
1014
1015 key = PyUnicode_FromString("faulthandler");
1016 if (key == NULL)
1017 return -1;
1018
1019 enable = PyDict_Contains(xoptions, key);
1020 Py_DECREF(key);
1021 if (!enable)
1022 return 0;
1023 }
1024 else
1025 enable = 1;
1026
1027 module = PyImport_ImportModule("faulthandler");
1028 if (module == NULL) {
1029 return -1;
1030 }
1031 res = PyObject_CallMethod(module, "enable", "");
1032 Py_DECREF(module);
1033 if (res == NULL)
1034 return -1;
1035 Py_DECREF(res);
1036 return 0;
1037}
1038
1039int _PyFaulthandler_Init(void)
1040{
1041#ifdef HAVE_SIGALTSTACK
1042 int err;
1043
1044 /* Try to allocate an alternate stack for faulthandler() signal handler to
1045 * be able to allocate memory on the stack, even on a stack overflow. If it
1046 * fails, ignore the error. */
1047 stack.ss_flags = 0;
1048 stack.ss_size = SIGSTKSZ;
1049 stack.ss_sp = PyMem_Malloc(stack.ss_size);
1050 if (stack.ss_sp != NULL) {
1051 err = sigaltstack(&stack, NULL);
1052 if (err) {
1053 PyMem_Free(stack.ss_sp);
1054 stack.ss_sp = NULL;
1055 }
1056 }
1057#endif
1058#ifdef FAULTHANDLER_LATER
Victor Stinner024e37a2011-03-31 01:31:06 +02001059 thread.file = NULL;
1060 thread.cancel_event = PyThread_allocate_lock();
Victor Stinnerde10f402011-04-08 12:57:06 +02001061 thread.running = PyThread_allocate_lock();
1062 if (!thread.cancel_event || !thread.running) {
Victor Stinner024e37a2011-03-31 01:31:06 +02001063 PyErr_SetString(PyExc_RuntimeError,
1064 "could not allocate locks for faulthandler");
1065 return -1;
1066 }
Victor Stinnerde10f402011-04-08 12:57:06 +02001067 PyThread_acquire_lock(thread.cancel_event, 1);
Victor Stinner024e37a2011-03-31 01:31:06 +02001068#endif
1069
1070 return faulthandler_env_options();
1071}
1072
1073void _PyFaulthandler_Fini(void)
1074{
1075#ifdef FAULTHANDLER_USER
Victor Stinnera01ca122011-04-01 12:56:17 +02001076 unsigned int signum;
Victor Stinner024e37a2011-03-31 01:31:06 +02001077#endif
1078
1079#ifdef FAULTHANDLER_LATER
1080 /* later */
Victor Stinnerde10f402011-04-08 12:57:06 +02001081 cancel_dump_tracebacks_later();
Victor Stinner024e37a2011-03-31 01:31:06 +02001082 if (thread.cancel_event) {
Victor Stinnerde10f402011-04-08 12:57:06 +02001083 PyThread_release_lock(thread.cancel_event);
Victor Stinner024e37a2011-03-31 01:31:06 +02001084 PyThread_free_lock(thread.cancel_event);
1085 thread.cancel_event = NULL;
1086 }
Victor Stinnerde10f402011-04-08 12:57:06 +02001087 if (thread.running) {
1088 PyThread_free_lock(thread.running);
1089 thread.running = NULL;
Victor Stinner024e37a2011-03-31 01:31:06 +02001090 }
1091#endif
1092
1093#ifdef FAULTHANDLER_USER
1094 /* user */
1095 if (user_signals != NULL) {
Victor Stinnera01ca122011-04-01 12:56:17 +02001096 for (signum=0; signum < NSIG; signum++)
1097 faulthandler_unregister(&user_signals[signum], signum);
Victor Stinner024e37a2011-03-31 01:31:06 +02001098 free(user_signals);
1099 user_signals = NULL;
1100 }
1101#endif
1102
1103 /* fatal */
1104 faulthandler_disable();
1105#ifdef HAVE_SIGALTSTACK
1106 if (stack.ss_sp != NULL) {
1107 PyMem_Free(stack.ss_sp);
1108 stack.ss_sp = NULL;
1109 }
1110#endif
1111}