0

I'm using ncurses and whenever I get a segfault, ncurses doesn't properly release control of the terminal (because endwin() was never called). I set up a signal handler:

void handler(int signum) {
    endwin();
    exit(EXIT_FAILURE);
}

but the problem with this is that the segfault is ignored, as opposed to delayed until after endwin(). I'm fairly new to C++; can segfaults be caught like exceptions, so that I could have a finally block? Or is there someway to resend the segfault from inside the handler?

Nick
  • 2,821
  • 5
  • 30
  • 35
  • possible duplicate of [How to catch segmentation fault in Linux?](http://stackoverflow.com/questions/2350489/how-to-catch-segmentation-fault-in-linux) – casablanca Nov 13 '10 at 01:02
  • Just out of interest, what happens if you put a breakpoint in the signal handler? Can gdb get back to the context of the original segfault then? – Steve Jessop Nov 13 '10 at 01:30
  • C++ doesn't have finally blocks. Use a sentry class, the destructor of which calls endwin(); – Rob K Nov 13 '10 at 05:57

2 Answers2

4

Segfault is undefined behavior. You must find it and fix it. Don't worry about ncurses not releasing the terminal, and find and fix the bug.

Dialecticus
  • 16,400
  • 7
  • 43
  • 103
  • I guess I should have been clearer. This is a practical matter solely for debugging my code. When I encounter a segfault, I want to go find it and fix it, but it's sorta hard to operate GDB when ncurses still hasn't released the terminal. I did eventually find this bug, but it took me longer than it would have, and I'll likely have more bugs as I keep coding. So there's no way to do what I'm asking? – Nick Nov 13 '10 at 01:25
  • @Nick: When you hit a segfault it means that you have screwed stuff up so badly that there is no point in continuing because anything you do is just making things worse. – Martin York Nov 13 '10 at 01:34
  • @Martin York: It's not that he doesn't want to fix the bug, it's that finding the bug is harder when all the resources haven't been relinquished. Imagine if you had to reboot your computer every time to fix a null pointer dereference, would you not want to find a way to avoid rebooting? – dreamlax Nov 13 '10 at 01:39
  • @Nick, ah nice catch 22. Maybe possible duplicate link from casablanca can help? – Dialecticus Nov 13 '10 at 01:43
  • @Dialecticus: exception::what() just returns "Segmentation fault". The other suggestion (using siginfo_t) is better than what I have, but "Error at address 0x608b22" doesn't really help me too much. A line number would be fantastic though. It looks like Microsoft got this one right (wow!). They added try-finally (as opposed to the standard try-catch-finally), but on Linux this doesn't seem to work. – Nick Nov 13 '10 at 01:48
  • Is it possible to catch SIGSEGV signal, release terminal there, and put a breakpoint at that spot? – Dialecticus Nov 13 '10 at 02:15
  • So first of all to OP: After your curses app crashed and left your terminal broken try Ctrl+J to reset it that should help you with the broken terminal. To everyone else: Of course you have to fix the bug. But think of it that way. You are doing a solo project opensource or whatever no testing team and a bug gets to the customer. Yes bad work right there but wouldn't it be nice if the customers terminal would be screwed up? Doing apps in other languages this is done by a TryCatch or a with/using block. Whats the way in c++? Because I'm also looking for it. Is there even a way for segfault?! – Phillip May 03 '23 at 09:35
0

From the signal man page:

According to POSIX, the behavior of a process is undefined after it ignores a SIGFPE, SIGILL, or SIGSEGV signal that was not generated by kill(2) or raise(3).

Trying to do anything after a seg fault is crazy. It's like the air-bag in your activating after a crash and you keep on driving, because, well, you have an air bag and it will keep you safe in a crash. Papering over this with a handler is not the way.

One way would be to make your program take input from a file or stub out the output. You could also try remotely attaching to a process with gdb. Never done it but it might be worth a try.

Paul Rubel
  • 26,632
  • 7
  • 60
  • 80
  • No, it's like crashing your car and thinking, "Hey, I should probably grab my child before getting out of the burning vehicle." (The child in this case is the terminal.) The remote debugging might work, but it looks involved. I could try it maybe, but I'd rather have it as an extreme last resort. – Nick Nov 13 '10 at 01:54