win32: protect access to ctrlc_flag with critical section.
On Windows, console handlers are run in a separate thread, without actually interrupting the main thread.
This commit is contained in:
parent
9e42c1e6f4
commit
b3ffff5945
45
util/util.c
45
util/util.c
|
@ -32,15 +32,17 @@
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
#include "output.h"
|
#include "output.h"
|
||||||
|
|
||||||
static volatile int ctrlc_flag;
|
|
||||||
|
|
||||||
#ifdef WIN32
|
#ifdef WIN32
|
||||||
|
static int ctrlc_flag;
|
||||||
static HANDLE ctrlc_event;
|
static HANDLE ctrlc_event;
|
||||||
|
static CRITICAL_SECTION ctrlc_cs;
|
||||||
|
|
||||||
static WINAPI BOOL ctrlc_handler(DWORD event)
|
static WINAPI BOOL ctrlc_handler(DWORD event)
|
||||||
{
|
{
|
||||||
if (event == CTRL_C_EVENT) {
|
if (event == CTRL_C_EVENT) {
|
||||||
|
EnterCriticalSection(&ctrlc_cs);
|
||||||
ctrlc_flag = 1;
|
ctrlc_flag = 1;
|
||||||
|
LeaveCriticalSection(&ctrlc_cs);
|
||||||
SetEvent(ctrlc_event);
|
SetEvent(ctrlc_event);
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
@ -51,12 +53,33 @@ static WINAPI BOOL ctrlc_handler(DWORD event)
|
||||||
void ctrlc_init(void)
|
void ctrlc_init(void)
|
||||||
{
|
{
|
||||||
ctrlc_event = CreateEvent(0, TRUE, FALSE, NULL);
|
ctrlc_event = CreateEvent(0, TRUE, FALSE, NULL);
|
||||||
|
InitializeCriticalSection(&ctrlc_cs);
|
||||||
SetConsoleCtrlHandler(ctrlc_handler, TRUE);
|
SetConsoleCtrlHandler(ctrlc_handler, TRUE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ctrlc_exit(void)
|
||||||
|
{
|
||||||
|
SetConsoleCtrlHandler(NULL, TRUE);
|
||||||
|
DeleteCriticalSection(&ctrlc_cs);
|
||||||
|
CloseHandle(ctrlc_event);
|
||||||
|
}
|
||||||
|
|
||||||
|
int ctrlc_check(void)
|
||||||
|
{
|
||||||
|
int cc;
|
||||||
|
|
||||||
|
EnterCriticalSection(&ctrlc_cs);
|
||||||
|
cc = ctrlc_flag;
|
||||||
|
LeaveCriticalSection(&ctrlc_cs);
|
||||||
|
|
||||||
|
return cc;
|
||||||
|
}
|
||||||
|
|
||||||
void ctrlc_reset(void)
|
void ctrlc_reset(void)
|
||||||
{
|
{
|
||||||
|
EnterCriticalSection(&ctrlc_cs);
|
||||||
ctrlc_flag = 0;
|
ctrlc_flag = 0;
|
||||||
|
LeaveCriticalSection(&ctrlc_cs);
|
||||||
ResetEvent(ctrlc_event);
|
ResetEvent(ctrlc_event);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -65,6 +88,8 @@ HANDLE ctrlc_win32_event(void)
|
||||||
return ctrlc_event;
|
return ctrlc_event;
|
||||||
}
|
}
|
||||||
#else /* WIN32 */
|
#else /* WIN32 */
|
||||||
|
static volatile int ctrlc_flag;
|
||||||
|
|
||||||
static void sigint_handler(int signum)
|
static void sigint_handler(int signum)
|
||||||
{
|
{
|
||||||
ctrlc_flag = 1;
|
ctrlc_flag = 1;
|
||||||
|
@ -84,16 +109,21 @@ void ctrlc_init(void)
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ctrlc_exit(void)
|
||||||
|
{
|
||||||
|
signal(SIGINT, SIG_DFL);
|
||||||
|
}
|
||||||
|
|
||||||
void ctrlc_reset(void)
|
void ctrlc_reset(void)
|
||||||
{
|
{
|
||||||
ctrlc_flag = 0;
|
ctrlc_flag = 0;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
int ctrlc_check(void)
|
int ctrlc_check(void)
|
||||||
{
|
{
|
||||||
return ctrlc_flag;
|
return ctrlc_flag;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
char *get_arg(char **text)
|
char *get_arg(char **text)
|
||||||
{
|
{
|
||||||
|
@ -310,10 +340,12 @@ char *expand_tilde(const char *path)
|
||||||
if (expanded)
|
if (expanded)
|
||||||
snprintf(expanded, len, "%s%s", home, path + 1);
|
snprintf(expanded, len, "%s%s", home, path + 1);
|
||||||
else
|
else
|
||||||
printc_err("%s: malloc: %s\n", __FUNCTION__, last_error());
|
printc_err("%s: malloc: %s\n", __FUNCTION__,
|
||||||
|
last_error());
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
printc_err("%s: getenv: %s\n", __FUNCTION__, last_error());
|
printc_err("%s: getenv: %s\n", __FUNCTION__,
|
||||||
|
last_error());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
expanded = (char *)malloc(strlen(path) + 1);
|
expanded = (char *)malloc(strlen(path) + 1);
|
||||||
|
@ -321,7 +353,8 @@ char *expand_tilde(const char *path)
|
||||||
if (expanded)
|
if (expanded)
|
||||||
strcpy(expanded, path);
|
strcpy(expanded, path);
|
||||||
else
|
else
|
||||||
printc_err("%s: malloc: %s\n", __FUNCTION__, last_error());
|
printc_err("%s: malloc: %s\n", __FUNCTION__,
|
||||||
|
last_error());
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Caller must free()! */
|
/* Caller must free()! */
|
||||||
|
|
|
@ -40,6 +40,7 @@ const char *last_error(void);
|
||||||
|
|
||||||
/* Check and catch ^C from the user */
|
/* Check and catch ^C from the user */
|
||||||
void ctrlc_init(void);
|
void ctrlc_init(void);
|
||||||
|
void ctrlc_exit(void);
|
||||||
void ctrlc_reset(void);
|
void ctrlc_reset(void);
|
||||||
int ctrlc_check(void);
|
int ctrlc_check(void);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue