@@ -53,6 +53,7 @@ struct CONSOLE_SCREEN_BUFFER_INFO {
5353#[ link( name = "kernel32" ) ]
5454extern "system" {
5555 fn SetConsoleTextAttribute ( handle : HANDLE , attr : WORD ) -> BOOL ;
56+ fn GetConsoleMode ( handle : HANDLE , mode : * mut DWORD ) -> BOOL ;
5657 fn GetStdHandle ( which : DWORD ) -> HANDLE ;
5758 fn GetConsoleScreenBufferInfo ( handle : HANDLE , info : * mut CONSOLE_SCREEN_BUFFER_INFO ) -> BOOL ;
5859}
@@ -91,24 +92,30 @@ fn bits_to_color(bits: u16) -> color::Color {
9192 color | ( u32:: from ( bits) & 0x8 ) // copy the hi-intensity bit
9293}
9394
95+ fn get_stdout_handle ( ) -> HANDLE {
96+ unsafe {
97+ // Magic -11 means stdout, from
98+ // https://docs.microsoft.com/en-us/windows/console/getstdhandle
99+ //
100+ // You may be wondering, "but what about stderr?", and the answer
101+ // to that is that setting terminal attributes on the stdout
102+ // handle also sets them for stderr, since they go to the same
103+ // terminal! Admittedly, this is fragile, since stderr could be
104+ // redirected to a different console. This is good enough for
105+ // rustc though. See #13400.
106+ GetStdHandle ( -11i32 as DWORD )
107+ }
108+ }
109+
94110impl < T : Write + Send + ' static > WinConsole < T > {
95111 fn apply ( & mut self ) {
96112 let _unused = self . buf . flush ( ) ;
97113 let mut accum: WORD = 0 ;
98114 accum |= color_to_bits ( self . foreground ) ;
99115 accum |= color_to_bits ( self . background ) << 4 ;
100116
117+ let out = get_stdout_handle ( ) ;
101118 unsafe {
102- // Magic -11 means stdout, from
103- // https://docs.microsoft.com/en-us/windows/console/getstdhandle
104- //
105- // You may be wondering, "but what about stderr?", and the answer
106- // to that is that setting terminal attributes on the stdout
107- // handle also sets them for stderr, since they go to the same
108- // terminal! Admittedly, this is fragile, since stderr could be
109- // redirected to a different console. This is good enough for
110- // rustc though. See #13400.
111- let out = GetStdHandle ( -11i32 as DWORD ) ;
112119 SetConsoleTextAttribute ( out, accum) ;
113120 }
114121 }
@@ -160,6 +167,21 @@ impl<T: Write + Send + 'static> Terminal for WinConsole<T> {
160167 Ok ( true )
161168 }
162169
170+ fn supports_ansi_colors ( & self ) -> bool {
171+ // From https://docs.microsoft.com/en-us/windows/console/getconsolemode
172+ const ENABLE_VIRTUAL_TERMINAL_PROCESSING : DWORD = 0x0004 ;
173+
174+ let stdout = get_stdout_handle ( ) ;
175+ let mut mode: DWORD = 0 ;
176+ unsafe {
177+ if GetConsoleMode ( stdout, & mut mode) != 0 {
178+ mode & ENABLE_VIRTUAL_TERMINAL_PROCESSING != 0
179+ } else {
180+ false
181+ }
182+ }
183+ }
184+
163185 fn reset ( & mut self ) -> io:: Result < bool > {
164186 self . foreground = self . def_foreground ;
165187 self . background = self . def_background ;
0 commit comments