-
Notifications
You must be signed in to change notification settings - Fork 55
Description
Hey there,
Frankly good designed library.
Specifically I am not aware how golang std works but if it gets its streams using GetStdHandle GetConsoleMode will fail if a stream was redirected.
https://stackoverflow.com/questions/33476316/win32-getconsolemode-error-code-6
GetConsoleMode takes A handle to the console input buffer or the console screen buffer.
https://docs.microsoft.com/en-us/windows/console/getconsolemode
The standard handles of a process may be redirected by a call to SetStdHandle, in which case GetStdHandle returns the redirected handle. If the standard handles have been redirected, you can specify the CONIN$ value in a call to the CreateFile function to get a handle to a console's input buffer. Similarly, you can specify the CONOUT$ value to get a handle to a console's active screen buffer.
https://docs.microsoft.com/en-us/windows/console/getstdhandle
If this is the case it could be handled by oppening CONIN CONOUT. (I am not sure though how SetConsoleMode will work on such handles).
But my point is if GetConsoleMode fails maybe it'd better to return error in newMaster?
Lines 32 to 67 in 05dadd9
| func (m *master) initStdios() { | |
| m.in = windows.Handle(os.Stdin.Fd()) | |
| if err := windows.GetConsoleMode(m.in, &m.inMode); err == nil { | |
| // Validate that windows.ENABLE_VIRTUAL_TERMINAL_INPUT is supported, but do not set it. | |
| if err = windows.SetConsoleMode(m.in, m.inMode|windows.ENABLE_VIRTUAL_TERMINAL_INPUT); err == nil { | |
| vtInputSupported = true | |
| } | |
| // Unconditionally set the console mode back even on failure because SetConsoleMode | |
| // remembers invalid bits on input handles. | |
| windows.SetConsoleMode(m.in, m.inMode) | |
| } else { | |
| fmt.Printf("failed to get console mode for stdin: %v\n", err) | |
| } | |
| m.out = windows.Handle(os.Stdout.Fd()) | |
| if err := windows.GetConsoleMode(m.out, &m.outMode); err == nil { | |
| if err := windows.SetConsoleMode(m.out, m.outMode|windows.ENABLE_VIRTUAL_TERMINAL_PROCESSING); err == nil { | |
| m.outMode |= windows.ENABLE_VIRTUAL_TERMINAL_PROCESSING | |
| } else { | |
| windows.SetConsoleMode(m.out, m.outMode) | |
| } | |
| } else { | |
| fmt.Printf("failed to get console mode for stdout: %v\n", err) | |
| } | |
| m.err = windows.Handle(os.Stderr.Fd()) | |
| if err := windows.GetConsoleMode(m.err, &m.errMode); err == nil { | |
| if err := windows.SetConsoleMode(m.err, m.errMode|windows.ENABLE_VIRTUAL_TERMINAL_PROCESSING); err == nil { | |
| m.errMode |= windows.ENABLE_VIRTUAL_TERMINAL_PROCESSING | |
| } else { | |
| windows.SetConsoleMode(m.err, m.errMode) | |
| } | |
| } else { | |
| fmt.Printf("failed to get console mode for stderr: %v\n", err) | |
| } | |
| } |
Thank you.