Skip to content

Commit 271d7c8

Browse files
committed
Merge pull request #91147 from bruvzg/con_redir_3
[Windows] Improve console IO redirection.
2 parents 3207014 + 8748147 commit 271d7c8

File tree

3 files changed

+35
-25
lines changed

3 files changed

+35
-25
lines changed

platform/windows/console_wrapper_windows.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -136,6 +136,10 @@ int main(int argc, char *argv[]) {
136136
STARTUPINFOW si;
137137
ZeroMemory(&si, sizeof(si));
138138
si.cb = sizeof(si);
139+
si.dwFlags = STARTF_USESTDHANDLES;
140+
si.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
141+
si.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
142+
si.hStdError = GetStdHandle(STD_ERROR_HANDLE);
139143

140144
WCHAR new_command_line[32767];
141145
_snwprintf_s(new_command_line, 32767, _TRUNCATE, L"%ls %ls", exe_name, PathGetArgsW(GetCommandLineW()));

platform/windows/os_windows.cpp

Lines changed: 27 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,24 @@ void RedirectStream(const char *p_file_name, const char *p_mode, FILE *p_cpp_str
115115
}
116116

117117
void RedirectIOToConsole() {
118+
// Save current handles.
119+
HANDLE h_stdin = GetStdHandle(STD_INPUT_HANDLE);
120+
HANDLE h_stdout = GetStdHandle(STD_OUTPUT_HANDLE);
121+
HANDLE h_stderr = GetStdHandle(STD_ERROR_HANDLE);
122+
118123
if (AttachConsole(ATTACH_PARENT_PROCESS)) {
124+
// Restore redirection (Note: if not redirected it's NULL handles not INVALID_HANDLE_VALUE).
125+
if (h_stdin != 0) {
126+
SetStdHandle(STD_INPUT_HANDLE, h_stdin);
127+
}
128+
if (h_stdout != 0) {
129+
SetStdHandle(STD_OUTPUT_HANDLE, h_stdout);
130+
}
131+
if (h_stderr != 0) {
132+
SetStdHandle(STD_ERROR_HANDLE, h_stderr);
133+
}
134+
135+
// Update file handles.
119136
RedirectStream("CONIN$", "r", stdin, STD_INPUT_HANDLE);
120137
RedirectStream("CONOUT$", "w", stdout, STD_OUTPUT_HANDLE);
121138
RedirectStream("CONOUT$", "w", stderr, STD_ERROR_HANDLE);
@@ -173,10 +190,6 @@ void OS_Windows::initialize() {
173190
add_error_handler(&error_handlers);
174191
#endif
175192

176-
#ifndef WINDOWS_SUBSYSTEM_CONSOLE
177-
RedirectIOToConsole();
178-
#endif
179-
180193
FileAccess::make_default<FileAccessWindows>(FileAccess::ACCESS_RESOURCES);
181194
FileAccess::make_default<FileAccessWindows>(FileAccess::ACCESS_USERDATA);
182195
FileAccess::make_default<FileAccessWindows>(FileAccess::ACCESS_FILESYSTEM);
@@ -1521,10 +1534,10 @@ void OS_Windows::unset_environment(const String &p_var) const {
15211534
}
15221535

15231536
String OS_Windows::get_stdin_string() {
1524-
WCHAR buff[1024];
1537+
char buff[1024];
15251538
DWORD count = 0;
1526-
if (ReadConsoleW(GetStdHandle(STD_INPUT_HANDLE), buff, 1024, &count, nullptr)) {
1527-
return String::utf16((const char16_t *)buff, count);
1539+
if (ReadFile(GetStdHandle(STD_INPUT_HANDLE), buff, 1024, &count, nullptr)) {
1540+
return String::utf8((const char *)buff, count);
15281541
}
15291542

15301543
return String();
@@ -1908,6 +1921,13 @@ String OS_Windows::get_system_ca_certificates() {
19081921
OS_Windows::OS_Windows(HINSTANCE _hInstance) {
19091922
hInstance = _hInstance;
19101923

1924+
#ifndef WINDOWS_SUBSYSTEM_CONSOLE
1925+
RedirectIOToConsole();
1926+
#endif
1927+
1928+
SetConsoleOutputCP(CP_UTF8);
1929+
SetConsoleCP(CP_UTF8);
1930+
19111931
CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED);
19121932

19131933
#ifdef WASAPI_ENABLED

platform/windows/windows_terminal_logger.cpp

Lines changed: 4 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -53,26 +53,12 @@ void WindowsTerminalLogger::logv(const char *p_format, va_list p_list, bool p_er
5353
}
5454
buf[len] = 0;
5555

56-
int wlen = MultiByteToWideChar(CP_UTF8, 0, buf, len, nullptr, 0);
57-
if (wlen < 0) {
58-
return;
59-
}
60-
61-
wchar_t *wbuf = (wchar_t *)memalloc((len + 1) * sizeof(wchar_t));
62-
ERR_FAIL_NULL_MSG(wbuf, "Out of memory.");
63-
MultiByteToWideChar(CP_UTF8, 0, buf, len, wbuf, wlen);
64-
wbuf[wlen] = 0;
65-
66-
if (p_err) {
67-
fwprintf(stderr, L"%ls", wbuf);
68-
} else {
69-
wprintf(L"%ls", wbuf);
70-
}
71-
72-
memfree(wbuf);
56+
DWORD written = 0;
57+
HANDLE h = p_err ? GetStdHandle(STD_ERROR_HANDLE) : GetStdHandle(STD_OUTPUT_HANDLE);
58+
WriteFile(h, &buf[0], len, &written, nullptr);
7359

7460
#ifdef DEBUG_ENABLED
75-
fflush(stdout);
61+
FlushFileBuffers(h);
7662
#endif
7763
}
7864

0 commit comments

Comments
 (0)