Skip to content

Commit 176478a

Browse files
kusmagitster
authored andcommitted
mingw: make fgetc raise SIGINT if apropriate
Set a control-handler to prevent the process from terminating, and simulate SIGINT so it can be handled by a signal-handler as usual. Signed-off-by: Erik Faye-Lund <[email protected]> Signed-off-by: Junio C Hamano <[email protected]>
1 parent f4f5498 commit 176478a

File tree

2 files changed

+72
-10
lines changed

2 files changed

+72
-10
lines changed

compat/mingw.c

Lines changed: 66 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -319,6 +319,31 @@ ssize_t mingw_write(int fd, const void *buf, size_t count)
319319
return write(fd, buf, min(count, 31 * 1024 * 1024));
320320
}
321321

322+
static BOOL WINAPI ctrl_ignore(DWORD type)
323+
{
324+
return TRUE;
325+
}
326+
327+
#undef fgetc
328+
int mingw_fgetc(FILE *stream)
329+
{
330+
int ch;
331+
if (!isatty(_fileno(stream)))
332+
return fgetc(stream);
333+
334+
SetConsoleCtrlHandler(ctrl_ignore, TRUE);
335+
while (1) {
336+
ch = fgetc(stream);
337+
if (ch != EOF || GetLastError() != ERROR_OPERATION_ABORTED)
338+
break;
339+
340+
/* Ctrl+C was pressed, simulate SIGINT and retry */
341+
mingw_raise(SIGINT);
342+
}
343+
SetConsoleCtrlHandler(ctrl_ignore, FALSE);
344+
return ch;
345+
}
346+
322347
#undef fopen
323348
FILE *mingw_fopen (const char *filename, const char *otype)
324349
{
@@ -1546,7 +1571,7 @@ static HANDLE timer_event;
15461571
static HANDLE timer_thread;
15471572
static int timer_interval;
15481573
static int one_shot;
1549-
static sig_handler_t timer_fn = SIG_DFL;
1574+
static sig_handler_t timer_fn = SIG_DFL, sigint_fn = SIG_DFL;
15501575

15511576
/* The timer works like this:
15521577
* The thread, ticktack(), is a trivial routine that most of the time
@@ -1560,13 +1585,7 @@ static sig_handler_t timer_fn = SIG_DFL;
15601585
static unsigned __stdcall ticktack(void *dummy)
15611586
{
15621587
while (WaitForSingleObject(timer_event, timer_interval) == WAIT_TIMEOUT) {
1563-
if (timer_fn == SIG_DFL) {
1564-
if (isatty(STDERR_FILENO))
1565-
fputs("Alarm clock\n", stderr);
1566-
exit(128 + SIGALRM);
1567-
}
1568-
if (timer_fn != SIG_IGN)
1569-
timer_fn(SIGALRM);
1588+
mingw_raise(SIGALRM);
15701589
if (one_shot)
15711590
break;
15721591
}
@@ -1657,12 +1676,49 @@ int sigaction(int sig, struct sigaction *in, struct sigaction *out)
16571676
sig_handler_t mingw_signal(int sig, sig_handler_t handler)
16581677
{
16591678
sig_handler_t old = timer_fn;
1660-
if (sig != SIGALRM)
1679+
1680+
switch (sig) {
1681+
case SIGALRM:
1682+
timer_fn = handler;
1683+
break;
1684+
1685+
case SIGINT:
1686+
sigint_fn = handler;
1687+
break;
1688+
1689+
default:
16611690
return signal(sig, handler);
1662-
timer_fn = handler;
1691+
}
1692+
16631693
return old;
16641694
}
16651695

1696+
#undef raise
1697+
int mingw_raise(int sig)
1698+
{
1699+
switch (sig) {
1700+
case SIGALRM:
1701+
if (timer_fn == SIG_DFL) {
1702+
if (isatty(STDERR_FILENO))
1703+
fputs("Alarm clock\n", stderr);
1704+
exit(128 + SIGALRM);
1705+
} else if (timer_fn != SIG_IGN)
1706+
timer_fn(SIGALRM);
1707+
return 0;
1708+
1709+
case SIGINT:
1710+
if (sigint_fn == SIG_DFL)
1711+
exit(128 + SIGINT);
1712+
else if (sigint_fn != SIG_IGN)
1713+
sigint_fn(SIGINT);
1714+
return 0;
1715+
1716+
default:
1717+
return raise(sig);
1718+
}
1719+
}
1720+
1721+
16661722
static const char *make_backslash_path(const char *path)
16671723
{
16681724
static char buf[PATH_MAX + 1];

compat/mingw.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -179,6 +179,9 @@ int mingw_open (const char *filename, int oflags, ...);
179179
ssize_t mingw_write(int fd, const void *buf, size_t count);
180180
#define write mingw_write
181181

182+
int mingw_fgetc(FILE *stream);
183+
#define fgetc mingw_fgetc
184+
182185
FILE *mingw_fopen (const char *filename, const char *otype);
183186
#define fopen mingw_fopen
184187

@@ -290,6 +293,9 @@ static inline unsigned int git_ntohl(unsigned int x)
290293
sig_handler_t mingw_signal(int sig, sig_handler_t handler);
291294
#define signal mingw_signal
292295

296+
int mingw_raise(int sig);
297+
#define raise mingw_raise
298+
293299
/*
294300
* ANSI emulation wrappers
295301
*/

0 commit comments

Comments
 (0)