ziu
ziu

Reputation: 2720

pthread_sigmask interferes with GDB

I have been working on a multithreaded program under Linux with particular requirements about signal handling. For instance, I need the program to print statistics for a single Ctrl-C input.

I implemented that using pthread_sigmask and sigwait, i.e. I block all the non-critical signals in the main thread before creating the rest of the threads and I start a "catcher" thread blocked on sigwait.

Initialization (in main):

sigfillset(&set);
sigdelset(&set, SIGSEGV);
sigdelset(&set, SIGBUS);
sigdelset(&set, SIGILL);

s = pthread_sigmask(SIG_BLOCK, &set, NULL);
if (s != 0)
    handle_error_en(s, "pthread_sigmask");

s = pthread_create(&signal_thread, NULL, &sig_thread, (void *) &set);
if (s != 0)
    handle_error_en(s, "pthread_create");

Catcher thread routine:

void *sig_thread(void *arg) {
    sigset_t *set = (sigset_t *) arg;
    int s, sig;

    pthread_detach(pthread_self());

    for(;;) {
        s = sigwait(set, &sig);
        if (s != 0)
            handle_error_en(s, "sigwait");
        switch(sig) {
            case SIGINT:
                break;
            case SIGTERM:
                break;
            case SIGUSR1:
                break;
            case SIGUSR2:
                break;
            default:
                break;
        }
    }
    pthread_exit(NULL);
    return NULL;
}

Everything works as expected, but my catching mechanism prevents GDB from pausing the program (the SIGINT routine is triggered). How can I fix this ?

Thanks

Upvotes: 2

Views: 873

Answers (1)

ecatmur
ecatmur

Reputation: 157414

Try pausing the program with SIGSTOP (instead of SIGINT) before attaching gdb. SIGSTOP cannot be caught or ignored, and it will suspend your program until gdb is attached to it (and can then continue it).

Upvotes: 6

Related Questions