2 * reactos/subsys/csrss/win32csr/conio.c
4 * Console I/O functions
6 * ReactOS Operating System
9 /* INCLUDES ******************************************************************/
15 /* FUNCTIONS *****************************************************************/
18 ConioConsoleFromProcessData(PCSR_PROCESS ProcessData
, PCSRSS_CONSOLE
*Console
)
20 PCSRSS_CONSOLE ProcessConsole
;
22 RtlEnterCriticalSection(&ProcessData
->HandleTableLock
);
23 ProcessConsole
= ProcessData
->Console
;
28 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
29 return STATUS_INVALID_HANDLE
;
32 InterlockedIncrement(&ProcessConsole
->ReferenceCount
);
33 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
34 EnterCriticalSection(&(ProcessConsole
->Lock
));
35 *Console
= ProcessConsole
;
37 return STATUS_SUCCESS
;
41 ConioConsoleCtrlEventTimeout(DWORD Event
, PCSR_PROCESS ProcessData
, DWORD Timeout
)
45 DPRINT("ConioConsoleCtrlEvent Parent ProcessId = %x\n", ProcessData
->ClientId
.UniqueProcess
);
47 if (ProcessData
->CtrlDispatcher
)
50 Thread
= CreateRemoteThread(ProcessData
->ProcessHandle
, NULL
, 0,
51 (LPTHREAD_START_ROUTINE
) ProcessData
->CtrlDispatcher
,
52 UlongToPtr(Event
), 0, NULL
);
55 DPRINT1("Failed thread creation (Error: 0x%x)\n", GetLastError());
58 WaitForSingleObject(Thread
, Timeout
);
64 ConioConsoleCtrlEvent(DWORD Event
, PCSR_PROCESS ProcessData
)
66 ConioConsoleCtrlEventTimeout(Event
, ProcessData
, 0);
69 static NTSTATUS WINAPI
70 CsrInitConsole(PCSRSS_CONSOLE Console
, int ShowCmd
)
73 SECURITY_ATTRIBUTES SecurityAttributes
;
74 PCSRSS_SCREEN_BUFFER NewBuffer
;
79 Console
->Title
.MaximumLength
= Console
->Title
.Length
= 0;
80 Console
->Title
.Buffer
= NULL
;
82 hInst
= GetModuleHandleW(L
"win32csr");
83 if (LoadStringW(hInst
,IDS_COMMAND_PROMPT
,Title
,sizeof(Title
)/sizeof(Title
[0])))
85 RtlCreateUnicodeString(&Console
->Title
, Title
);
89 RtlCreateUnicodeString(&Console
->Title
, L
"Command Prompt");
92 Console
->ReferenceCount
= 0;
93 Console
->LineBuffer
= NULL
;
94 Console
->Header
.Type
= CONIO_CONSOLE_MAGIC
;
95 Console
->Header
.Console
= Console
;
96 Console
->Mode
= ENABLE_LINE_INPUT
| ENABLE_ECHO_INPUT
| ENABLE_PROCESSED_INPUT
| ENABLE_MOUSE_INPUT
;
97 InitializeListHead(&Console
->BufferList
);
98 Console
->ActiveBuffer
= NULL
;
99 InitializeListHead(&Console
->InputEvents
);
100 InitializeListHead(&Console
->HistoryBuffers
);
101 Console
->CodePage
= GetOEMCP();
102 Console
->OutputCodePage
= GetOEMCP();
104 SecurityAttributes
.nLength
= sizeof(SECURITY_ATTRIBUTES
);
105 SecurityAttributes
.lpSecurityDescriptor
= NULL
;
106 SecurityAttributes
.bInheritHandle
= TRUE
;
108 Console
->ActiveEvent
= CreateEventW(&SecurityAttributes
, TRUE
, FALSE
, NULL
);
109 if (NULL
== Console
->ActiveEvent
)
111 RtlFreeUnicodeString(&Console
->Title
);
112 return STATUS_UNSUCCESSFUL
;
114 Console
->PrivateData
= NULL
;
115 InitializeCriticalSection(&Console
->Lock
);
117 GuiMode
= DtbgIsDesktopVisible();
119 /* allocate console screen buffer */
120 NewBuffer
= HeapAlloc(Win32CsrApiHeap
, HEAP_ZERO_MEMORY
, sizeof(CSRSS_SCREEN_BUFFER
));
121 if (NULL
== NewBuffer
)
123 RtlFreeUnicodeString(&Console
->Title
);
124 DeleteCriticalSection(&Console
->Lock
);
125 CloseHandle(Console
->ActiveEvent
);
126 return STATUS_INSUFFICIENT_RESOURCES
;
128 /* init screen buffer with defaults */
129 NewBuffer
->CursorInfo
.bVisible
= TRUE
;
130 NewBuffer
->CursorInfo
.dwSize
= CSR_DEFAULT_CURSOR_SIZE
;
131 /* make console active, and insert into console list */
132 Console
->ActiveBuffer
= (PCSRSS_SCREEN_BUFFER
) NewBuffer
;
135 * If we are not in GUI-mode, start the text-mode console. If we fail,
136 * try to start the GUI-mode console (win32k will automatically switch
137 * to graphical mode, therefore no additional code is needed).
141 DPRINT1("WIN32CSR: Opening text-mode console\n");
142 Status
= TuiInitConsole(Console
);
143 if (!NT_SUCCESS(Status
))
145 DPRINT1("Failed to open text-mode console, switching to gui-mode, Status = 0x%08lx\n", Status
);
151 * Try to open the GUI-mode console. Two cases are possible:
152 * - We are in GUI-mode, therefore GuiMode == TRUE, the previous test-case
153 * failed and we start GUI-mode console.
154 * - We are in text-mode, therefore GuiMode == FALSE, the previous test-case
155 * succeeded BUT we failed at starting text-mode console. Then GuiMode
156 * was switched to TRUE in order to try to open the console in GUI-mode.
160 DPRINT1("WIN32CSR: Opening GUI-mode console\n");
161 Status
= GuiInitConsole(Console
, ShowCmd
);
162 if (!NT_SUCCESS(Status
))
164 HeapFree(Win32CsrApiHeap
,0, NewBuffer
);
165 RtlFreeUnicodeString(&Console
->Title
);
166 DeleteCriticalSection(&Console
->Lock
);
167 CloseHandle(Console
->ActiveEvent
);
168 DPRINT1("GuiInitConsole: failed, Status = 0x%08lx\n", Status
);
173 Status
= CsrInitConsoleScreenBuffer(Console
, NewBuffer
);
174 if (!NT_SUCCESS(Status
))
176 ConioCleanupConsole(Console
);
177 RtlFreeUnicodeString(&Console
->Title
);
178 DeleteCriticalSection(&Console
->Lock
);
179 CloseHandle(Console
->ActiveEvent
);
180 HeapFree(Win32CsrApiHeap
, 0, NewBuffer
);
181 DPRINT1("CsrInitConsoleScreenBuffer: failed\n");
185 /* copy buffer contents to screen */
186 ConioDrawConsole(Console
);
188 return STATUS_SUCCESS
;
191 CSR_API(CsrAllocConsole
)
193 PCSRSS_CONSOLE Console
;
194 NTSTATUS Status
= STATUS_SUCCESS
;
195 BOOLEAN NewConsole
= FALSE
;
197 DPRINT("CsrAllocConsole\n");
199 RtlEnterCriticalSection(&ProcessData
->HandleTableLock
);
200 if (ProcessData
->Console
)
202 DPRINT1("Process already has a console\n");
203 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
204 return STATUS_INVALID_PARAMETER
;
207 /* If we don't need a console, then get out of here */
208 if (!Request
->Data
.AllocConsoleRequest
.ConsoleNeeded
)
210 DPRINT("No console needed\n");
211 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
212 return STATUS_SUCCESS
;
215 /* If we already have one, then don't create a new one... */
216 if (!Request
->Data
.AllocConsoleRequest
.Console
||
217 Request
->Data
.AllocConsoleRequest
.Console
!= ProcessData
->ParentConsole
)
219 /* Allocate a console structure */
221 Console
= HeapAlloc(Win32CsrApiHeap
, HEAP_ZERO_MEMORY
, sizeof(CSRSS_CONSOLE
));
224 DPRINT1("Not enough memory for console\n");
225 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
226 return STATUS_NO_MEMORY
;
228 /* initialize list head */
229 InitializeListHead(&Console
->ProcessList
);
230 /* insert process data required for GUI initialization */
231 InsertHeadList(&Console
->ProcessList
, &ProcessData
->ConsoleLink
);
232 /* Initialize the Console */
233 Status
= CsrInitConsole(Console
, Request
->Data
.AllocConsoleRequest
.ShowCmd
);
234 if (!NT_SUCCESS(Status
))
236 DPRINT1("Console init failed\n");
237 HeapFree(Win32CsrApiHeap
, 0, Console
);
238 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
244 /* Reuse our current console */
245 Console
= Request
->Data
.AllocConsoleRequest
.Console
;
248 /* Set the Process Console */
249 ProcessData
->Console
= Console
;
251 /* Return it to the caller */
252 Request
->Data
.AllocConsoleRequest
.Console
= Console
;
254 /* Add a reference count because the process is tied to the console */
255 _InterlockedIncrement(&Console
->ReferenceCount
);
257 if (NewConsole
|| !ProcessData
->bInheritHandles
)
259 /* Insert the Objects */
260 Status
= Win32CsrInsertObject(ProcessData
,
261 &Request
->Data
.AllocConsoleRequest
.InputHandle
,
263 GENERIC_READ
| GENERIC_WRITE
,
265 FILE_SHARE_READ
| FILE_SHARE_WRITE
);
266 if (! NT_SUCCESS(Status
))
268 DPRINT1("Failed to insert object\n");
269 ConioDeleteConsole((Object_t
*) Console
);
270 ProcessData
->Console
= 0;
271 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
275 Status
= Win32CsrInsertObject(ProcessData
,
276 &Request
->Data
.AllocConsoleRequest
.OutputHandle
,
277 &Console
->ActiveBuffer
->Header
,
278 GENERIC_READ
| GENERIC_WRITE
,
280 FILE_SHARE_READ
| FILE_SHARE_WRITE
);
281 if (!NT_SUCCESS(Status
))
283 DPRINT1("Failed to insert object\n");
284 ConioDeleteConsole((Object_t
*) Console
);
285 Win32CsrReleaseObject(ProcessData
,
286 Request
->Data
.AllocConsoleRequest
.InputHandle
);
287 ProcessData
->Console
= 0;
288 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
293 /* Duplicate the Event */
294 if (!DuplicateHandle(GetCurrentProcess(),
295 ProcessData
->Console
->ActiveEvent
,
296 ProcessData
->ProcessHandle
,
297 &ProcessData
->ConsoleEvent
,
302 DPRINT1("DuplicateHandle() failed: %lu\n", GetLastError());
303 ConioDeleteConsole((Object_t
*) Console
);
304 if (NewConsole
|| !ProcessData
->bInheritHandles
)
306 Win32CsrReleaseObject(ProcessData
,
307 Request
->Data
.AllocConsoleRequest
.OutputHandle
);
308 Win32CsrReleaseObject(ProcessData
,
309 Request
->Data
.AllocConsoleRequest
.InputHandle
);
311 ProcessData
->Console
= 0;
312 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
316 /* Set the Ctrl Dispatcher */
317 ProcessData
->CtrlDispatcher
= Request
->Data
.AllocConsoleRequest
.CtrlDispatcher
;
318 DPRINT("CSRSS:CtrlDispatcher address: %x\n", ProcessData
->CtrlDispatcher
);
322 /* Insert into the list if it has not been added */
323 InsertHeadList(&ProcessData
->Console
->ProcessList
, &ProcessData
->ConsoleLink
);
326 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
327 return STATUS_SUCCESS
;
330 CSR_API(CsrFreeConsole
)
332 Win32CsrReleaseConsole(ProcessData
);
333 return STATUS_SUCCESS
;
337 ConioDeleteConsole(Object_t
*Object
)
339 PCSRSS_CONSOLE Console
= (PCSRSS_CONSOLE
) Object
;
342 DPRINT("ConioDeleteConsole\n");
344 /* Drain input event queue */
345 while (Console
->InputEvents
.Flink
!= &Console
->InputEvents
)
347 Event
= (ConsoleInput
*) Console
->InputEvents
.Flink
;
348 Console
->InputEvents
.Flink
= Console
->InputEvents
.Flink
->Flink
;
349 Console
->InputEvents
.Flink
->Flink
->Blink
= &Console
->InputEvents
;
350 HeapFree(Win32CsrApiHeap
, 0, Event
);
353 ConioCleanupConsole(Console
);
354 if (Console
->LineBuffer
)
355 RtlFreeHeap(Win32CsrApiHeap
, 0, Console
->LineBuffer
);
356 while (!IsListEmpty(&Console
->HistoryBuffers
))
357 HistoryDeleteBuffer((struct tagHISTORY_BUFFER
*)Console
->HistoryBuffers
.Flink
);
359 ConioDeleteScreenBuffer(Console
->ActiveBuffer
);
360 if (!IsListEmpty(&Console
->BufferList
))
362 DPRINT1("BUG: screen buffer list not empty\n");
365 CloseHandle(Console
->ActiveEvent
);
366 if (Console
->UnpauseEvent
) CloseHandle(Console
->UnpauseEvent
);
367 DeleteCriticalSection(&Console
->Lock
);
368 RtlFreeUnicodeString(&Console
->Title
);
369 IntDeleteAllAliases(Console
->Aliases
);
370 HeapFree(Win32CsrApiHeap
, 0, Console
);
374 CsrInitConsoleSupport(VOID
)
376 DPRINT("CSR: CsrInitConsoleSupport()\n");
378 /* Should call LoadKeyboardLayout */
382 ConioPause(PCSRSS_CONSOLE Console
, UINT Flags
)
384 Console
->PauseFlags
|= Flags
;
385 if (!Console
->UnpauseEvent
)
386 Console
->UnpauseEvent
= CreateEvent(NULL
, TRUE
, FALSE
, NULL
);
390 ConioUnpause(PCSRSS_CONSOLE Console
, UINT Flags
)
392 Console
->PauseFlags
&= ~Flags
;
393 if (Console
->PauseFlags
== 0 && Console
->UnpauseEvent
)
395 SetEvent(Console
->UnpauseEvent
);
396 CloseHandle(Console
->UnpauseEvent
);
397 Console
->UnpauseEvent
= NULL
;
401 CSR_API(CsrSetConsoleMode
)
404 PCSRSS_CONSOLE Console
;
405 PCSRSS_SCREEN_BUFFER Buff
;
407 DPRINT("CsrSetConsoleMode\n");
409 Status
= Win32CsrLockObject(ProcessData
,
410 Request
->Data
.SetConsoleModeRequest
.ConsoleHandle
,
411 (Object_t
**) &Console
, GENERIC_WRITE
, 0);
412 if (! NT_SUCCESS(Status
))
417 Buff
= (PCSRSS_SCREEN_BUFFER
)Console
;
418 if (CONIO_CONSOLE_MAGIC
== Console
->Header
.Type
)
420 Console
->Mode
= Request
->Data
.SetConsoleModeRequest
.Mode
& CONSOLE_INPUT_MODE_VALID
;
422 else if (CONIO_SCREEN_BUFFER_MAGIC
== Console
->Header
.Type
)
424 Buff
->Mode
= Request
->Data
.SetConsoleModeRequest
.Mode
& CONSOLE_OUTPUT_MODE_VALID
;
428 Status
= STATUS_INVALID_HANDLE
;
431 Win32CsrUnlockObject((Object_t
*)Console
);
436 CSR_API(CsrGetConsoleMode
)
439 PCSRSS_CONSOLE Console
;
440 PCSRSS_SCREEN_BUFFER Buff
; /* gee, I really wish I could use an anonymous union here */
442 DPRINT("CsrGetConsoleMode\n");
444 Status
= Win32CsrLockObject(ProcessData
, Request
->Data
.GetConsoleModeRequest
.ConsoleHandle
,
445 (Object_t
**) &Console
, GENERIC_READ
, 0);
446 if (! NT_SUCCESS(Status
))
450 Status
= STATUS_SUCCESS
;
451 Buff
= (PCSRSS_SCREEN_BUFFER
) Console
;
452 if (CONIO_CONSOLE_MAGIC
== Console
->Header
.Type
)
454 Request
->Data
.GetConsoleModeRequest
.ConsoleMode
= Console
->Mode
;
456 else if (CONIO_SCREEN_BUFFER_MAGIC
== Buff
->Header
.Type
)
458 Request
->Data
.GetConsoleModeRequest
.ConsoleMode
= Buff
->Mode
;
462 Status
= STATUS_INVALID_HANDLE
;
465 Win32CsrUnlockObject((Object_t
*)Console
);
472 PCSRSS_CONSOLE Console
;
475 DPRINT("CsrSetTitle\n");
477 if (!Win32CsrValidateBuffer(ProcessData
, Request
->Data
.SetTitleRequest
.Title
,
478 Request
->Data
.SetTitleRequest
.Length
, 1))
480 return STATUS_ACCESS_VIOLATION
;
483 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
484 if(NT_SUCCESS(Status
))
486 Buffer
= RtlAllocateHeap(RtlGetProcessHeap(), 0, Request
->Data
.SetTitleRequest
.Length
);
489 /* copy title to console */
490 RtlFreeUnicodeString(&Console
->Title
);
491 Console
->Title
.Buffer
= Buffer
;
492 Console
->Title
.Length
= Console
->Title
.MaximumLength
= Request
->Data
.SetTitleRequest
.Length
;
493 memcpy(Console
->Title
.Buffer
, Request
->Data
.SetTitleRequest
.Title
, Console
->Title
.Length
);
494 if (! ConioChangeTitle(Console
))
496 Status
= STATUS_UNSUCCESSFUL
;
500 Status
= STATUS_SUCCESS
;
505 Status
= STATUS_NO_MEMORY
;
507 ConioUnlockConsole(Console
);
516 PCSRSS_CONSOLE Console
;
519 DPRINT("CsrGetTitle\n");
522 if (!Win32CsrValidateBuffer(ProcessData
, Request
->Data
.GetTitleRequest
.Title
,
523 Request
->Data
.GetTitleRequest
.Length
, 1))
525 return STATUS_ACCESS_VIOLATION
;
528 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
529 if (! NT_SUCCESS(Status
))
531 DPRINT1("Can't get console\n");
535 /* Copy title of the console to the user title buffer */
536 if (Request
->Data
.GetTitleRequest
.Length
>= sizeof(WCHAR
))
538 Length
= min(Request
->Data
.GetTitleRequest
.Length
- sizeof(WCHAR
), Console
->Title
.Length
);
539 memcpy(Request
->Data
.GetTitleRequest
.Title
, Console
->Title
.Buffer
, Length
);
540 Request
->Data
.GetTitleRequest
.Title
[Length
/ sizeof(WCHAR
)] = L
'\0';
543 Request
->Data
.GetTitleRequest
.Length
= Console
->Title
.Length
;
545 ConioUnlockConsole(Console
);
546 return STATUS_SUCCESS
;
549 /**********************************************************************
550 * HardwareStateProperty
553 * Set/Get the value of the HardwareState and switch
554 * between direct video buffer ouput and GDI windowed
557 * Client hands us a CSRSS_CONSOLE_HARDWARE_STATE
558 * object. We use the same object to Request.
560 * ConsoleHwState has the correct size to be compatible
561 * with NT's, but values are not.
563 static NTSTATUS FASTCALL
564 SetConsoleHardwareState (PCSRSS_CONSOLE Console
, DWORD ConsoleHwState
)
566 DPRINT1("Console Hardware State: %d\n", ConsoleHwState
);
568 if ((CONSOLE_HARDWARE_STATE_GDI_MANAGED
== ConsoleHwState
)
569 ||(CONSOLE_HARDWARE_STATE_DIRECT
== ConsoleHwState
))
571 if (Console
->HardwareState
!= ConsoleHwState
)
573 /* TODO: implement switching from full screen to windowed mode */
574 /* TODO: or back; now simply store the hardware state */
575 Console
->HardwareState
= ConsoleHwState
;
578 return STATUS_SUCCESS
;
581 return STATUS_INVALID_PARAMETER_3
; /* Client: (handle, set_get, [mode]) */
584 CSR_API(CsrHardwareStateProperty
)
586 PCSRSS_CONSOLE Console
;
589 DPRINT("CsrHardwareStateProperty\n");
591 Status
= ConioLockConsole(ProcessData
,
592 Request
->Data
.ConsoleHardwareStateRequest
.ConsoleHandle
,
595 if (! NT_SUCCESS(Status
))
597 DPRINT1("Failed to get console handle in SetConsoleHardwareState\n");
601 switch (Request
->Data
.ConsoleHardwareStateRequest
.SetGet
)
603 case CONSOLE_HARDWARE_STATE_GET
:
604 Request
->Data
.ConsoleHardwareStateRequest
.State
= Console
->HardwareState
;
607 case CONSOLE_HARDWARE_STATE_SET
:
608 DPRINT("Setting console hardware state.\n");
609 Status
= SetConsoleHardwareState(Console
, Request
->Data
.ConsoleHardwareStateRequest
.State
);
613 Status
= STATUS_INVALID_PARAMETER_2
; /* Client: (handle, [set_get], mode) */
617 ConioUnlockConsole(Console
);
622 CSR_API(CsrGetConsoleWindow
)
624 PCSRSS_CONSOLE Console
;
627 DPRINT("CsrGetConsoleWindow\n");
629 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
630 if (! NT_SUCCESS(Status
))
635 Request
->Data
.GetConsoleWindowRequest
.WindowHandle
= Console
->hWindow
;
636 ConioUnlockConsole(Console
);
638 return STATUS_SUCCESS
;
641 CSR_API(CsrSetConsoleIcon
)
643 PCSRSS_CONSOLE Console
;
646 DPRINT("CsrSetConsoleIcon\n");
648 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
649 if (! NT_SUCCESS(Status
))
654 Status
= (ConioChangeIcon(Console
, Request
->Data
.SetConsoleIconRequest
.WindowIcon
)
655 ? STATUS_SUCCESS
: STATUS_UNSUCCESSFUL
);
656 ConioUnlockConsole(Console
);
661 CSR_API(CsrGetConsoleCodePage
)
663 PCSRSS_CONSOLE Console
;
666 DPRINT("CsrGetConsoleCodePage\n");
668 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
669 if (! NT_SUCCESS(Status
))
674 Request
->Data
.GetConsoleCodePage
.CodePage
= Console
->CodePage
;
675 ConioUnlockConsole(Console
);
676 return STATUS_SUCCESS
;
679 CSR_API(CsrSetConsoleCodePage
)
681 PCSRSS_CONSOLE Console
;
684 DPRINT("CsrSetConsoleCodePage\n");
686 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
687 if (! NT_SUCCESS(Status
))
692 if (IsValidCodePage(Request
->Data
.SetConsoleCodePage
.CodePage
))
694 Console
->CodePage
= Request
->Data
.SetConsoleCodePage
.CodePage
;
695 ConioUnlockConsole(Console
);
696 return STATUS_SUCCESS
;
699 ConioUnlockConsole(Console
);
700 return STATUS_INVALID_PARAMETER
;
703 CSR_API(CsrGetConsoleOutputCodePage
)
705 PCSRSS_CONSOLE Console
;
708 DPRINT("CsrGetConsoleOutputCodePage\n");
710 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
711 if (! NT_SUCCESS(Status
))
716 Request
->Data
.GetConsoleOutputCodePage
.CodePage
= Console
->OutputCodePage
;
717 ConioUnlockConsole(Console
);
718 return STATUS_SUCCESS
;
721 CSR_API(CsrSetConsoleOutputCodePage
)
723 PCSRSS_CONSOLE Console
;
726 DPRINT("CsrSetConsoleOutputCodePage\n");
728 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
729 if (! NT_SUCCESS(Status
))
734 if (IsValidCodePage(Request
->Data
.SetConsoleOutputCodePage
.CodePage
))
736 Console
->OutputCodePage
= Request
->Data
.SetConsoleOutputCodePage
.CodePage
;
737 ConioUnlockConsole(Console
);
738 return STATUS_SUCCESS
;
741 ConioUnlockConsole(Console
);
742 return STATUS_INVALID_PARAMETER
;
745 CSR_API(CsrGetProcessList
)
748 PCSRSS_CONSOLE Console
;
749 PCSR_PROCESS current
;
750 PLIST_ENTRY current_entry
;
754 DPRINT("CsrGetProcessList\n");
756 Buffer
= Request
->Data
.GetProcessListRequest
.ProcessId
;
757 if (!Win32CsrValidateBuffer(ProcessData
, Buffer
, Request
->Data
.GetProcessListRequest
.nMaxIds
, sizeof(DWORD
)))
758 return STATUS_ACCESS_VIOLATION
;
760 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
761 if (! NT_SUCCESS(Status
))
766 for (current_entry
= Console
->ProcessList
.Flink
;
767 current_entry
!= &Console
->ProcessList
;
768 current_entry
= current_entry
->Flink
)
770 current
= CONTAINING_RECORD(current_entry
, CSR_PROCESS
, ConsoleLink
);
771 if (++nItems
<= Request
->Data
.GetProcessListRequest
.nMaxIds
)
773 *Buffer
++ = HandleToUlong(current
->ClientId
.UniqueProcess
);
777 ConioUnlockConsole(Console
);
779 Request
->Data
.GetProcessListRequest
.nProcessIdsTotal
= nItems
;
780 return STATUS_SUCCESS
;
783 CSR_API(CsrGenerateCtrlEvent
)
785 PCSRSS_CONSOLE Console
;
786 PCSR_PROCESS current
;
787 PLIST_ENTRY current_entry
;
791 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
792 if (! NT_SUCCESS(Status
))
797 Group
= Request
->Data
.GenerateCtrlEvent
.ProcessGroup
;
798 Status
= STATUS_INVALID_PARAMETER
;
799 for (current_entry
= Console
->ProcessList
.Flink
;
800 current_entry
!= &Console
->ProcessList
;
801 current_entry
= current_entry
->Flink
)
803 current
= CONTAINING_RECORD(current_entry
, CSR_PROCESS
, ConsoleLink
);
804 if (Group
== 0 || current
->ProcessGroupId
== Group
)
806 ConioConsoleCtrlEvent(Request
->Data
.GenerateCtrlEvent
.Event
, current
);
807 Status
= STATUS_SUCCESS
;
811 ConioUnlockConsole(Console
);
816 CSR_API(CsrGetConsoleSelectionInfo
)
819 PCSRSS_CONSOLE Console
;
821 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
822 if (NT_SUCCESS(Status
))
824 memset(&Request
->Data
.GetConsoleSelectionInfo
.Info
, 0, sizeof(CONSOLE_SELECTION_INFO
));
825 if (Console
->Selection
.dwFlags
!= 0)
826 Request
->Data
.GetConsoleSelectionInfo
.Info
= Console
->Selection
;
827 ConioUnlockConsole(Console
);