Does messing with signal handlers and longjmp affect Python interpreter? I'm trying to find solution for problem, described in http://groups.google.com/group/comp.lang.python/browse_thread/thread/98cbae94ca4beefb/9d4d96fd0dd9fbc3 and came up with test application. It works well but i'm not sure it is ok for long-running python interpreter?
#include <Python.h> #include <signal.h> #include <setjmp.h> const char *py_source = "def fn():\n" " yield 1\n"; jmp_buf env; enum _ { detect, no, yes } has_buggy_gen_iternext = detect; static sighandler_t old_abrt = SIG_DFL; void signal_handler (int sig) { if (sig == SIGABRT) longjmp(env, 1); } int main (int argc, char *argv[]) { Py_Initialize(); PyObject *globals = PyDict_New(); // insert function code into interpreter PyObject *code = PyRun_String(py_source, Py_file_input, globals, NULL); Py_DECREF(code); // compile call to the function code = Py_CompileString("fn()", "<string>", Py_eval_input); // do call PyObject *gen = PyEval_EvalCode((PyCodeObject *)code, globals, NULL); gen = PyObject_GetIter((PyObject *)gen); // detect if we are using bad Python interpreter if (has_buggy_gen_iternext == detect) { if (setjmp(env) == 0) // first time, set signal handler old_abrt = signal(SIGABRT, signal_handler); else { // jumped here from signal handler -- bad Python has_buggy_gen_iternext = yes; signal(SIGABRT, old_abrt); } } if (has_buggy_gen_iternext == yes) printf("generators are disabled\n"); else { // iterate result PyObject *item; while ((item = PyIter_Next(gen))) { printf("> %ld\n", PyInt_AsLong(item)); Py_DECREF(item); } if (has_buggy_gen_iternext == detect) { // ok, restore old signal handler has_buggy_gen_iternext = no; signal(SIGABRT, old_abrt); } } Py_DECREF(gen); Py_DECREF(code); Py_DECREF(globals); Py_Finalize(); return 0; } -- http://mail.python.org/mailman/listinfo/python-list