2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS system libraries
4 * FILE: dll/win32/kernel32/client/console/console.c
5 * PURPOSE: Win32 server console functions
6 * PROGRAMMERS: James Tabor <jimtabor@adsl-64-217-116-74.dsl.hstntx.swbell.net>
7 * Hermes Belusca-Maito (hermes.belusca@sfr.fr)
10 /* INCLUDES *******************************************************************/
18 /* GLOBALS ********************************************************************/
20 extern RTL_CRITICAL_SECTION ConsoleLock
;
21 extern BOOLEAN ConsoleInitialized
;
23 /* Console reserved "file" names */
24 static LPCWSTR BaseConFileName
= CONSOLE_FILE_NAME
;
25 static LPCWSTR BaseConInputFileName
= CONSOLE_INPUT_FILE_NAME
;
26 static LPCWSTR BaseConOutputFileName
= CONSOLE_OUTPUT_FILE_NAME
;
28 /* Console Control handling */
29 static PHANDLER_ROUTINE InitialHandler
[1];
30 static PHANDLER_ROUTINE
* CtrlHandlers
;
31 static ULONG NrCtrlHandlers
;
32 static ULONG NrAllocatedHandlers
;
33 static BOOLEAN LastCloseNotify
= FALSE
;
35 extern BOOL WINAPI
IsDebuggerPresent(VOID
);
37 /* Console Input facilities */
38 HANDLE InputWaitHandle
= INVALID_HANDLE_VALUE
;
40 #define EXENAME_LENGTH 255 + 1
41 static RTL_CRITICAL_SECTION ExeNameLock
;
42 static BOOLEAN ExeNameInitialized
;
43 static WCHAR ExeNameBuffer
[EXENAME_LENGTH
]; // NULL-terminated
44 static USHORT ExeNameLength
; // Count in number of characters without NULL
45 static WCHAR StartDirBuffer
[MAX_PATH
+ 1]; // NULL-terminated
46 static USHORT StartDirLength
; // Count in number of characters without NULL
49 /* Default Console Control Handler ********************************************/
53 DefaultConsoleCtrlHandler(DWORD Event
)
55 DPRINT("Default handler called: %lx\n", Event
);
59 DPRINT("Ctrl-C Event\n");
62 case CTRL_BREAK_EVENT
:
63 DPRINT("Ctrl-Break Event\n");
66 case CTRL_CLOSE_EVENT
:
67 DPRINT("Ctrl Close Event\n");
70 case CTRL_LAST_CLOSE_EVENT
:
71 DPRINT("Ctrl Last Close Event\n");
74 case CTRL_LOGOFF_EVENT
:
75 DPRINT("Ctrl Logoff Event\n");
78 case CTRL_SHUTDOWN_EVENT
:
79 DPRINT("Ctrl Shutdown Event\n");
83 ExitProcess(CONTROL_C_EXIT
);
89 ConsoleControlDispatcher(IN LPVOID lpThreadParameter
)
92 DWORD CodeAndFlag
= PtrToUlong(lpThreadParameter
);
93 DWORD nCode
= CodeAndFlag
& MAXLONG
;
95 EXCEPTION_RECORD erException
;
97 DPRINT1("Console Dispatcher Active: %lx %lx\n", CodeAndFlag
, nCode
);
98 SetThreadPriority(GetCurrentThread(), THREAD_PRIORITY_HIGHEST
);
103 case CTRL_BREAK_EVENT
:
105 if (IsDebuggerPresent())
107 erException
.ExceptionCode
= (nCode
== CTRL_C_EVENT
?
108 DBG_CONTROL_C
: DBG_CONTROL_BREAK
);
109 erException
.ExceptionFlags
= 0;
110 erException
.ExceptionRecord
= NULL
;
111 erException
.ExceptionAddress
= DefaultConsoleCtrlHandler
;
112 erException
.NumberParameters
= 0;
116 RtlRaiseException(&erException
);
118 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER
)
120 RtlEnterCriticalSection(&ConsoleLock
);
122 if ((nCode
!= CTRL_C_EVENT
) ||
123 (NtCurrentPeb()->ProcessParameters
->ConsoleFlags
!= 1))
125 for (i
= NrCtrlHandlers
; i
> 0; i
--)
127 if (CtrlHandlers
[i
- 1](nCode
)) break;
131 RtlLeaveCriticalSection(&ConsoleLock
);
140 case CTRL_CLOSE_EVENT
:
141 case CTRL_LOGOFF_EVENT
:
142 case CTRL_SHUTDOWN_EVENT
:
145 case CTRL_LAST_CLOSE_EVENT
:
147 * In case the console app hasn't register for last close notification,
148 * just kill this console handler thread. We don't want that such apps
149 * get killed for unexpected reasons. On the contrary apps that registered
150 * can be killed because they expect to be.
152 if (!LastCloseNotify
) ExitThread(0);
156 ExitProcess(CONTROL_C_EXIT
);
164 ASSERT(ConsoleInitialized
);
166 RtlEnterCriticalSection(&ConsoleLock
);
169 if ((nCode
!= CTRL_C_EVENT
) || (NtCurrentPeb()->ProcessParameters
->ConsoleFlags
!= 1))
171 for (i
= NrCtrlHandlers
; i
> 0; i
--)
174 (CodeAndFlag
& MINLONG
) &&
175 ((nCode
== CTRL_LOGOFF_EVENT
) || (nCode
== CTRL_SHUTDOWN_EVENT
)))
177 DPRINT("Skipping system/service apps\n");
181 if (CtrlHandlers
[i
- 1](nCode
))
185 case CTRL_CLOSE_EVENT
:
186 case CTRL_LAST_CLOSE_EVENT
:
187 case CTRL_LOGOFF_EVENT
:
188 case CTRL_SHUTDOWN_EVENT
:
189 nExitCode
= CodeAndFlag
;
197 RtlLeaveCriticalSection(&ConsoleLock
);
199 ExitThread(nExitCode
);
200 return STATUS_SUCCESS
;
204 InitializeCtrlHandling(VOID
)
206 /* Initialize Console Ctrl Handler */
207 NrAllocatedHandlers
= NrCtrlHandlers
= 1;
208 CtrlHandlers
= InitialHandler
;
209 CtrlHandlers
[0] = DefaultConsoleCtrlHandler
;
213 /* Input EXE Name Support *****************************************************/
219 PPEB Peb
= NtCurrentPeb();
220 PCURDIR CurrentDirectory
= &Peb
->ProcessParameters
->CurrentDirectory
;
221 PLDR_DATA_TABLE_ENTRY ImageEntry
;
223 if (ExeNameInitialized
) return;
225 /* Initialize the EXE name lock */
226 Status
= RtlInitializeCriticalSection(&ExeNameLock
);
227 if (!NT_SUCCESS(Status
)) return;
228 ExeNameInitialized
= TRUE
;
230 ImageEntry
= CONTAINING_RECORD(Peb
->Ldr
->InLoadOrderModuleList
.Flink
,
231 LDR_DATA_TABLE_ENTRY
,
234 /* Retrieve the EXE name, NULL-terminate it... */
235 ExeNameLength
= min(sizeof(ExeNameBuffer
)/sizeof(ExeNameBuffer
[0]),
236 ImageEntry
->BaseDllName
.Length
/ sizeof(WCHAR
));
237 RtlCopyMemory(ExeNameBuffer
,
238 ImageEntry
->BaseDllName
.Buffer
,
239 ImageEntry
->BaseDllName
.Length
);
240 ExeNameBuffer
[ExeNameLength
] = UNICODE_NULL
;
242 /* ... and retrieve the current directory path and NULL-terminate it. */
243 StartDirLength
= min(sizeof(StartDirBuffer
)/sizeof(StartDirBuffer
[0]),
244 CurrentDirectory
->DosPath
.Length
/ sizeof(WCHAR
));
245 RtlCopyMemory(StartDirBuffer
,
246 CurrentDirectory
->DosPath
.Buffer
,
247 CurrentDirectory
->DosPath
.Length
);
248 StartDirBuffer
[StartDirLength
] = UNICODE_NULL
;
253 * The "LPDWORD Length" parameters point on input to the maximum size of
254 * the buffers that can hold data (if != 0), and on output they hold the
255 * real size of the data. If "Length" are == 0 on input, then on output
256 * they receive the full size of the data.
257 * The "LPWSTR* String" parameters have a double meaning:
258 * - when "CaptureStrings" is TRUE, data is copied to the buffers pointed
259 * by the pointers (*String).
260 * - when "CaptureStrings" is FALSE, "*String" are set to the addresses of
264 SetUpAppName(IN BOOLEAN CaptureStrings
,
265 IN OUT LPDWORD CurDirLength
,
266 IN OUT LPWSTR
* CurDir
,
267 IN OUT LPDWORD AppNameLength
,
268 IN OUT LPWSTR
* AppName
)
272 /* Retrieve the needed buffer size */
273 Length
= (StartDirLength
+ 1) * sizeof(WCHAR
);
274 if (*CurDirLength
> 0) Length
= min(Length
, *CurDirLength
);
275 *CurDirLength
= Length
;
277 /* Capture the data if needed, or, return a pointer to it */
281 * Length is always >= sizeof(WCHAR). Copy everything but the
282 * possible trailing NULL character, and then NULL-terminate.
284 Length
-= sizeof(WCHAR
);
285 RtlCopyMemory(*CurDir
, StartDirBuffer
, Length
);
286 (*CurDir
)[Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
290 *CurDir
= StartDirBuffer
;
293 /* Retrieve the needed buffer size */
294 Length
= (ExeNameLength
+ 1) * sizeof(WCHAR
);
295 if (*AppNameLength
> 0) Length
= min(Length
, *AppNameLength
);
296 *AppNameLength
= Length
;
298 /* Capture the data if needed, or, return a pointer to it */
302 * Length is always >= sizeof(WCHAR). Copy everything but the
303 * possible trailing NULL character, and then NULL-terminate.
305 Length
-= sizeof(WCHAR
);
306 RtlCopyMemory(*AppName
, ExeNameBuffer
, Length
);
307 (*AppName
)[Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
311 *AppName
= ExeNameBuffer
;
316 GetCurrentExeName(OUT PWCHAR ExeName
,
317 IN USHORT BufferSize
)
321 if (ExeNameInitialized
)
323 RtlEnterCriticalSection(&ExeNameLock
);
325 if (BufferSize
> ExeNameLength
* sizeof(WCHAR
))
326 BufferSize
= ExeNameLength
* sizeof(WCHAR
);
328 RtlCopyMemory(ExeName
, ExeNameBuffer
, BufferSize
);
330 RtlLeaveCriticalSection(&ExeNameLock
);
331 ExeLength
= BufferSize
;
335 *ExeName
= UNICODE_NULL
;
342 /* FUNCTIONS ******************************************************************/
345 IntCheckForConsoleFileName(IN LPCWSTR pszName
,
346 IN DWORD dwDesiredAccess
)
348 LPCWSTR ConsoleName
= pszName
;
349 ULONG DeviceNameInfo
;
352 * Check whether we deal with a DOS device, and if so,
353 * strip the path till the file name.
354 * Therefore, things like \\.\CON or C:\some_path\CONIN$
355 * are transformed into CON or CONIN$, for example.
357 DeviceNameInfo
= RtlIsDosDeviceName_U(pszName
);
358 if (DeviceNameInfo
!= 0)
360 ConsoleName
= (LPCWSTR
)((ULONG_PTR
)ConsoleName
+ ((DeviceNameInfo
>> 16) & 0xFFFF));
363 /* Return a standard console "file" name according to what we passed in parameters */
364 if (_wcsicmp(ConsoleName
, BaseConInputFileName
) == 0)
366 return BaseConInputFileName
;
368 else if (_wcsicmp(ConsoleName
, BaseConOutputFileName
) == 0)
370 return BaseConOutputFileName
;
372 else if (_wcsicmp(ConsoleName
, BaseConFileName
) == 0)
374 if ((dwDesiredAccess
& (GENERIC_READ
| GENERIC_WRITE
)) == GENERIC_READ
)
376 return BaseConInputFileName
;
378 else if ((dwDesiredAccess
& (GENERIC_READ
| GENERIC_WRITE
)) == GENERIC_WRITE
)
380 return BaseConOutputFileName
;
384 /* If we are there, that means that either the file name or the desired access are wrong */
390 * @implemented (Undocumented)
391 * @note See http://undoc.airesoft.co.uk/kernel32.dll/ConsoleMenuControl.php
396 ConsoleMenuControl(HANDLE hConsoleOutput
,
400 CONSOLE_API_MESSAGE ApiMessage
;
401 PCONSOLE_MENUCONTROL MenuControlRequest
= &ApiMessage
.Data
.MenuControlRequest
;
403 MenuControlRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
404 MenuControlRequest
->OutputHandle
= hConsoleOutput
;
405 MenuControlRequest
->CmdIdLow
= dwCmdIdLow
;
406 MenuControlRequest
->CmdIdHigh
= dwCmdIdHigh
;
407 MenuControlRequest
->MenuHandle
= NULL
;
409 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
411 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepMenuControl
),
412 sizeof(*MenuControlRequest
));
414 return MenuControlRequest
->MenuHandle
;
424 DuplicateConsoleHandle(HANDLE hConsole
,
425 DWORD dwDesiredAccess
,
429 CONSOLE_API_MESSAGE ApiMessage
;
430 PCONSOLE_DUPLICATEHANDLE DuplicateHandleRequest
= &ApiMessage
.Data
.DuplicateHandleRequest
;
432 if ( (dwOptions
& ~(DUPLICATE_CLOSE_SOURCE
| DUPLICATE_SAME_ACCESS
)) ||
433 (!(dwOptions
& DUPLICATE_SAME_ACCESS
) &&
434 (dwDesiredAccess
& ~(GENERIC_READ
| GENERIC_WRITE
))) )
436 SetLastError(ERROR_INVALID_PARAMETER
);
437 return INVALID_HANDLE_VALUE
;
440 DuplicateHandleRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
441 DuplicateHandleRequest
->SourceHandle
= hConsole
;
442 DuplicateHandleRequest
->DesiredAccess
= dwDesiredAccess
;
443 DuplicateHandleRequest
->InheritHandle
= bInheritHandle
;
444 DuplicateHandleRequest
->Options
= dwOptions
;
446 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
448 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepDuplicateHandle
),
449 sizeof(*DuplicateHandleRequest
));
450 if (!NT_SUCCESS(ApiMessage
.Status
))
452 BaseSetLastNTError(ApiMessage
.Status
);
453 return INVALID_HANDLE_VALUE
;
456 return DuplicateHandleRequest
->TargetHandle
;
465 GetConsoleHandleInformation(IN HANDLE hHandle
,
466 OUT LPDWORD lpdwFlags
)
468 CONSOLE_API_MESSAGE ApiMessage
;
469 PCONSOLE_GETHANDLEINFO GetHandleInfoRequest
= &ApiMessage
.Data
.GetHandleInfoRequest
;
471 GetHandleInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
472 GetHandleInfoRequest
->Handle
= hHandle
;
474 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
476 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetHandleInformation
),
477 sizeof(*GetHandleInfoRequest
));
478 if (!NT_SUCCESS(ApiMessage
.Status
))
480 BaseSetLastNTError(ApiMessage
.Status
);
484 *lpdwFlags
= GetHandleInfoRequest
->Flags
;
495 SetConsoleHandleInformation(IN HANDLE hHandle
,
499 CONSOLE_API_MESSAGE ApiMessage
;
500 PCONSOLE_SETHANDLEINFO SetHandleInfoRequest
= &ApiMessage
.Data
.SetHandleInfoRequest
;
502 SetHandleInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
503 SetHandleInfoRequest
->Handle
= hHandle
;
504 SetHandleInfoRequest
->Mask
= dwMask
;
505 SetHandleInfoRequest
->Flags
= dwFlags
;
507 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
509 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetHandleInformation
),
510 sizeof(*SetHandleInfoRequest
));
511 if (!NT_SUCCESS(ApiMessage
.Status
))
513 BaseSetLastNTError(ApiMessage
.Status
);
526 GetConsoleDisplayMode(LPDWORD lpModeFlags
)
528 CONSOLE_API_MESSAGE ApiMessage
;
529 PCONSOLE_GETDISPLAYMODE GetDisplayModeRequest
= &ApiMessage
.Data
.GetDisplayModeRequest
;
531 if (lpModeFlags
== NULL
)
533 SetLastError(ERROR_INVALID_PARAMETER
);
537 GetDisplayModeRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
539 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
541 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetDisplayMode
),
542 sizeof(*GetDisplayModeRequest
));
543 if (!NT_SUCCESS(ApiMessage
.Status
))
545 BaseSetLastNTError(ApiMessage
.Status
);
549 *lpModeFlags
= GetDisplayModeRequest
->DisplayMode
; // ModeFlags
556 * @unimplemented (Undocumented)
560 GetConsoleFontInfo(HANDLE hConsoleOutput
,
563 PCONSOLE_FONT_INFO lpConsoleFontInfo
)
565 DPRINT1("GetConsoleFontInfo(0x%p, %d, %lu, 0x%p) UNIMPLEMENTED!\n", hConsoleOutput
, bMaximumWindow
, nFontCount
, lpConsoleFontInfo
);
566 SetLastError(ERROR_CALL_NOT_IMPLEMENTED
);
577 GetConsoleFontSize(HANDLE hConsoleOutput
,
580 COORD Empty
= {0, 0};
581 DPRINT1("GetConsoleFontSize(0x%p, 0x%x) UNIMPLEMENTED!\n", hConsoleOutput
, nFont
);
582 SetLastError(ERROR_CALL_NOT_IMPLEMENTED
);
588 * @implemented (Undocumented)
592 GetConsoleHardwareState(HANDLE hConsoleOutput
,
596 CONSOLE_API_MESSAGE ApiMessage
;
597 PCONSOLE_GETSETHWSTATE HardwareStateRequest
= &ApiMessage
.Data
.HardwareStateRequest
;
599 DPRINT1("GetConsoleHardwareState(%lu, 0x%p) UNIMPLEMENTED!\n", Flags
, State
);
601 if (Flags
== NULL
|| State
== NULL
)
603 SetLastError(ERROR_INVALID_PARAMETER
);
607 HardwareStateRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
608 HardwareStateRequest
->OutputHandle
= hConsoleOutput
;
610 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
612 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetHardwareState
),
613 sizeof(*HardwareStateRequest
));
614 if (!NT_SUCCESS(ApiMessage
.Status
))
616 BaseSetLastNTError(ApiMessage
.Status
);
620 *Flags
= HardwareStateRequest
->Flags
;
621 *State
= HardwareStateRequest
->State
;
628 * @implemented (Undocumented)
632 GetConsoleInputWaitHandle(VOID
)
634 return InputWaitHandle
;
643 GetCurrentConsoleFont(HANDLE hConsoleOutput
,
645 PCONSOLE_FONT_INFO lpConsoleCurrentFont
)
647 DPRINT1("GetCurrentConsoleFont(0x%p, 0x%x, 0x%p) UNIMPLEMENTED!\n", hConsoleOutput
, bMaximumWindow
, lpConsoleCurrentFont
);
648 SetLastError(ERROR_CALL_NOT_IMPLEMENTED
);
654 * @unimplemented (Undocumented)
659 GetNumberOfConsoleFonts(VOID
)
661 DPRINT1("GetNumberOfConsoleFonts() UNIMPLEMENTED!\n");
662 SetLastError(ERROR_CALL_NOT_IMPLEMENTED
);
668 * @implemented (Undocumented)
669 * @note See http://blog.airesoft.co.uk/2012/10/things-ms-can-do-that-they-dont-tell-you-about-console-graphics/
673 InvalidateConsoleDIBits(IN HANDLE hConsoleOutput
,
674 IN PSMALL_RECT lpRect
)
676 CONSOLE_API_MESSAGE ApiMessage
;
677 PCONSOLE_INVALIDATEDIBITS InvalidateDIBitsRequest
= &ApiMessage
.Data
.InvalidateDIBitsRequest
;
681 SetLastError(ERROR_INVALID_PARAMETER
);
685 InvalidateDIBitsRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
686 InvalidateDIBitsRequest
->OutputHandle
= hConsoleOutput
;
687 InvalidateDIBitsRequest
->Region
= *lpRect
;
689 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
691 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepInvalidateBitMapRect
),
692 sizeof(*InvalidateDIBitsRequest
));
693 if (!NT_SUCCESS(ApiMessage
.Status
))
695 BaseSetLastNTError(ApiMessage
.Status
);
704 * @implemented (Undocumented)
708 OpenConsoleW(LPCWSTR wsName
,
709 DWORD dwDesiredAccess
,
713 CONSOLE_API_MESSAGE ApiMessage
;
714 PCONSOLE_OPENCONSOLE OpenConsoleRequest
= &ApiMessage
.Data
.OpenConsoleRequest
;
715 CONSOLE_HANDLE_TYPE HandleType
;
717 if (wsName
&& (_wcsicmp(wsName
, BaseConInputFileName
) == 0))
719 HandleType
= HANDLE_INPUT
;
721 else if (wsName
&& (_wcsicmp(wsName
, BaseConOutputFileName
) == 0))
723 HandleType
= HANDLE_OUTPUT
;
727 SetLastError(ERROR_INVALID_PARAMETER
);
728 return INVALID_HANDLE_VALUE
;
731 if ( (dwDesiredAccess
& ~(GENERIC_READ
| GENERIC_WRITE
)) ||
732 (dwShareMode
& ~(FILE_SHARE_READ
| FILE_SHARE_WRITE
)) )
734 SetLastError(ERROR_INVALID_PARAMETER
);
735 return INVALID_HANDLE_VALUE
;
738 OpenConsoleRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
739 OpenConsoleRequest
->HandleType
= HandleType
;
740 OpenConsoleRequest
->DesiredAccess
= dwDesiredAccess
;
741 OpenConsoleRequest
->InheritHandle
= bInheritHandle
;
742 OpenConsoleRequest
->ShareMode
= dwShareMode
;
744 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
746 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepOpenConsole
),
747 sizeof(*OpenConsoleRequest
));
748 if (!NT_SUCCESS(ApiMessage
.Status
))
750 BaseSetLastNTError(ApiMessage
.Status
);
751 return INVALID_HANDLE_VALUE
;
754 return OpenConsoleRequest
->Handle
;
759 * @implemented (Undocumented)
760 * @note See http://undoc.airesoft.co.uk/kernel32.dll/SetConsoleCursor.php
765 SetConsoleCursor(HANDLE hConsoleOutput
,
768 CONSOLE_API_MESSAGE ApiMessage
;
769 PCONSOLE_SETCURSOR SetCursorRequest
= &ApiMessage
.Data
.SetCursorRequest
;
771 SetCursorRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
772 SetCursorRequest
->OutputHandle
= hConsoleOutput
;
773 SetCursorRequest
->CursorHandle
= hCursor
;
775 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
777 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetCursor
),
778 sizeof(*SetCursorRequest
));
779 if (!NT_SUCCESS(ApiMessage
.Status
))
781 BaseSetLastNTError(ApiMessage
.Status
);
794 SetConsoleDisplayMode(HANDLE hConsoleOutput
,
795 DWORD dwFlags
, // dwModeFlags
796 PCOORD lpNewScreenBufferDimensions
)
798 CONSOLE_API_MESSAGE ApiMessage
;
799 PCONSOLE_SETDISPLAYMODE SetDisplayModeRequest
= &ApiMessage
.Data
.SetDisplayModeRequest
;
801 SetDisplayModeRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
802 SetDisplayModeRequest
->OutputHandle
= hConsoleOutput
;
803 SetDisplayModeRequest
->DisplayMode
= dwFlags
; // ModeFlags ; dwModeFlags
804 SetDisplayModeRequest
->NewSBDim
.X
= 0;
805 SetDisplayModeRequest
->NewSBDim
.Y
= 0;
806 /* SetDisplayModeRequest->EventHandle; */
808 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
810 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetDisplayMode
),
811 sizeof(*SetDisplayModeRequest
));
812 if (!NT_SUCCESS(ApiMessage
.Status
))
814 BaseSetLastNTError(ApiMessage
.Status
);
818 if (lpNewScreenBufferDimensions
)
819 *lpNewScreenBufferDimensions
= SetDisplayModeRequest
->NewSBDim
;
826 * @unimplemented (Undocumented)
831 SetConsoleFont(HANDLE hConsoleOutput
,
834 DPRINT1("SetConsoleFont(0x%p, %lu) UNIMPLEMENTED!\n", hConsoleOutput
, nFont
);
835 SetLastError(ERROR_CALL_NOT_IMPLEMENTED
);
841 * @implemented (Undocumented)
845 SetConsoleHardwareState(HANDLE hConsoleOutput
,
849 CONSOLE_API_MESSAGE ApiMessage
;
850 PCONSOLE_GETSETHWSTATE HardwareStateRequest
= &ApiMessage
.Data
.HardwareStateRequest
;
852 DPRINT1("SetConsoleHardwareState(%lu, %lu) UNIMPLEMENTED!\n", Flags
, State
);
854 HardwareStateRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
855 HardwareStateRequest
->OutputHandle
= hConsoleOutput
;
856 HardwareStateRequest
->Flags
= Flags
;
857 HardwareStateRequest
->State
= State
;
859 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
861 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetHardwareState
),
862 sizeof(*HardwareStateRequest
));
863 if (!NT_SUCCESS(ApiMessage
.Status
))
865 BaseSetLastNTError(ApiMessage
.Status
);
874 * @unimplemented (Undocumented)
879 SetConsoleKeyShortcuts(DWORD Unknown0
,
884 DPRINT1("SetConsoleKeyShortcuts(0x%x, 0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0
, Unknown1
, Unknown2
, Unknown3
);
885 SetLastError(ERROR_CALL_NOT_IMPLEMENTED
);
891 * @implemented (Undocumented)
892 * @note See http://undoc.airesoft.co.uk/kernel32.dll/SetConsoleMaximumWindowSize.php
893 * Does nothing, returns TRUE only. Checked on Windows Server 2003.
897 SetConsoleMaximumWindowSize(HANDLE hConsoleOutput
,
900 DPRINT1("SetConsoleMaximumWindowSize(0x%p, {%d, %d}) does nothing\n",
901 hConsoleOutput
, dwMaximumSize
.X
, dwMaximumSize
.Y
);
907 * @implemented (Undocumented)
912 SetConsoleMenuClose(BOOL bEnable
)
914 CONSOLE_API_MESSAGE ApiMessage
;
915 PCONSOLE_SETMENUCLOSE SetMenuCloseRequest
= &ApiMessage
.Data
.SetMenuCloseRequest
;
917 SetMenuCloseRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
918 SetMenuCloseRequest
->Enable
= bEnable
;
920 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
922 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetMenuClose
),
923 sizeof(*SetMenuCloseRequest
));
924 if (!NT_SUCCESS(ApiMessage
.Status
))
926 BaseSetLastNTError(ApiMessage
.Status
);
935 * @implemented (Undocumented)
936 * @note See http://comments.gmane.org/gmane.comp.lang.harbour.devel/27844
937 * Usage example: https://github.com/harbour/core/commit/d79a1b7b812cbde6ddf718ebfd6939a24f633e52
942 SetConsolePalette(HANDLE hConsoleOutput
,
946 CONSOLE_API_MESSAGE ApiMessage
;
947 PCONSOLE_SETPALETTE SetPaletteRequest
= &ApiMessage
.Data
.SetPaletteRequest
;
949 SetPaletteRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
950 SetPaletteRequest
->OutputHandle
= hConsoleOutput
;
951 SetPaletteRequest
->PaletteHandle
= hPalette
;
952 SetPaletteRequest
->Usage
= dwUsage
;
954 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
956 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetPalette
),
957 sizeof(*SetPaletteRequest
));
958 if (!NT_SUCCESS(ApiMessage
.Status
))
960 BaseSetLastNTError(ApiMessage
.Status
);
968 * @implemented (Undocumented)
969 * @note See http://undoc.airesoft.co.uk/kernel32.dll/ShowConsoleCursor.php
974 ShowConsoleCursor(HANDLE hConsoleOutput
,
977 CONSOLE_API_MESSAGE ApiMessage
;
978 PCONSOLE_SHOWCURSOR ShowCursorRequest
= &ApiMessage
.Data
.ShowCursorRequest
;
980 ShowCursorRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
981 ShowCursorRequest
->OutputHandle
= hConsoleOutput
;
982 ShowCursorRequest
->Show
= bShow
;
983 ShowCursorRequest
->RefCount
= 0;
985 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
987 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepShowCursor
),
988 sizeof(*ShowCursorRequest
));
990 return ShowCursorRequest
->RefCount
;
995 * FUNCTION: Checks whether the given handle is a valid console handle.
998 * hIoHandle - Handle to be checked.
1001 * TRUE : Handle is a valid console handle.
1002 * FALSE: Handle is not a valid console handle.
1004 * STATUS: Officially undocumented
1011 VerifyConsoleIoHandle(HANDLE hIoHandle
)
1013 CONSOLE_API_MESSAGE ApiMessage
;
1014 PCONSOLE_VERIFYHANDLE VerifyHandleRequest
= &ApiMessage
.Data
.VerifyHandleRequest
;
1016 VerifyHandleRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1017 VerifyHandleRequest
->Handle
= hIoHandle
;
1018 VerifyHandleRequest
->IsValid
= FALSE
;
1020 /* If the process is not attached to a console, return invalid handle */
1021 if (VerifyHandleRequest
->ConsoleHandle
== NULL
) return FALSE
;
1023 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1025 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepVerifyIoHandle
),
1026 sizeof(*VerifyHandleRequest
));
1027 if (!NT_SUCCESS(ApiMessage
.Status
))
1029 BaseSetLastNTError(ApiMessage
.Status
);
1033 return VerifyHandleRequest
->IsValid
;
1038 * @implemented (Undocumented)
1043 CloseConsoleHandle(HANDLE hHandle
)
1045 CONSOLE_API_MESSAGE ApiMessage
;
1046 PCONSOLE_CLOSEHANDLE CloseHandleRequest
= &ApiMessage
.Data
.CloseHandleRequest
;
1048 CloseHandleRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1049 CloseHandleRequest
->Handle
= hHandle
;
1051 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1053 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepCloseHandle
),
1054 sizeof(*CloseHandleRequest
));
1055 if (!NT_SUCCESS(ApiMessage
.Status
))
1057 BaseSetLastNTError(ApiMessage
.Status
);
1071 GetStdHandle(DWORD nStdHandle
)
1073 * FUNCTION: Get a handle for the standard input, standard output
1074 * and a standard error device.
1077 * nStdHandle - Specifies the device for which to return the handle.
1079 * RETURNS: If the function succeeds, the return value is the handle
1080 * of the specified device. Otherwise the value is INVALID_HANDLE_VALUE.
1083 PRTL_USER_PROCESS_PARAMETERS Ppb
= NtCurrentPeb()->ProcessParameters
;
1084 HANDLE Handle
= INVALID_HANDLE_VALUE
;
1088 case STD_INPUT_HANDLE
:
1089 Handle
= Ppb
->StandardInput
;
1092 case STD_OUTPUT_HANDLE
:
1093 Handle
= Ppb
->StandardOutput
;
1096 case STD_ERROR_HANDLE
:
1097 Handle
= Ppb
->StandardError
;
1101 /* If the returned handle is invalid, set last error */
1102 if (Handle
== INVALID_HANDLE_VALUE
) SetLastError(ERROR_INVALID_HANDLE
);
1114 SetStdHandle(DWORD nStdHandle
,
1117 * FUNCTION: Set the handle for the standard input, standard output or
1118 * the standard error device.
1121 * nStdHandle - Specifies the handle to be set.
1122 * hHandle - The handle to set.
1124 * RETURNS: TRUE if the function succeeds, FALSE otherwise.
1127 PRTL_USER_PROCESS_PARAMETERS Ppb
= NtCurrentPeb()->ProcessParameters
;
1129 /* No need to check if hHandle == INVALID_HANDLE_VALUE */
1133 case STD_INPUT_HANDLE
:
1134 Ppb
->StandardInput
= hHandle
;
1137 case STD_OUTPUT_HANDLE
:
1138 Ppb
->StandardOutput
= hHandle
;
1141 case STD_ERROR_HANDLE
:
1142 Ppb
->StandardError
= hHandle
;
1146 /* nStdHandle was invalid, bail out */
1147 SetLastError(ERROR_INVALID_HANDLE
);
1156 IntAllocConsole(LPWSTR Title
,
1159 DWORD DesktopLength
,
1163 DWORD AppNameLength
,
1164 LPTHREAD_START_ROUTINE CtrlRoutine
,
1165 LPTHREAD_START_ROUTINE PropRoutine
,
1166 PCONSOLE_START_INFO ConsoleStartInfo
)
1168 BOOL Success
= TRUE
;
1169 #ifdef USE_CONSOLE_INIT_HANDLES
1173 CONSOLE_API_MESSAGE ApiMessage
;
1174 PCONSOLE_ALLOCCONSOLE AllocConsoleRequest
= &ApiMessage
.Data
.AllocConsoleRequest
;
1175 PCSR_CAPTURE_BUFFER CaptureBuffer
;
1177 AllocConsoleRequest
->CtrlRoutine
= CtrlRoutine
;
1178 AllocConsoleRequest
->PropRoutine
= PropRoutine
;
1180 CaptureBuffer
= CsrAllocateCaptureBuffer(5, TitleLength
+
1184 sizeof(CONSOLE_START_INFO
));
1185 if (CaptureBuffer
== NULL
)
1187 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
1192 CsrCaptureMessageBuffer(CaptureBuffer
,
1194 sizeof(CONSOLE_START_INFO
),
1195 (PVOID
*)&AllocConsoleRequest
->ConsoleStartInfo
);
1197 AllocConsoleRequest
->TitleLength
= TitleLength
;
1198 CsrCaptureMessageBuffer(CaptureBuffer
,
1201 (PVOID
*)&AllocConsoleRequest
->ConsoleTitle
);
1203 AllocConsoleRequest
->DesktopLength
= DesktopLength
;
1204 CsrCaptureMessageBuffer(CaptureBuffer
,
1207 (PVOID
*)&AllocConsoleRequest
->Desktop
);
1209 AllocConsoleRequest
->CurDirLength
= CurDirLength
;
1210 CsrCaptureMessageBuffer(CaptureBuffer
,
1213 (PVOID
*)&AllocConsoleRequest
->CurDir
);
1215 AllocConsoleRequest
->AppNameLength
= AppNameLength
;
1216 CsrCaptureMessageBuffer(CaptureBuffer
,
1219 (PVOID
*)&AllocConsoleRequest
->AppName
);
1221 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1223 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepAlloc
),
1224 sizeof(*AllocConsoleRequest
));
1225 if (!NT_SUCCESS(ApiMessage
.Status
))
1227 BaseSetLastNTError(ApiMessage
.Status
);
1232 #ifdef USE_CONSOLE_INIT_HANDLES
1233 // Is AllocConsoleRequest->ConsoleStartInfo->Events aligned on handle boundary ????
1234 Status
= NtWaitForMultipleObjects(2, AllocConsoleRequest
->ConsoleStartInfo
->Events
,
1235 WaitAny
, FALSE
, NULL
);
1236 if (!NT_SUCCESS(Status
))
1238 BaseSetLastNTError(Status
);
1243 NtClose(AllocConsoleRequest
->ConsoleStartInfo
->Events
[0]);
1244 NtClose(AllocConsoleRequest
->ConsoleStartInfo
->Events
[1]);
1245 if (Status
!= STATUS_SUCCESS
)
1247 NtCurrentPeb()->ProcessParameters
->ConsoleHandle
= NULL
;
1253 RtlCopyMemory(ConsoleStartInfo
,
1254 AllocConsoleRequest
->ConsoleStartInfo
,
1255 sizeof(CONSOLE_START_INFO
));
1260 if (CaptureBuffer
) CsrFreeCaptureBuffer(CaptureBuffer
);
1270 CONSOLE_START_INFO ConsoleStartInfo
;
1272 PWCHAR ConsoleTitle
;
1277 ULONG TitleLength
= (MAX_PATH
+ 1) * sizeof(WCHAR
);
1278 ULONG DesktopLength
= (MAX_PATH
+ 1) * sizeof(WCHAR
);
1279 ULONG AppNameLength
= 128 * sizeof(WCHAR
);
1280 ULONG CurDirLength
= (MAX_PATH
+ 1) * sizeof(WCHAR
);
1284 RtlEnterCriticalSection(&ConsoleLock
);
1286 if (NtCurrentPeb()->ProcessParameters
->ConsoleHandle
)
1288 DPRINT1("AllocConsole: Allocating a console to a process already having one\n");
1289 SetLastError(ERROR_ACCESS_DENIED
);
1294 /* Set up the console properties */
1295 SetUpConsoleInfo(FALSE
,
1301 DPRINT("ConsoleTitle = '%S' - Desktop = '%S'\n",
1302 ConsoleTitle
, Desktop
);
1304 /* Initialize the Input EXE name */
1311 DPRINT("CurDir = '%S' - AppName = '%S'\n",
1314 Success
= IntAllocConsole(ConsoleTitle
,
1322 ConsoleControlDispatcher
,
1327 /* Set up the handles */
1328 SetUpHandles(&ConsoleStartInfo
);
1329 InputWaitHandle
= ConsoleStartInfo
.InputWaitHandle
;
1331 /* Initialize Console Ctrl Handling */
1332 InitializeCtrlHandling();
1334 /* Sets the current console locale for this thread */
1339 RtlLeaveCriticalSection(&ConsoleLock
);
1352 CONSOLE_API_MESSAGE ApiMessage
;
1353 PCONSOLE_FREECONSOLE FreeConsoleRequest
= &ApiMessage
.Data
.FreeConsoleRequest
;
1354 HANDLE ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1356 /* We must have a non-trivial handle to close */
1357 if (ConsoleHandle
== NULL
) // IsConsoleHandle(ConsoleHandle)
1359 SetLastError(ERROR_INVALID_PARAMETER
);
1363 /* Set up the data to send to the Console Server */
1364 FreeConsoleRequest
->ConsoleHandle
= ConsoleHandle
;
1366 /* Call the server */
1367 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1369 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepFree
),
1370 sizeof(*FreeConsoleRequest
));
1372 /* Check for success */
1373 if (!NT_SUCCESS(ApiMessage
.Status
))
1375 BaseSetLastNTError(ApiMessage
.Status
);
1379 /* Reset the console handle */
1380 NtCurrentPeb()->ProcessParameters
->ConsoleHandle
= NULL
;
1382 /* Close the associated input handle */
1383 CloseHandle(InputWaitHandle
);
1384 InputWaitHandle
= INVALID_HANDLE_VALUE
;
1395 GetConsoleScreenBufferInfo(HANDLE hConsoleOutput
,
1396 PCONSOLE_SCREEN_BUFFER_INFO lpConsoleScreenBufferInfo
)
1398 CONSOLE_API_MESSAGE ApiMessage
;
1399 PCONSOLE_GETSCREENBUFFERINFO ScreenBufferInfoRequest
= &ApiMessage
.Data
.ScreenBufferInfoRequest
;
1401 if (lpConsoleScreenBufferInfo
== NULL
)
1403 SetLastError(ERROR_INVALID_PARAMETER
);
1407 ScreenBufferInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1408 ScreenBufferInfoRequest
->OutputHandle
= hConsoleOutput
;
1410 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1412 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetScreenBufferInfo
),
1413 sizeof(*ScreenBufferInfoRequest
));
1414 if (!NT_SUCCESS(ApiMessage
.Status
))
1416 BaseSetLastNTError(ApiMessage
.Status
);
1420 lpConsoleScreenBufferInfo
->dwSize
= ScreenBufferInfoRequest
->ScreenBufferSize
;
1421 lpConsoleScreenBufferInfo
->dwCursorPosition
= ScreenBufferInfoRequest
->CursorPosition
;
1422 lpConsoleScreenBufferInfo
->wAttributes
= ScreenBufferInfoRequest
->Attributes
;
1423 lpConsoleScreenBufferInfo
->srWindow
.Left
= ScreenBufferInfoRequest
->ViewOrigin
.X
;
1424 lpConsoleScreenBufferInfo
->srWindow
.Top
= ScreenBufferInfoRequest
->ViewOrigin
.Y
;
1425 lpConsoleScreenBufferInfo
->srWindow
.Right
= ScreenBufferInfoRequest
->ViewOrigin
.X
+ ScreenBufferInfoRequest
->ViewSize
.X
- 1;
1426 lpConsoleScreenBufferInfo
->srWindow
.Bottom
= ScreenBufferInfoRequest
->ViewOrigin
.Y
+ ScreenBufferInfoRequest
->ViewSize
.Y
- 1;
1427 lpConsoleScreenBufferInfo
->dwMaximumWindowSize
= ScreenBufferInfoRequest
->MaximumViewSize
;
1439 SetConsoleCursorPosition(HANDLE hConsoleOutput
,
1440 COORD dwCursorPosition
)
1442 CONSOLE_API_MESSAGE ApiMessage
;
1443 PCONSOLE_SETCURSORPOSITION SetCursorPositionRequest
= &ApiMessage
.Data
.SetCursorPositionRequest
;
1445 SetCursorPositionRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1446 SetCursorPositionRequest
->OutputHandle
= hConsoleOutput
;
1447 SetCursorPositionRequest
->Position
= dwCursorPosition
;
1449 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1451 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetCursorPosition
),
1452 sizeof(*SetCursorPositionRequest
));
1453 if (!NT_SUCCESS(ApiMessage
.Status
))
1455 BaseSetLastNTError(ApiMessage
.Status
);
1468 GetConsoleMode(HANDLE hConsoleHandle
,
1471 CONSOLE_API_MESSAGE ApiMessage
;
1472 PCONSOLE_GETSETCONSOLEMODE ConsoleModeRequest
= &ApiMessage
.Data
.ConsoleModeRequest
;
1476 SetLastError(ERROR_INVALID_PARAMETER
);
1480 ConsoleModeRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1481 ConsoleModeRequest
->Handle
= hConsoleHandle
;
1483 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1485 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetMode
),
1486 sizeof(*ConsoleModeRequest
));
1487 if (!NT_SUCCESS(ApiMessage
.Status
))
1489 BaseSetLastNTError(ApiMessage
.Status
);
1493 *lpMode
= ConsoleModeRequest
->Mode
;
1505 SetConsoleMode(HANDLE hConsoleHandle
,
1508 CONSOLE_API_MESSAGE ApiMessage
;
1509 PCONSOLE_GETSETCONSOLEMODE ConsoleModeRequest
= &ApiMessage
.Data
.ConsoleModeRequest
;
1511 ConsoleModeRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1512 ConsoleModeRequest
->Handle
= hConsoleHandle
;
1513 ConsoleModeRequest
->Mode
= dwMode
;
1515 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1517 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetMode
),
1518 sizeof(*ConsoleModeRequest
));
1519 if (!NT_SUCCESS(ApiMessage
.Status
))
1521 BaseSetLastNTError(ApiMessage
.Status
);
1534 GetNumberOfConsoleInputEvents(HANDLE hConsoleInput
,
1535 LPDWORD lpNumberOfEvents
)
1537 CONSOLE_API_MESSAGE ApiMessage
;
1538 PCONSOLE_GETNUMINPUTEVENTS GetNumInputEventsRequest
= &ApiMessage
.Data
.GetNumInputEventsRequest
;
1540 GetNumInputEventsRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1541 GetNumInputEventsRequest
->InputHandle
= hConsoleInput
;
1542 GetNumInputEventsRequest
->NumberOfEvents
= 0;
1544 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1546 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetNumberOfInputEvents
),
1547 sizeof(*GetNumInputEventsRequest
));
1548 if (!NT_SUCCESS(ApiMessage
.Status
))
1550 BaseSetLastNTError(ApiMessage
.Status
);
1554 if (lpNumberOfEvents
== NULL
)
1556 SetLastError(ERROR_INVALID_ACCESS
);
1560 *lpNumberOfEvents
= GetNumInputEventsRequest
->NumberOfEvents
;
1572 GetLargestConsoleWindowSize(HANDLE hConsoleOutput
)
1574 CONSOLE_API_MESSAGE ApiMessage
;
1575 PCONSOLE_GETLARGESTWINDOWSIZE GetLargestWindowSizeRequest
= &ApiMessage
.Data
.GetLargestWindowSizeRequest
;
1577 GetLargestWindowSizeRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1578 GetLargestWindowSizeRequest
->OutputHandle
= hConsoleOutput
;
1579 GetLargestWindowSizeRequest
->Size
.X
= 0;
1580 GetLargestWindowSizeRequest
->Size
.Y
= 0;
1582 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1584 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetLargestWindowSize
),
1585 sizeof(*GetLargestWindowSizeRequest
));
1586 if (!NT_SUCCESS(ApiMessage
.Status
))
1588 BaseSetLastNTError(ApiMessage
.Status
);
1591 DPRINT("GetLargestConsoleWindowSize, X = %d, Y = %d\n", GetLargestWindowSizeRequest
->Size
.X
, GetLargestWindowSizeRequest
->Size
.Y
);
1592 return GetLargestWindowSizeRequest
->Size
;
1601 GetConsoleCursorInfo(HANDLE hConsoleOutput
,
1602 PCONSOLE_CURSOR_INFO lpConsoleCursorInfo
)
1604 CONSOLE_API_MESSAGE ApiMessage
;
1605 PCONSOLE_GETSETCURSORINFO CursorInfoRequest
= &ApiMessage
.Data
.CursorInfoRequest
;
1607 if (!lpConsoleCursorInfo
)
1609 if (!hConsoleOutput
)
1610 SetLastError(ERROR_INVALID_HANDLE
);
1612 SetLastError(ERROR_INVALID_ACCESS
);
1617 CursorInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1618 CursorInfoRequest
->OutputHandle
= hConsoleOutput
;
1620 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1622 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetCursorInfo
),
1623 sizeof(*CursorInfoRequest
));
1624 if (!NT_SUCCESS(ApiMessage
.Status
))
1626 BaseSetLastNTError(ApiMessage
.Status
);
1630 *lpConsoleCursorInfo
= CursorInfoRequest
->Info
;
1641 SetConsoleCursorInfo(HANDLE hConsoleOutput
,
1642 CONST CONSOLE_CURSOR_INFO
*lpConsoleCursorInfo
)
1644 CONSOLE_API_MESSAGE ApiMessage
;
1645 PCONSOLE_GETSETCURSORINFO CursorInfoRequest
= &ApiMessage
.Data
.CursorInfoRequest
;
1647 CursorInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1648 CursorInfoRequest
->OutputHandle
= hConsoleOutput
;
1649 CursorInfoRequest
->Info
= *lpConsoleCursorInfo
;
1651 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1653 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetCursorInfo
),
1654 sizeof(*CursorInfoRequest
));
1655 if (!NT_SUCCESS(ApiMessage
.Status
))
1657 BaseSetLastNTError(ApiMessage
.Status
);
1670 GetNumberOfConsoleMouseButtons(LPDWORD lpNumberOfMouseButtons
)
1672 CONSOLE_API_MESSAGE ApiMessage
;
1673 PCONSOLE_GETMOUSEINFO GetMouseInfoRequest
= &ApiMessage
.Data
.GetMouseInfoRequest
;
1675 GetMouseInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1677 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1679 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetMouseInfo
),
1680 sizeof(*GetMouseInfoRequest
));
1681 if (!NT_SUCCESS(ApiMessage
.Status
))
1683 BaseSetLastNTError(ApiMessage
.Status
);
1687 *lpNumberOfMouseButtons
= GetMouseInfoRequest
->NumButtons
;
1698 SetConsoleActiveScreenBuffer(HANDLE hConsoleOutput
)
1700 CONSOLE_API_MESSAGE ApiMessage
;
1701 PCONSOLE_SETACTIVESCREENBUFFER SetScreenBufferRequest
= &ApiMessage
.Data
.SetScreenBufferRequest
;
1703 SetScreenBufferRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1704 SetScreenBufferRequest
->OutputHandle
= hConsoleOutput
;
1706 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1708 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetActiveScreenBuffer
),
1709 sizeof(*SetScreenBufferRequest
));
1710 if (!NT_SUCCESS(ApiMessage
.Status
))
1712 BaseSetLastNTError(ApiMessage
.Status
);
1726 FlushConsoleInputBuffer(HANDLE hConsoleInput
)
1728 CONSOLE_API_MESSAGE ApiMessage
;
1729 PCONSOLE_FLUSHINPUTBUFFER FlushInputBufferRequest
= &ApiMessage
.Data
.FlushInputBufferRequest
;
1731 FlushInputBufferRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1732 FlushInputBufferRequest
->InputHandle
= hConsoleInput
;
1734 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1736 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepFlushInputBuffer
),
1737 sizeof(*FlushInputBufferRequest
));
1738 if (!NT_SUCCESS(ApiMessage
.Status
))
1740 BaseSetLastNTError(ApiMessage
.Status
);
1754 SetConsoleScreenBufferSize(HANDLE hConsoleOutput
,
1757 CONSOLE_API_MESSAGE ApiMessage
;
1758 PCONSOLE_SETSCREENBUFFERSIZE SetScreenBufferSizeRequest
= &ApiMessage
.Data
.SetScreenBufferSizeRequest
;
1760 SetScreenBufferSizeRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1761 SetScreenBufferSizeRequest
->OutputHandle
= hConsoleOutput
;
1762 SetScreenBufferSizeRequest
->Size
= dwSize
;
1764 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1766 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetScreenBufferSize
),
1767 sizeof(*SetScreenBufferSizeRequest
));
1768 if (!NT_SUCCESS(ApiMessage
.Status
))
1770 BaseSetLastNTError(ApiMessage
.Status
);
1780 IntScrollConsoleScreenBuffer(HANDLE hConsoleOutput
,
1781 CONST SMALL_RECT
* lpScrollRectangle
,
1782 CONST SMALL_RECT
* lpClipRectangle
,
1783 COORD dwDestinationOrigin
,
1784 CONST CHAR_INFO
* lpFill
,
1787 CONSOLE_API_MESSAGE ApiMessage
;
1788 PCONSOLE_SCROLLSCREENBUFFER ScrollScreenBufferRequest
= &ApiMessage
.Data
.ScrollScreenBufferRequest
;
1790 ScrollScreenBufferRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1791 ScrollScreenBufferRequest
->OutputHandle
= hConsoleOutput
;
1792 ScrollScreenBufferRequest
->ScrollRectangle
= *lpScrollRectangle
;
1794 if (lpClipRectangle
!= NULL
)
1796 ScrollScreenBufferRequest
->UseClipRectangle
= TRUE
;
1797 ScrollScreenBufferRequest
->ClipRectangle
= *lpClipRectangle
;
1801 ScrollScreenBufferRequest
->UseClipRectangle
= FALSE
;
1804 ScrollScreenBufferRequest
->DestinationOrigin
= dwDestinationOrigin
;
1805 ScrollScreenBufferRequest
->Fill
= *lpFill
;
1806 ScrollScreenBufferRequest
->Unicode
= bUnicode
;
1808 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1810 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepScrollScreenBuffer
),
1811 sizeof(*ScrollScreenBufferRequest
));
1812 if (!NT_SUCCESS(ApiMessage
.Status
))
1814 BaseSetLastNTError(ApiMessage
.Status
);
1828 ScrollConsoleScreenBufferA(HANDLE hConsoleOutput
,
1829 CONST SMALL_RECT
* lpScrollRectangle
,
1830 CONST SMALL_RECT
* lpClipRectangle
,
1831 COORD dwDestinationOrigin
,
1832 CONST CHAR_INFO
* lpFill
)
1834 return IntScrollConsoleScreenBuffer(hConsoleOutput
,
1837 dwDestinationOrigin
,
1849 ScrollConsoleScreenBufferW(HANDLE hConsoleOutput
,
1850 CONST SMALL_RECT
*lpScrollRectangle
,
1851 CONST SMALL_RECT
*lpClipRectangle
,
1852 COORD dwDestinationOrigin
,
1853 CONST CHAR_INFO
*lpFill
)
1855 return IntScrollConsoleScreenBuffer(hConsoleOutput
,
1858 dwDestinationOrigin
,
1869 SetConsoleWindowInfo(HANDLE hConsoleOutput
,
1871 CONST SMALL_RECT
*lpConsoleWindow
)
1873 CONSOLE_API_MESSAGE ApiMessage
;
1874 PCONSOLE_SETWINDOWINFO SetWindowInfoRequest
= &ApiMessage
.Data
.SetWindowInfoRequest
;
1876 if (lpConsoleWindow
== NULL
)
1878 SetLastError(ERROR_INVALID_PARAMETER
);
1882 SetWindowInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1883 SetWindowInfoRequest
->OutputHandle
= hConsoleOutput
;
1884 SetWindowInfoRequest
->Absolute
= bAbsolute
;
1885 SetWindowInfoRequest
->WindowRect
= *lpConsoleWindow
;
1887 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1889 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetWindowInfo
),
1890 sizeof(*SetWindowInfoRequest
));
1891 if (!NT_SUCCESS(ApiMessage
.Status
))
1893 BaseSetLastNTError(ApiMessage
.Status
);
1907 SetConsoleTextAttribute(HANDLE hConsoleOutput
,
1910 CONSOLE_API_MESSAGE ApiMessage
;
1911 PCONSOLE_SETTEXTATTRIB SetTextAttribRequest
= &ApiMessage
.Data
.SetTextAttribRequest
;
1913 SetTextAttribRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
1914 SetTextAttribRequest
->OutputHandle
= hConsoleOutput
;
1915 SetTextAttribRequest
->Attributes
= wAttributes
;
1917 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
1919 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetTextAttribute
),
1920 sizeof(*SetTextAttribRequest
));
1921 if (!NT_SUCCESS(ApiMessage
.Status
))
1923 BaseSetLastNTError(ApiMessage
.Status
);
1933 AddConsoleCtrlHandler(PHANDLER_ROUTINE HandlerRoutine
)
1935 PHANDLER_ROUTINE
* NewCtrlHandlers
= NULL
;
1937 if (HandlerRoutine
== NULL
)
1939 NtCurrentPeb()->ProcessParameters
->ConsoleFlags
= TRUE
;
1943 if (NrCtrlHandlers
== NrAllocatedHandlers
)
1945 NewCtrlHandlers
= RtlAllocateHeap(RtlGetProcessHeap(),
1947 (NrCtrlHandlers
+ 4) * sizeof(PHANDLER_ROUTINE
));
1948 if (NewCtrlHandlers
== NULL
)
1950 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
1954 memmove(NewCtrlHandlers
, CtrlHandlers
, sizeof(PHANDLER_ROUTINE
) * NrCtrlHandlers
);
1956 if (NrAllocatedHandlers
> 1) RtlFreeHeap(RtlGetProcessHeap(), 0, CtrlHandlers
);
1958 CtrlHandlers
= NewCtrlHandlers
;
1959 NrAllocatedHandlers
+= 4;
1962 ASSERT(NrCtrlHandlers
< NrAllocatedHandlers
);
1964 CtrlHandlers
[NrCtrlHandlers
++] = HandlerRoutine
;
1971 RemoveConsoleCtrlHandler(PHANDLER_ROUTINE HandlerRoutine
)
1975 if (HandlerRoutine
== NULL
)
1977 NtCurrentPeb()->ProcessParameters
->ConsoleFlags
= FALSE
;
1981 for (i
= 0; i
< NrCtrlHandlers
; i
++)
1983 if (CtrlHandlers
[i
] == HandlerRoutine
)
1985 if (i
< (NrCtrlHandlers
- 1))
1987 memmove(&CtrlHandlers
[i
],
1989 (NrCtrlHandlers
- i
+ 1) * sizeof(PHANDLER_ROUTINE
));
1997 SetLastError(ERROR_INVALID_PARAMETER
);
2008 SetConsoleCtrlHandler(PHANDLER_ROUTINE HandlerRoutine
,
2013 RtlEnterCriticalSection(&BaseDllDirectoryLock
);
2016 Ret
= AddConsoleCtrlHandler(HandlerRoutine
);
2020 Ret
= RemoveConsoleCtrlHandler(HandlerRoutine
);
2023 RtlLeaveCriticalSection(&BaseDllDirectoryLock
);
2034 GenerateConsoleCtrlEvent(DWORD dwCtrlEvent
,
2035 DWORD dwProcessGroupId
)
2037 CONSOLE_API_MESSAGE ApiMessage
;
2038 PCONSOLE_GENERATECTRLEVENT GenerateCtrlEventRequest
= &ApiMessage
.Data
.GenerateCtrlEventRequest
;
2040 if (dwCtrlEvent
!= CTRL_C_EVENT
&& dwCtrlEvent
!= CTRL_BREAK_EVENT
)
2042 SetLastError(ERROR_INVALID_PARAMETER
);
2046 GenerateCtrlEventRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2047 GenerateCtrlEventRequest
->CtrlEvent
= dwCtrlEvent
;
2048 GenerateCtrlEventRequest
->ProcessGroupId
= dwProcessGroupId
;
2050 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2052 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGenerateCtrlEvent
),
2053 sizeof(*GenerateCtrlEventRequest
));
2054 if (!NT_SUCCESS(ApiMessage
.Status
))
2056 BaseSetLastNTError(ApiMessage
.Status
);
2065 IntGetConsoleTitle(LPVOID lpConsoleTitle
, DWORD dwNumChars
, BOOLEAN bUnicode
)
2067 CONSOLE_API_MESSAGE ApiMessage
;
2068 PCONSOLE_GETSETCONSOLETITLE TitleRequest
= &ApiMessage
.Data
.TitleRequest
;
2069 PCSR_CAPTURE_BUFFER CaptureBuffer
;
2071 if (dwNumChars
== 0) return 0;
2073 TitleRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2074 TitleRequest
->Length
= dwNumChars
* (bUnicode
? sizeof(WCHAR
) : sizeof(CHAR
));
2075 TitleRequest
->Unicode
= bUnicode
;
2077 CaptureBuffer
= CsrAllocateCaptureBuffer(1, TitleRequest
->Length
);
2078 if (CaptureBuffer
== NULL
)
2080 DPRINT1("CsrAllocateCaptureBuffer failed!\n");
2081 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
2085 CsrAllocateMessagePointer(CaptureBuffer
,
2086 TitleRequest
->Length
,
2087 (PVOID
*)&TitleRequest
->Title
);
2089 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2091 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetTitle
),
2092 sizeof(*TitleRequest
));
2093 if (!NT_SUCCESS(ApiMessage
.Status
))
2095 CsrFreeCaptureBuffer(CaptureBuffer
);
2096 BaseSetLastNTError(ApiMessage
.Status
);
2100 dwNumChars
= TitleRequest
->Length
/ (bUnicode
? sizeof(WCHAR
) : sizeof(CHAR
));
2104 memcpy(lpConsoleTitle
, TitleRequest
->Title
, TitleRequest
->Length
);
2107 ((LPWSTR
)lpConsoleTitle
)[dwNumChars
] = UNICODE_NULL
;
2109 ((LPSTR
)lpConsoleTitle
)[dwNumChars
] = ANSI_NULL
;
2112 CsrFreeCaptureBuffer(CaptureBuffer
);
2124 GetConsoleTitleW(LPWSTR lpConsoleTitle
,
2127 return IntGetConsoleTitle(lpConsoleTitle
, nSize
, TRUE
);
2137 GetConsoleTitleA(LPSTR lpConsoleTitle
,
2140 return IntGetConsoleTitle(lpConsoleTitle
, nSize
, FALSE
);
2145 IntSetConsoleTitle(CONST VOID
*lpConsoleTitle
, BOOLEAN bUnicode
)
2147 CONSOLE_API_MESSAGE ApiMessage
;
2148 PCONSOLE_GETSETCONSOLETITLE TitleRequest
= &ApiMessage
.Data
.TitleRequest
;
2149 PCSR_CAPTURE_BUFFER CaptureBuffer
;
2151 ULONG NumChars
= (ULONG
)(lpConsoleTitle
? (bUnicode
? wcslen(lpConsoleTitle
) : strlen(lpConsoleTitle
)) : 0);
2153 TitleRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2154 TitleRequest
->Length
= NumChars
* (bUnicode
? sizeof(WCHAR
) : sizeof(CHAR
));
2155 TitleRequest
->Unicode
= bUnicode
;
2157 CaptureBuffer
= CsrAllocateCaptureBuffer(1, TitleRequest
->Length
);
2158 if (CaptureBuffer
== NULL
)
2160 DPRINT1("CsrAllocateCaptureBuffer failed!\n");
2161 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
2165 CsrCaptureMessageBuffer(CaptureBuffer
,
2166 (PVOID
)lpConsoleTitle
,
2167 TitleRequest
->Length
,
2168 (PVOID
*)&TitleRequest
->Title
);
2170 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2172 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetTitle
),
2173 sizeof(*TitleRequest
));
2175 CsrFreeCaptureBuffer(CaptureBuffer
);
2177 if (!NT_SUCCESS(ApiMessage
.Status
))
2179 BaseSetLastNTError(ApiMessage
.Status
);
2192 SetConsoleTitleW(LPCWSTR lpConsoleTitle
)
2194 return IntSetConsoleTitle(lpConsoleTitle
, TRUE
);
2204 SetConsoleTitleA(LPCSTR lpConsoleTitle
)
2206 return IntSetConsoleTitle(lpConsoleTitle
, FALSE
);
2215 CreateConsoleScreenBuffer(DWORD dwDesiredAccess
,
2217 CONST SECURITY_ATTRIBUTES
*lpSecurityAttributes
,
2219 LPVOID lpScreenBufferData
)
2221 CONSOLE_API_MESSAGE ApiMessage
;
2222 PCONSOLE_CREATESCREENBUFFER CreateScreenBufferRequest
= &ApiMessage
.Data
.CreateScreenBufferRequest
;
2223 PCSR_CAPTURE_BUFFER CaptureBuffer
= NULL
;
2224 PCONSOLE_GRAPHICS_BUFFER_INFO GraphicsBufferInfo
= lpScreenBufferData
;
2226 if ( (dwDesiredAccess
& ~(GENERIC_READ
| GENERIC_WRITE
)) ||
2227 (dwShareMode
& ~(FILE_SHARE_READ
| FILE_SHARE_WRITE
)) ||
2228 (dwFlags
!= CONSOLE_TEXTMODE_BUFFER
&& dwFlags
!= CONSOLE_GRAPHICS_BUFFER
) )
2230 SetLastError(ERROR_INVALID_PARAMETER
);
2231 return INVALID_HANDLE_VALUE
;
2234 CreateScreenBufferRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2235 CreateScreenBufferRequest
->DesiredAccess
= dwDesiredAccess
;
2236 CreateScreenBufferRequest
->InheritHandle
=
2237 (lpSecurityAttributes
? lpSecurityAttributes
->bInheritHandle
: FALSE
);
2238 CreateScreenBufferRequest
->ShareMode
= dwShareMode
;
2239 CreateScreenBufferRequest
->ScreenBufferType
= dwFlags
;
2241 if (dwFlags
== CONSOLE_GRAPHICS_BUFFER
)
2243 if (CreateScreenBufferRequest
->InheritHandle
|| GraphicsBufferInfo
== NULL
)
2245 SetLastError(ERROR_INVALID_PARAMETER
);
2246 return INVALID_HANDLE_VALUE
;
2249 CreateScreenBufferRequest
->GraphicsBufferInfo
= *GraphicsBufferInfo
;
2251 CaptureBuffer
= CsrAllocateCaptureBuffer(1, GraphicsBufferInfo
->dwBitMapInfoLength
);
2252 if (CaptureBuffer
== NULL
)
2254 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
2255 return INVALID_HANDLE_VALUE
;
2258 CsrCaptureMessageBuffer(CaptureBuffer
,
2259 (PVOID
)GraphicsBufferInfo
->lpBitMapInfo
,
2260 GraphicsBufferInfo
->dwBitMapInfoLength
,
2261 (PVOID
*)&CreateScreenBufferRequest
->GraphicsBufferInfo
.lpBitMapInfo
);
2264 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2266 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepCreateScreenBuffer
),
2267 sizeof(*CreateScreenBufferRequest
));
2269 if (CaptureBuffer
) CsrFreeCaptureBuffer(CaptureBuffer
);
2271 if (!NT_SUCCESS(ApiMessage
.Status
))
2273 BaseSetLastNTError(ApiMessage
.Status
);
2274 return INVALID_HANDLE_VALUE
;
2277 if (dwFlags
== CONSOLE_GRAPHICS_BUFFER
&& GraphicsBufferInfo
)
2279 GraphicsBufferInfo
->hMutex
= CreateScreenBufferRequest
->hMutex
; // CreateScreenBufferRequest->GraphicsBufferInfo.hMutex ;
2280 GraphicsBufferInfo
->lpBitMap
= CreateScreenBufferRequest
->lpBitMap
; // CreateScreenBufferRequest->GraphicsBufferInfo.lpBitMap;
2283 return CreateScreenBufferRequest
->OutputHandle
;
2295 CONSOLE_API_MESSAGE ApiMessage
;
2296 PCONSOLE_GETINPUTOUTPUTCP GetConsoleCPRequest
= &ApiMessage
.Data
.GetConsoleCPRequest
;
2298 /* Get the Input Code Page */
2299 GetConsoleCPRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2300 GetConsoleCPRequest
->OutputCP
= FALSE
;
2302 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2304 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetCP
),
2305 sizeof(*GetConsoleCPRequest
));
2306 if (!NT_SUCCESS(ApiMessage
.Status
))
2308 BaseSetLastNTError(ApiMessage
.Status
);
2312 return GetConsoleCPRequest
->CodePage
;
2322 SetConsoleCP(UINT wCodePageID
)
2324 CONSOLE_API_MESSAGE ApiMessage
;
2325 PCONSOLE_SETINPUTOUTPUTCP SetConsoleCPRequest
= &ApiMessage
.Data
.SetConsoleCPRequest
;
2327 /* Set the Input Code Page */
2328 SetConsoleCPRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2329 SetConsoleCPRequest
->CodePage
= wCodePageID
;
2330 SetConsoleCPRequest
->OutputCP
= FALSE
;
2331 /* SetConsoleCPRequest->EventHandle; */
2333 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2335 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetCP
),
2336 sizeof(*SetConsoleCPRequest
));
2337 if (!NT_SUCCESS(ApiMessage
.Status
))
2339 BaseSetLastNTError(ApiMessage
.Status
);
2353 GetConsoleOutputCP(VOID
)
2355 CONSOLE_API_MESSAGE ApiMessage
;
2356 PCONSOLE_GETINPUTOUTPUTCP GetConsoleCPRequest
= &ApiMessage
.Data
.GetConsoleCPRequest
;
2358 /* Get the Output Code Page */
2359 GetConsoleCPRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2360 GetConsoleCPRequest
->OutputCP
= TRUE
;
2362 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2364 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetCP
),
2365 sizeof(*GetConsoleCPRequest
));
2366 if (!NT_SUCCESS(ApiMessage
.Status
))
2368 BaseSetLastNTError(ApiMessage
.Status
);
2372 return GetConsoleCPRequest
->CodePage
;
2382 SetConsoleOutputCP(UINT wCodePageID
)
2384 CONSOLE_API_MESSAGE ApiMessage
;
2385 PCONSOLE_SETINPUTOUTPUTCP SetConsoleCPRequest
= &ApiMessage
.Data
.SetConsoleCPRequest
;
2387 /* Set the Output Code Page */
2388 SetConsoleCPRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2389 SetConsoleCPRequest
->CodePage
= wCodePageID
;
2390 SetConsoleCPRequest
->OutputCP
= TRUE
;
2391 /* SetConsoleCPRequest->EventHandle; */
2393 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2395 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetCP
),
2396 sizeof(*SetConsoleCPRequest
));
2397 if (!NT_SUCCESS(ApiMessage
.Status
))
2399 BaseSetLastNTError(ApiMessage
.Status
);
2412 GetConsoleProcessList(LPDWORD lpdwProcessList
,
2413 DWORD dwProcessCount
)
2415 CONSOLE_API_MESSAGE ApiMessage
;
2416 PCONSOLE_GETPROCESSLIST GetProcessListRequest
= &ApiMessage
.Data
.GetProcessListRequest
;
2417 PCSR_CAPTURE_BUFFER CaptureBuffer
;
2418 ULONG nProcesses
= 0;
2420 if (lpdwProcessList
== NULL
|| dwProcessCount
== 0)
2422 SetLastError(ERROR_INVALID_PARAMETER
);
2426 CaptureBuffer
= CsrAllocateCaptureBuffer(1, dwProcessCount
* sizeof(DWORD
));
2427 if (CaptureBuffer
== NULL
)
2429 DPRINT1("CsrAllocateCaptureBuffer failed!\n");
2430 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
2434 GetProcessListRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2435 GetProcessListRequest
->ProcessCount
= dwProcessCount
;
2437 CsrAllocateMessagePointer(CaptureBuffer
,
2438 dwProcessCount
* sizeof(DWORD
),
2439 (PVOID
*)&GetProcessListRequest
->ProcessIdsList
);
2441 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2443 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetProcessList
),
2444 sizeof(*GetProcessListRequest
));
2445 if (!NT_SUCCESS(ApiMessage
.Status
))
2447 BaseSetLastNTError(ApiMessage
.Status
);
2451 nProcesses
= GetProcessListRequest
->ProcessCount
;
2452 if (dwProcessCount
>= nProcesses
)
2454 memcpy(lpdwProcessList
, GetProcessListRequest
->ProcessIdsList
, nProcesses
* sizeof(DWORD
));
2458 CsrFreeCaptureBuffer(CaptureBuffer
);
2468 GetConsoleSelectionInfo(PCONSOLE_SELECTION_INFO lpConsoleSelectionInfo
)
2470 CONSOLE_API_MESSAGE ApiMessage
;
2471 PCONSOLE_GETSELECTIONINFO GetSelectionInfoRequest
= &ApiMessage
.Data
.GetSelectionInfoRequest
;
2473 if (lpConsoleSelectionInfo
== NULL
)
2475 SetLastError(ERROR_INVALID_PARAMETER
);
2479 GetSelectionInfoRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2481 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2483 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetSelectionInfo
),
2484 sizeof(*GetSelectionInfoRequest
));
2485 if (!NT_SUCCESS(ApiMessage
.Status
))
2487 BaseSetLastNTError(ApiMessage
.Status
);
2491 *lpConsoleSelectionInfo
= GetSelectionInfoRequest
->Info
;
2499 * @note Strongly inspired by AllocConsole.
2502 IntAttachConsole(DWORD ProcessId
,
2503 LPTHREAD_START_ROUTINE CtrlRoutine
,
2504 LPTHREAD_START_ROUTINE PropRoutine
,
2505 PCONSOLE_START_INFO ConsoleStartInfo
)
2507 BOOL Success
= TRUE
;
2508 #ifdef USE_CONSOLE_INIT_HANDLES
2512 CONSOLE_API_MESSAGE ApiMessage
;
2513 PCONSOLE_ATTACHCONSOLE AttachConsoleRequest
= &ApiMessage
.Data
.AttachConsoleRequest
;
2514 PCSR_CAPTURE_BUFFER CaptureBuffer
;
2516 AttachConsoleRequest
->ProcessId
= ProcessId
;
2517 AttachConsoleRequest
->CtrlRoutine
= CtrlRoutine
;
2518 AttachConsoleRequest
->PropRoutine
= PropRoutine
;
2520 CaptureBuffer
= CsrAllocateCaptureBuffer(1, sizeof(CONSOLE_START_INFO
));
2521 if (CaptureBuffer
== NULL
)
2523 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
2528 CsrCaptureMessageBuffer(CaptureBuffer
,
2530 sizeof(CONSOLE_START_INFO
),
2531 (PVOID
*)&AttachConsoleRequest
->ConsoleStartInfo
);
2533 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2535 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepAttach
),
2536 sizeof(*AttachConsoleRequest
));
2537 if (!NT_SUCCESS(ApiMessage
.Status
))
2539 BaseSetLastNTError(ApiMessage
.Status
);
2544 #ifdef USE_CONSOLE_INIT_HANDLES
2545 // Is AttachConsoleRequest->ConsoleStartInfo->Events aligned on handle boundary ????
2546 Status
= NtWaitForMultipleObjects(2, AttachConsoleRequest
->ConsoleStartInfo
->Events
,
2547 WaitAny
, FALSE
, NULL
);
2548 if (!NT_SUCCESS(Status
))
2550 BaseSetLastNTError(Status
);
2555 NtClose(AttachConsoleRequest
->ConsoleStartInfo
->Events
[0]);
2556 NtClose(AttachConsoleRequest
->ConsoleStartInfo
->Events
[1]);
2557 if (Status
!= STATUS_SUCCESS
)
2559 NtCurrentPeb()->ProcessParameters
->ConsoleHandle
= NULL
;
2565 RtlCopyMemory(ConsoleStartInfo
,
2566 AttachConsoleRequest
->ConsoleStartInfo
,
2567 sizeof(CONSOLE_START_INFO
));
2572 if (CaptureBuffer
) CsrFreeCaptureBuffer(CaptureBuffer
);
2578 AttachConsole(DWORD dwProcessId
)
2581 CONSOLE_START_INFO ConsoleStartInfo
;
2586 RtlEnterCriticalSection(&ConsoleLock
);
2588 if (NtCurrentPeb()->ProcessParameters
->ConsoleHandle
)
2590 DPRINT1("AttachConsole: Attaching a console to a process already having one\n");
2591 SetLastError(ERROR_ACCESS_DENIED
);
2596 /* Set up the console properties */
2597 SetUpConsoleInfo(FALSE
,
2604 Success
= IntAttachConsole(dwProcessId
,
2605 ConsoleControlDispatcher
,
2610 /* Set up the handles */
2611 SetUpHandles(&ConsoleStartInfo
);
2612 InputWaitHandle
= ConsoleStartInfo
.InputWaitHandle
;
2614 /* Initialize Console Ctrl Handling */
2615 InitializeCtrlHandling();
2617 /* Sets the current console locale for this thread */
2622 RtlLeaveCriticalSection(&ConsoleLock
);
2633 GetConsoleWindow(VOID
)
2635 CONSOLE_API_MESSAGE ApiMessage
;
2636 PCONSOLE_GETWINDOW GetWindowRequest
= &ApiMessage
.Data
.GetWindowRequest
;
2638 GetWindowRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2640 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2642 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetConsoleWindow
),
2643 sizeof(*GetWindowRequest
));
2644 if (!NT_SUCCESS(ApiMessage
.Status
))
2646 BaseSetLastNTError(ApiMessage
.Status
);
2650 return GetWindowRequest
->WindowHandle
;
2660 SetConsoleIcon(HICON hIcon
)
2662 CONSOLE_API_MESSAGE ApiMessage
;
2663 PCONSOLE_SETICON SetIconRequest
= &ApiMessage
.Data
.SetIconRequest
;
2665 SetIconRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2666 SetIconRequest
->IconHandle
= hIcon
;
2668 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2670 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepSetIcon
),
2671 sizeof(*SetIconRequest
));
2672 if (!NT_SUCCESS(ApiMessage
.Status
))
2674 BaseSetLastNTError(ApiMessage
.Status
);
2682 /******************************************************************************
2683 * \name SetConsoleInputExeNameW
2684 * \brief Sets the console input file name from a unicode string.
2685 * \param lpExeName Pointer to a unicode string with the name.
2686 * \return TRUE if successful, FALSE if unsuccsedful.
2687 * \remarks If lpExeName is 0 or the string length is 0 or greater than 255,
2688 * the function fails and sets last error to ERROR_INVALID_PARAMETER.
2693 SetConsoleInputExeNameW(IN LPWSTR lpExeName
)
2697 ExeLength
= lstrlenW(lpExeName
);
2698 if ((ExeLength
== 0) || (ExeLength
>= EXENAME_LENGTH
))
2700 /* Fail if string is empty or too long */
2701 SetLastError(ERROR_INVALID_PARAMETER
);
2705 RtlEnterCriticalSection(&ExeNameLock
);
2708 /* Set the input EXE name, not NULL terminated */
2709 RtlCopyMemory(ExeNameBuffer
, lpExeName
, ExeLength
* sizeof(WCHAR
));
2710 ExeNameLength
= (USHORT
)ExeLength
;
2714 RtlLeaveCriticalSection(&ExeNameLock
);
2722 /******************************************************************************
2723 * \name SetConsoleInputExeNameA
2724 * \brief Sets the console input file name from an ansi string.
2725 * \param lpExeName Pointer to an ansi string with the name.
2726 * \return TRUE if successful, FALSE if unsuccsedful.
2727 * \remarks If lpExeName is 0 or the string length is 0 or greater than 255,
2728 * the function fails and sets last error to ERROR_INVALID_PARAMETER.
2733 SetConsoleInputExeNameA(IN LPSTR lpExeName
)
2736 #ifdef USE_TEB_STATIC_USTR
2737 PUNICODE_STRING ExeNameU
;
2739 UNICODE_STRING ExeNameU
;
2741 ANSI_STRING ExeNameA
;
2742 #ifndef USE_TEB_STATIC_USTR
2743 WCHAR Buffer
[EXENAME_LENGTH
];
2746 #ifdef USE_TEB_STATIC_USTR
2748 * Use the TEB static UNICODE string for storage. It is already
2749 * initialized at process creation time by the Memory Manager.
2751 ExeNameU
= &NtCurrentTeb()->StaticUnicodeString
;
2754 /* Initialize string for conversion */
2755 RtlInitAnsiString(&ExeNameA
, lpExeName
);
2758 if ((ExeNameA
.Length
== 0) || (ExeNameA
.Length
>= EXENAME_LENGTH
))
2760 /* Fail if string is empty or too long */
2761 SetLastError(ERROR_INVALID_PARAMETER
);
2765 #ifndef USE_TEB_STATIC_USTR
2766 ExeNameU
.Length
= 0;
2767 ExeNameU
.MaximumLength
= (USHORT
)sizeof(Buffer
);
2768 ExeNameU
.Buffer
= Buffer
;
2771 #ifdef USE_TEB_STATIC_USTR
2772 Status
= RtlAnsiStringToUnicodeString(ExeNameU
, &ExeNameA
, FALSE
);
2774 Status
= RtlAnsiStringToUnicodeString(&ExeNameU
, &ExeNameA
, FALSE
);
2776 if (!NT_SUCCESS(Status
))
2778 /* Fail if string is empty or too long */
2779 if (Status
== STATUS_BUFFER_OVERFLOW
)
2780 SetLastError(ERROR_FILENAME_EXCED_RANGE
);
2782 SetLastError(ERROR_INVALID_PARAMETER
);
2787 #ifdef USE_TEB_STATIC_USTR
2788 return SetConsoleInputExeNameW(ExeNameU
->Buffer
);
2790 return SetConsoleInputExeNameW(ExeNameU
.Buffer
);
2795 /******************************************************************************
2796 * \name GetConsoleInputExeNameW
2797 * \brief Retrieves the console input file name as unicode string.
2798 * \param nBufferLength Length of the buffer in WCHARs.
2799 * Specify 0 to receive the needed buffer length.
2800 * \param lpBuffer Pointer to a buffer that receives the string.
2801 * \return Needed buffer size if \p nBufferLength is 0.
2802 * Otherwise 1 if successful, 2 if buffer is too small.
2803 * \remarks Sets last error value to ERROR_BUFFER_OVERFLOW if the buffer
2804 * is not big enough.
2809 GetConsoleInputExeNameW(IN DWORD nBufferLength
,
2810 OUT LPWSTR lpExeName
)
2812 if (nBufferLength
<= ExeNameLength
)
2814 /* Buffer is not large enough! Return the correct size. */
2815 SetLastError(ERROR_BUFFER_OVERFLOW
);
2816 return ExeNameLength
+ 1;
2819 RtlEnterCriticalSection(&ExeNameLock
);
2822 /* Copy the input EXE name and NULL-terminate it */
2823 RtlCopyMemory(lpExeName
, ExeNameBuffer
, ExeNameLength
* sizeof(WCHAR
));
2824 lpExeName
[ExeNameLength
] = UNICODE_NULL
;
2828 RtlLeaveCriticalSection(&ExeNameLock
);
2836 /******************************************************************************
2837 * \name GetConsoleInputExeNameA
2838 * \brief Retrieves the console input file name as ansi string.
2839 * \param nBufferLength Length of the buffer in CHARs.
2840 * \param lpBuffer Pointer to a buffer that receives the string.
2841 * \return 1 if successful, 2 if buffer is too small.
2842 * \remarks Sets last error value to ERROR_BUFFER_OVERFLOW if the buffer
2843 * is not big enough. The buffer receives as much characters as fit.
2848 GetConsoleInputExeNameA(IN DWORD nBufferLength
,
2849 OUT LPSTR lpExeName
)
2853 UNICODE_STRING BufferU
;
2854 ANSI_STRING BufferA
;
2855 WCHAR Buffer
[EXENAME_LENGTH
];
2857 /* Get the UNICODE name */
2858 ExeLength
= GetConsoleInputExeNameW(EXENAME_LENGTH
, Buffer
);
2860 if ((ExeLength
== 0) || (ExeLength
>= EXENAME_LENGTH
))
2863 /* Initialize the strings for conversion */
2864 RtlInitUnicodeString(&BufferU
, Buffer
);
2866 BufferA
.MaximumLength
= (USHORT
)nBufferLength
;
2867 BufferA
.Buffer
= lpExeName
;
2869 /* Convert UNICODE name to ANSI, copying as much chars as it can fit */
2870 Status
= RtlUnicodeStringToAnsiString(&BufferA
, &BufferU
, FALSE
);
2871 if (!NT_SUCCESS(Status
))
2873 if (Status
== STATUS_BUFFER_OVERFLOW
)
2875 SetLastError(ERROR_BUFFER_OVERFLOW
);
2876 return ExeLength
+ 1;
2878 SetLastError(ERROR_INVALID_PARAMETER
);
2886 GetConsoleCharType(HANDLE hConsole
, COORD Coord
, PDWORD Type
)
2895 GetConsoleCursorMode(HANDLE hConsole
, PBOOL pUnknown1
, PBOOL pUnknown2
)
2904 SetConsoleCursorMode(HANDLE hConsole
, BOOL Unknown1
, BOOL Unknown2
)
2913 GetConsoleNlsMode(HANDLE hConsole
, LPDWORD lpMode
)
2922 SetConsoleNlsMode(HANDLE hConsole
, DWORD dwMode
)
2931 SetConsoleLocalEUDC(DWORD Unknown1
, DWORD Unknown2
, DWORD Unknown3
, DWORD Unknown4
)
2940 RegisterConsoleIME(HWND hWnd
, LPDWORD ThreadId
)
2949 RegisterConsoleOS2(BOOL bUnknown
)
2958 SetConsoleOS2OemFormat(BOOL bUnknown
)
2967 UnregisterConsoleIME(VOID
)
2976 IntGetConsoleKeyboardLayoutName(OUT PVOID pszLayoutName
,
2979 CONSOLE_API_MESSAGE ApiMessage
;
2980 PCONSOLE_GETKBDLAYOUTNAME GetKbdLayoutNameRequest
= &ApiMessage
.Data
.GetKbdLayoutNameRequest
;
2982 /* Set up the data to send to the Console Server */
2983 GetKbdLayoutNameRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
2984 GetKbdLayoutNameRequest
->Ansi
= bAnsi
;
2986 /* Call the server */
2987 CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
2989 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepGetKeyboardLayoutName
),
2990 sizeof(*GetKbdLayoutNameRequest
));
2992 /* Check for success */
2993 if (!NT_SUCCESS(ApiMessage
.Status
))
2995 BaseSetLastNTError(ApiMessage
.Status
);
2999 /* Retrieve the results */
3002 /* Copy only KL_NAMELENGTH == 9 characters, ANSI or UNICODE */
3004 strncpy(pszLayoutName
, (PCHAR
)GetKbdLayoutNameRequest
->LayoutBuffer
, KL_NAMELENGTH
);
3006 wcsncpy(pszLayoutName
, (PWCHAR
)GetKbdLayoutNameRequest
->LayoutBuffer
, KL_NAMELENGTH
);
3008 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER
)
3010 SetLastError(ERROR_INVALID_ACCESS
);
3011 _SEH2_YIELD(return FALSE
);
3019 * @implemented (undocumented)
3024 GetConsoleKeyboardLayoutNameA(OUT LPSTR pszLayoutName
)
3026 return IntGetConsoleKeyboardLayoutName(pszLayoutName
, TRUE
);
3030 * @implemented (undocumented)
3035 GetConsoleKeyboardLayoutNameW(OUT LPWSTR pszLayoutName
)
3037 return IntGetConsoleKeyboardLayoutName(pszLayoutName
, FALSE
);
3045 SetLastConsoleEventActive(VOID
)
3047 CONSOLE_API_MESSAGE ApiMessage
;
3048 PCONSOLE_NOTIFYLASTCLOSE NotifyLastCloseRequest
= &ApiMessage
.Data
.NotifyLastCloseRequest
;
3050 /* Set the flag used by the console control dispatcher */
3051 LastCloseNotify
= TRUE
;
3053 /* Set up the input arguments */
3054 NotifyLastCloseRequest
->ConsoleHandle
= NtCurrentPeb()->ProcessParameters
->ConsoleHandle
;
3056 /* Call CSRSS; just return the NTSTATUS cast to DWORD */
3057 return CsrClientCallServer((PCSR_API_MESSAGE
)&ApiMessage
,
3059 CSR_CREATE_API_NUMBER(CONSRV_SERVERDLL_INDEX
, ConsolepNotifyLastClose
),
3060 sizeof(*NotifyLastCloseRequest
));