mirror of
https://github.com/reactos/reactos.git
synced 2025-03-01 03:45:16 +00:00

Imported from https://www.nuget.org/packages/Microsoft.Windows.SDK.CRTSource/10.0.22621.3 License: MIT
83 lines
2.4 KiB
C++
83 lines
2.4 KiB
C++
//
|
|
// initcon.cpp
|
|
//
|
|
// Copyright (c) Microsoft Corporation. All rights reserved.
|
|
//
|
|
// Defines the global console output handle and the __dcrt_lowio_initialize_console_output() and
|
|
// __dcrt_terminate_console_output() functions, which initialize and close that handle.
|
|
// Also defines functions that can be used instead of the Console API to enable retry behavior
|
|
// in case the cached console handle is freed.
|
|
|
|
#include <corecrt_internal_lowio.h>
|
|
|
|
_CRT_LINKER_FORCE_INCLUDE(__dcrt_console_output_terminator);
|
|
|
|
// The global console output handle.
|
|
static HANDLE __dcrt_lowio_console_output_handle = _console_uninitialized_handle;
|
|
|
|
// Initializes the global console output handle
|
|
static void __dcrt_lowio_initialize_console_output()
|
|
{
|
|
__dcrt_lowio_console_output_handle = CreateFileW(
|
|
L"CONOUT$",
|
|
GENERIC_WRITE,
|
|
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
|
nullptr,
|
|
OPEN_EXISTING,
|
|
0,
|
|
nullptr);
|
|
}
|
|
|
|
extern "C" BOOL __cdecl __dcrt_lowio_ensure_console_output_initialized()
|
|
{
|
|
if (__dcrt_lowio_console_output_handle == _console_uninitialized_handle)
|
|
{
|
|
__dcrt_lowio_initialize_console_output();
|
|
}
|
|
|
|
if (__dcrt_lowio_console_output_handle == _console_invalid_handle)
|
|
{
|
|
return FALSE;
|
|
}
|
|
return TRUE;
|
|
}
|
|
|
|
// Closes the global console output handle
|
|
extern "C" void __cdecl __dcrt_terminate_console_output()
|
|
{
|
|
if ( __dcrt_lowio_console_output_handle != _console_invalid_handle
|
|
&& __dcrt_lowio_console_output_handle != _console_uninitialized_handle)
|
|
{
|
|
CloseHandle(__dcrt_lowio_console_output_handle);
|
|
}
|
|
}
|
|
|
|
template <typename Func>
|
|
static BOOL console_output_reopen_and_retry(Func const& fp) throw()
|
|
{
|
|
BOOL result = fp();
|
|
if (!result && GetLastError() == ERROR_INVALID_HANDLE) {
|
|
__dcrt_terminate_console_output();
|
|
__dcrt_lowio_initialize_console_output();
|
|
result = fp();
|
|
}
|
|
return result;
|
|
}
|
|
|
|
extern "C" BOOL __cdecl __dcrt_write_console(
|
|
_In_ void const * lpBuffer,
|
|
_In_ DWORD nNumberOfCharsToWrite,
|
|
_Out_ LPDWORD lpNumberOfCharsWritten
|
|
)
|
|
{
|
|
return console_output_reopen_and_retry(
|
|
[lpBuffer, nNumberOfCharsToWrite, lpNumberOfCharsWritten]()
|
|
{
|
|
return ::WriteConsoleW(
|
|
__dcrt_lowio_console_output_handle,
|
|
lpBuffer,
|
|
nNumberOfCharsToWrite,
|
|
lpNumberOfCharsWritten,
|
|
nullptr);
|
|
});
|
|
}
|