System.ConsolePal.WindowsConsoleStream.WriteFileNative C# (CSharp) Method

WriteFileNative() private static method

private static WriteFileNative ( IntPtr hFile, byte bytes, int offset, int count, bool useFileAPIs ) : int
hFile IntPtr
bytes byte
offset int
count int
useFileAPIs bool
return int
            private static unsafe int WriteFileNative(IntPtr hFile, byte[] bytes, int offset, int count, bool useFileAPIs)
            {
                Debug.Assert(offset >= 0, "offset >= 0");
                Debug.Assert(count >= 0, "count >= 0");
                Debug.Assert(bytes != null, "bytes != null");
                Debug.Assert(bytes.Length >= offset + count, "bytes.Length >= offset + count");

                // You can't use the fixed statement on an array of length 0.
                if (bytes.Length == 0)
                    return Interop.Errors.ERROR_SUCCESS;

                bool writeSuccess;
                fixed (byte* p = bytes)
                {
                    if (useFileAPIs)
                    {
                        int numBytesWritten;
                        writeSuccess = (0 != Interop.Kernel32.WriteFile(hFile, p + offset, count, out numBytesWritten, IntPtr.Zero));
                        Debug.Assert(!writeSuccess || count == numBytesWritten);
                    }
                    else
                    {

                        // If the code page could be Unicode, we should use ReadConsole instead, e.g.
                        // Note that WriteConsoleW has a max limit on num of chars to write (64K)
                        // [http://msdn.microsoft.com/en-us/library/ms687401.aspx]
                        // However, we do not need to worry about that because the StreamWriter in Console has
                        // a much shorter buffer size anyway.
                        int charsWritten;
                        writeSuccess = Interop.Kernel32.WriteConsole(hFile, p + offset, count / BytesPerWChar, out charsWritten, IntPtr.Zero);
                        Debug.Assert(!writeSuccess || count / BytesPerWChar == charsWritten);
                    }
                }
                if (writeSuccess)
                    return Interop.Errors.ERROR_SUCCESS;

                // For pipes that are closing or broken, just stop.
                // (E.g. ERROR_NO_DATA ("pipe is being closed") is returned when we write to a console that is closing;
                // ERROR_BROKEN_PIPE ("pipe was closed") is returned when stdin was closed, which is mot an error, but EOF.)
                int errorCode = Marshal.GetLastWin32Error();
                if (errorCode == Interop.Errors.ERROR_NO_DATA || errorCode == Interop.Errors.ERROR_BROKEN_PIPE)
                    return Interop.Errors.ERROR_SUCCESS;
                return errorCode;
            }
        }