Nathaniel Smith added the comment:

Letting Python-level signal handlers run in arbitrary threads is an interesting 
idea, but it's a non-trivial change to Python semantics that may well break 
some programs (previously it was guaranteed that signal handlers couldn't race 
with main thread code), and it doesn't fully fix the bug here (because it's 
common for Python programs to contain threads which don't run Python code, e.g. 
if they use zmq). I can imagine some potential benefits, but I feel like this 
needs some substantial rationale?

OTOH the pthread_kill-based fix I suggested is like 3 lines and AFAICT fixes 
the problem exactly.

> I dislike the idea of transfering the signal to the main thread from another 
> thread in the C signal handler using pthread_kill(). Most code behave very 
> badly when getting a signal, so getting a signal twice is likely to double 
> the pain.

This doesn't make much sense to me... CPython's pretty good at handling EINTR 
these days, and, well, the only case that's different is when you have a signal 
handler that needs to be run and the main thread is blocked in a syscall, which 
is exactly the case that's currently broken? 

> Moreover, pthread_sigmask() can block signals in the main thread for 
> deliberate reasons.

Sure, and with pthread_kill() this would have the effect that the signal would 
be queued by the kernel and delivered after signal is unmasked. That seems like 
pretty sensible semantics to me; in fact it's exactly what you get in 
single-threaded code.

Compare that to right now where AFAICT pthread_sigmask() is pretty useless in 
the presence of threads, because of the thing where if one thread has a signal 
blocked then the kernel will pick another thread to deliver it to.

> From the point of view of the Python signal handler, the current "if 
> (PyThread_get_thread_ident() != main_thread) return 0;" code in the C signal 
> handler is somehow an implicit pthread_sigmask(signal.SIG_BLOCK, range(1, 
> signal.NSIG)) on all threads except of the main thread, whereas Unix gives a 
> fine control on these masks with the pthread_sigmask() function.

That code isn't in the C signal handler, it's in the code that the interpreter 
runs occasionally to check if the C signal handler has been called, right?

----------

_______________________________________
Python tracker <rep...@bugs.python.org>
<http://bugs.python.org/issue21895>
_______________________________________
_______________________________________________
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com

Reply via email to