Handle Ctrl+C on Win32

Handle CTRL+C on Win32

The following code works for me:

#include <windows.h> 
#include <stdio.h>

BOOL WINAPI consoleHandler(DWORD signal) {

if (signal == CTRL_C_EVENT)
printf("Ctrl-C handled\n"); // do cleanup

return TRUE;
}

int main()
{
running = TRUE;
if (!SetConsoleCtrlHandler(consoleHandler, TRUE)) {
printf("\nERROR: Could not set control handler");
return 1;
}

while (1) { /* do work */ }

return 0;
}

What exactly is the effect of Ctrl-C on C++ Win32 console applications?

EDIT: SIGINT, not SIGTERM. And Assaf reports that no objects are destroyed (at least on Windows) for unhanded SIGINT.

The system sends a SIGINT. This concept applies (with some variance) for all C implementations. To handle it, you call signal, specifying a signal handler. See the documentation on the signal function at Open Group and MSDN.

The second question is a little trickier, and may depend on implementation. The best bet is to handle the signal, which allows you to use delete and exit() manually.

My consoleHandler does not handle CTRL+C even though properly set

From MSDN:

CTRL+BREAK is always treated as a signal, but typical CTRL+C behavior
can be changed in three ways that prevent the handler functions from
being called:

  • The SetConsoleMode function can disable the ENABLE_PROCESSED_INPUT mode for a console's input buffer, so CTRL+C is reported as keyboard
    input rather than as a signal.
  • Calling SetConsoleCtrlHandler with the NULL and TRUE arguments causes the calling process to ignore CTRL+C signals. This attribute is
    inherited by child processes, but it can be enabled or disabled by any
    process without affecting existing processes.
  • If a console process is being debugged and CTRL+C signals have not been disabled, the system generates a DBG_CONTROL_C exception. This
    exception is raised only for the benefit of the debugger, and an
    application should never use an exception handler to deal with it. If
    the debugger handles the exception, an application will not notice the
    CTRL+C, with one exception: alertable waits will terminate. If the
    debugger passes the exception on unhandled, CTRL+C is passed to the
    console process and treated as a signal, as previously discussed.

Perhaps the third point applies to your problem? Does your application behaves as expected when running in Release mode?

How can I catch a ctrl-c event?

signal isn't the most reliable way as it differs in implementations. I would recommend using sigaction. Tom's code would now look like this :

#include <signal.h>
#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>

void my_handler(int s){
printf("Caught signal %d\n",s);
exit(1);

}

int main(int argc,char** argv)
{

struct sigaction sigIntHandler;

sigIntHandler.sa_handler = my_handler;
sigemptyset(&sigIntHandler.sa_mask);
sigIntHandler.sa_flags = 0;

sigaction(SIGINT, &sigIntHandler, NULL);

pause();

return 0;
}

Windows handling CTRL+C in different thread?

From MSDN topic HandlerRoutine:

A HandlerRoutine function is an application-defined function used with the SetConsoleCtrlHandler function. A console process uses this function to handle control signals received by the process. When the signal is received, the system creates a new thread in the process to execute the function.

So, the answer is: this is impossible.



Related Topics



Leave a reply



Submit