[Python-Dev] Strange segfault in Python threads and linux kernel 2.6

Donovan Baarda abo at minkirri.apana.org.au
Fri Jan 21 00:56:00 CET 2005


On Thu, 2005-01-20 at 14:12 +0000, Michael Hudson wrote:
> Donovan Baarda <abo at minkirri.apana.org.au> writes:
> 
> > On Wed, 2005-01-19 at 13:37 +0000, Michael Hudson wrote:
> >> Donovan Baarda <abo at minkirri.apana.org.au> writes:
[...]
> >> The main oddness about python threads (before 2.3) is that they run
> >> with all signals masked.  You could play with a C wrapper (call
> >> setprocmask, then exec fop) to see if this is what is causing the
> >> problem.  But please try 2.4.
> >
> > Python 2.4 does indeed fix the problem. 
> 
> That's good to hear.
[...]

I still don't understand what Linux 2.4 vs Linux 2.6 had to do with it.
Reading the man pages for execve(), pthread_sigmask() and sigprocmask(),
I can see some ambiguities, but mostly only if you do things they warn
against (ie, use sigprocmask() instead of pthread_sigmask() in a
multi-threaded app).

The man page for execve() says that the new process will inherit the
"Process signal mask (see sigprocmask() )". This implies to me it will
inherit the mask from the main process, not the thread's signal mask.

It looks like Linux 2.4 uses the signal mask of the main thread or
process for the execve(), whereas Linux 2.6 uses the thread's signal
mask. Given that execve() replaces the whole process, including all
threads, I dunno if using the thread's mask is right. Could this be a
Linux 2.6 kernel bug?

> > I'm not sure what the correct behaviour should be. The fact that it
> > works in python2.4 feels more like a byproduct of the thread mask change
> > than correct behaviour. 
> 
> Well, getting rid of the thread mask changes was one of the goals of
> the change.

I gathered that... which kinda means the fact that it fixed execvp in
threads is a side effect...(though I also guess it fixed a lot of other
things like this too).

> > To me it seems like execvp() should be setting the signal mask back
> > to defaults or at least the mask of the main process before doing
> > the exec.
> 
> Possibly.  I think the 2.4 change -- not fiddling the process mask at
> all -- is the Right Thing, but that doesn't help 2.3 users.  This has
> all been discussed before at some length, on python-dev and in various
> bug reports on SF.

Would a simple bug-fix for 2.3 be to have os.execvp() set the mask to
something sane before executing C execvp()? Given that Python does not
have any visibility of the procmask...

This might be a good idea regardless as it will protect against this bug
resurfacing in the future if someone decides fiddling with the mask for
threads is a good idea again.

> In your situation, I think the simplest thing you can do is dig out an
> old patch of mine that exposes sigprocmask + co to Python and either
> make a custom Python incorporating the patch and use that, or put the
> code from the patch into an extension module.  Then before execing
> fop, use the new code to set the signal mask to something sane.  Not
> pretty, particularly, but it should work.

The extension module that exposes sigprocmask() is probably best for
now...

-- 
Donovan Baarda <abo at minkirri.apana.org.au>
http://minkirri.apana.org.au/~abo/



More information about the Python-Dev mailing list