Can't ctrl-c my SDL apps anymore

c, linux, opengl, sdl, signals

Solution

I've been having similar issues for a few days... and after a long and painful investigation I reached to this bug report in the NVIDIA OpenGL drivers.

The problem is that the initialization code of the NVIDIA OpenGL librariy corrupts the sigprocmask of the process. This may happen to any process that links to that library. In my case the session manager was affected, so every single process in my session inherited it.

You can check if that is your case with the following command:

$ grep SigBlk /proc/<pid>/status

The normal output should be:

SigBlk: 0000000000010000

If you instead get a big number that looks like a memory address, you have the bug.

Downgrading to 325.15-11 will solve your problems.

Problem

Yesterday I could and today I can't `ctrl-c` in the terminal to kill my SDL apps. Before `SDL_Init` is called, everything works as expected. After, `ctrl-c` does nothing. Calling `signal(SIGINT, SIG_DFL)` doesn't change this. I haven't updated anything I can think of except for Nvidia drivers. This happens with apps I've compiled months ago too. Is there any way to debug what's happening? [EDIT] Even this ceases to work after `SDL_Init` (although behaves normally within `gdb`): ``` signal(SIGINT, exit); raise(SIGINT); ``` The same happens with both SDL1.2.15 and SDL2 (glut is ok though). I'm running Fedora 18 (x64), gcc 4.7.2, nvidia drivers 331.2 with a gtx titan. `SDL_QUIT` occurs when I hit the close button on the window, but never `ctrl-c` (afaik it never used to either - SIGINT would simply kill the app). [EDIT2] This isn't consistently reproducible but is very common. Sometimes running other programs beforehand such as `echo` gives an increased chance for `ctrl-c` to work. If it doesn't work, repeats never works. After some further testing it seems `ctrl-c` stops working only when `SDL_INIT_TIMER` is passed to `SDL_Init`. What could the timer subsystem have to do with signals?? [EDIT3] Here's my test case... ``` #include <stdio.h> #include <unistd.h> #include <signal.h> #include <SDL2/SDL.h> int main() { SDL_Window* window = NULL; SDL_GLContext context; fprintf(stderr, "Start"); usleep(3000000); fprintf(stderr, ".\n"); //raise(SIGINT); //always works struct sigaction old; sigaction(SIGTERM, NULL, &old); fprintf(stderr, "Init"); SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_NOPARACHUTE); //SDL_Init(SDL_INIT_VIDEO | SDL_INIT_NOPARACHUTE); //no problems fprintf(stderr, ".\n"); usleep(3000000); sigaction(SIGINT, &old, NULL); //signal(SIGINT, SIG_DFL); //raise(SIGINT); //fails with SDL_INIT_TIMER (commonly, but not always) fprintf(stderr, "Window"); window = SDL_CreateWindow("sdlwin", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 512, 512, SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN | SDL_WINDOW_RESIZABLE); fprintf(stderr, ".\n"); usleep(3000000); fprintf(stderr, "Context"); context = SDL_GL_CreateContext(window); fprintf(stderr, ".\n"); usleep(3000000); fprintf(stderr, "Loop...\n"); while (1) { usleep(1000000); printf(".\n"); } return 0; } ``` In some cases the first `ctrl-c` just works. Sometimes the first ends the current `usleep` and it takes a second to kill the app. Other times, `ctrl-c` never works. The randomness makes me assume there's something uninitialized somewhere. Annoyingly I've just had a run where `ctrl-c` worked 90% of the time with only a couple of fails.

Original source

Related problems