To write to stdout in an asynchronous / nonblocking way, low-level I/O libraries such as boost::asio or libuv utilize the API of the operating system to monitor multiple file descriptors or HANDLE objects.
While Linux uses file descriptors which are integers, the Windows API has an object called a HANDLE.
libuv provides pipes. According to the libuv documentation https://docs.libuv.org/en/v1.x/pipe.html the function int uv_pipe_open(uv_pipe_t *handle, uv_file file)
opens an existing file descriptor or HANDLE as a pipe. While uv_file
that is an integer is obviously compatible with file descriptors on Linux, it is not directly obvious how that API works for Windows HANDLEs as well as the following code snippet shall describe:
int main()
{
auto loop = uv_default_loop();
uv_loop_init(loop);
uv_pipe_t outPipe;
uv_pipe_init(loop, &outPipe, 0);
#ifdef __linux__
uv_pipe_open(&outPipe, STDOUT_FILENO);
#elif WIN32
uv_pipe_open(&outPipe, GetStdHandle(STD_OUTPUT_HANDLE)); // HANDLE cannot be converted into an integer.
#endif
// call to uv_write.
}
How can one use libuv’s uv_pipe_open
in a Windows-compatible way to afterwards write to stdout in an nonblocking way?