Trying (not) to crash with libpthread (6.3-RELEASE)

Julian Elischer julian at elischer.org
Sat May 17 02:16:06 UTC 2008


Jille Timmermans wrote:
> Hello,
> 
> I'm trying to catch SIGSEGV, to be able to run 'unchecked' (possibly 
> crashing) code.
> And not letting the entire program die, but just kill that thread.
> So I wrote some testing code.
> But, I ran into a problem; the signal-handler does not work when a 
> thread is created (or something like that).
> The code below crashes on SIGSEGV, but should die in void sigcatcher(int);
> If you uncomment the crashingthread(NULL); line, it will die in the 
> signal handler.
> 
> pthread_create seems to take over signal handling.
> I quickly checked some pthread source, and it seems that it should call 
> my own handler.
> (There might be an exception for some signals, but I didn't found that)
> 
> Can anyone explain me what is happening here ?

yes, you are correct.
I a vain attempt to give something close to the semanticcs defined by
the pthread spec, the pthreads app sets a special thread to do nothing 
but catch signals. Originally when we started the immediate signals
such as SIGSEGV were exempt from this and were delivered to the thread
that caused it immediatly, however it was impossible to do this
effectively and still provide correct sematics for the rest of the
signals. Eventually we just gave up on SIGSEGV because we just 
couldn't get it to work.  We could catch the signal in the
signal thread, but we couldn't get it to deliver it to the
errant thread reliably, (because the errant thread couldn't
run any more at that point).

using top -H you should be able to see the extgra thread in the kernel
waiting for the signals.

This was one of the reasons that 1:1 threading eventually won out in
our threading evaluation period.  In M:N threading the aim is to 
switch threads without kernel involvement, however iti turns out
that to do SIGSEGV and friends properly, you need to re-do the
thread signal mask for every thread with a syscall for every thread
swap which defeats teh whole point.

With 1:1 threads this all "just works"

try libthr. it should work for you.



> 
> -- Jille
> 
> 
> cc -lpthread below.c
> #include <stdlib.h>
> #include <stdio.h>
> #include <unistd.h>
> #include <pthread.h>
> #include <signal.h>
> #include <err.h>
> 
> int success=0;
> 
> void
> sigcatcher(int sig) {
>  printf("[%p] signal %d\n", pthread_self(), sig);
>  printf("Test (probably) succeeded\n");
>  fflush(NULL);
>  success=1;
>  exit(0);
> }
> 
> void *
> crashingthread(void *nada) {
>  /* This will likely crash */
>  char *x=malloc(1);
> 
>  if(signal(SIGSEGV, sigcatcher)==SIG_ERR)
>    err(1, "signal(SIGSEGV, catchz0r)");
> 
>  x[666]=0;
> 
>  /* HOPEFULLY NOT REACHED (aargh! die harder!) */
> 
>  int i;
>  for(i=1; 999999>i; i++)
>    x[i]=0;
> 
>  /* NOT REACHED (either killed, or exit()'ed in sigcatcher) */
>  abort();
> }
> 
> int
> main(int argc, char **argv) {
>  pthread_t thr;
> 
>  if(signal(SIGSEGV, sigcatcher)==SIG_ERR)
>    err(1, "signal(SIGSEGV, catchz0r)");
> 
>  //crashingthread(NULL);
>  pthread_create(&thr, NULL, crashingthread, NULL);
> 
>  sleep(3);
>  return 0;
> }
> 
> _______________________________________________
> freebsd-hackers at freebsd.org mailing list
> http://lists.freebsd.org/mailman/listinfo/freebsd-hackers
> To unsubscribe, send any mail to "freebsd-hackers-unsubscribe at freebsd.org"



More information about the freebsd-hackers mailing list