diff options
author | Karsten Blees <blees@dcon.de> | 2010-07-31 00:04:02 +0000 |
---|---|---|
committer | Junio C Hamano <gitster@pobox.com> | 2014-06-10 13:32:44 -0700 |
commit | 143e615270bd17dcef0d8e5751dacc496eff687d (patch) | |
tree | 00264af173b8d49d1c9ef2cc5ba80aa7c0ee49ce /compat | |
parent | 617ce965aa3e5d44d0292c9094ee692f161a55d0 (diff) | |
download | git-143e615270bd17dcef0d8e5751dacc496eff687d.tar.gz |
Win32: detect console streams more reliably
GetStdHandle(STD_OUTPUT_HANDLE) doesn't work for stderr if stdout is
redirected. Use _get_osfhandle of the FILE* instead.
_isatty() is true for all character devices (including parallel and serial
ports). Check return value of GetConsoleScreenBufferInfo instead to
reliably detect console handles (also don't initialize internal state from
an uninitialized CONSOLE_SCREEN_BUFFER_INFO structure if the function
fails).
Signed-off-by: Karsten Blees <blees@dcon.de>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Stepan Kasal <kasal@ucw.cz>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
Diffstat (limited to 'compat')
-rw-r--r-- | compat/winansi.c | 50 |
1 files changed, 26 insertions, 24 deletions
diff --git a/compat/winansi.c b/compat/winansi.c index abe0feaa2c..c4be401a6e 100644 --- a/compat/winansi.c +++ b/compat/winansi.c @@ -25,27 +25,39 @@ static HANDLE console; static WORD plain_attr; static WORD attr; static int negative; +static FILE *last_stream = NULL; -static void init(void) +static int is_console(FILE *stream) { CONSOLE_SCREEN_BUFFER_INFO sbi; + HANDLE hcon; static int initialized = 0; - if (initialized) - return; - console = GetStdHandle(STD_OUTPUT_HANDLE); - if (console == INVALID_HANDLE_VALUE) - console = NULL; + /* use cached value if stream hasn't changed */ + if (stream == last_stream) + return console != NULL; - if (!console) - return; + last_stream = stream; + console = NULL; - GetConsoleScreenBufferInfo(console, &sbi); - attr = plain_attr = sbi.wAttributes; - negative = 0; + /* get OS handle of the stream */ + hcon = (HANDLE) _get_osfhandle(_fileno(stream)); + if (hcon == INVALID_HANDLE_VALUE) + return 0; + + /* check if its a handle to a console output screen buffer */ + if (!GetConsoleScreenBufferInfo(hcon, &sbi)) + return 0; + + if (!initialized) { + attr = plain_attr = sbi.wAttributes; + negative = 0; + initialized = 1; + } - initialized = 1; + console = hcon; + return 1; } static int write_console(const char *str, size_t len) @@ -292,12 +304,7 @@ int winansi_fputs(const char *str, FILE *stream) { int rv; - if (!isatty(fileno(stream))) - return fputs(str, stream); - - init(); - - if (!console) + if (!is_console(stream)) return fputs(str, stream); rv = ansi_emulate(str, stream); @@ -315,12 +322,7 @@ int winansi_vfprintf(FILE *stream, const char *format, va_list list) char *buf = small_buf; va_list cp; - if (!isatty(fileno(stream))) - goto abort; - - init(); - - if (!console) + if (!is_console(stream)) goto abort; va_copy(cp, list); |