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
;
136 Status
= TuiInitConsole(Console
);
137 if (! NT_SUCCESS(Status
))
139 DPRINT1("Failed to open text-mode console, switching to gui-mode\n");
145 Status
= GuiInitConsole(Console
, ShowCmd
);
146 if (! NT_SUCCESS(Status
))
148 HeapFree(Win32CsrApiHeap
,0, NewBuffer
);
149 RtlFreeUnicodeString(&Console
->Title
);
150 DeleteCriticalSection(&Console
->Lock
);
151 CloseHandle(Console
->ActiveEvent
);
152 DPRINT1("GuiInitConsole: failed\n");
157 Status
= CsrInitConsoleScreenBuffer(Console
, NewBuffer
);
158 if (! NT_SUCCESS(Status
))
160 ConioCleanupConsole(Console
);
161 RtlFreeUnicodeString(&Console
->Title
);
162 DeleteCriticalSection(&Console
->Lock
);
163 CloseHandle(Console
->ActiveEvent
);
164 HeapFree(Win32CsrApiHeap
, 0, NewBuffer
);
165 DPRINT1("CsrInitConsoleScreenBuffer: failed\n");
169 /* copy buffer contents to screen */
170 ConioDrawConsole(Console
);
172 return STATUS_SUCCESS
;
175 CSR_API(CsrAllocConsole
)
177 PCSRSS_CONSOLE Console
;
178 NTSTATUS Status
= STATUS_SUCCESS
;
179 BOOLEAN NewConsole
= FALSE
;
181 DPRINT("CsrAllocConsole\n");
183 RtlEnterCriticalSection(&ProcessData
->HandleTableLock
);
184 if (ProcessData
->Console
)
186 DPRINT1("Process already has a console\n");
187 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
188 return STATUS_INVALID_PARAMETER
;
191 /* If we don't need a console, then get out of here */
192 if (!Request
->Data
.AllocConsoleRequest
.ConsoleNeeded
)
194 DPRINT("No console needed\n");
195 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
196 return STATUS_SUCCESS
;
199 /* If we already have one, then don't create a new one... */
200 if (!Request
->Data
.AllocConsoleRequest
.Console
||
201 Request
->Data
.AllocConsoleRequest
.Console
!= ProcessData
->ParentConsole
)
203 /* Allocate a console structure */
205 Console
= HeapAlloc(Win32CsrApiHeap
, HEAP_ZERO_MEMORY
, sizeof(CSRSS_CONSOLE
));
208 DPRINT1("Not enough memory for console\n");
209 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
210 return STATUS_NO_MEMORY
;
212 /* initialize list head */
213 InitializeListHead(&Console
->ProcessList
);
214 /* insert process data required for GUI initialization */
215 InsertHeadList(&Console
->ProcessList
, &ProcessData
->ConsoleLink
);
216 /* Initialize the Console */
217 Status
= CsrInitConsole(Console
, Request
->Data
.AllocConsoleRequest
.ShowCmd
);
218 if (!NT_SUCCESS(Status
))
220 DPRINT1("Console init failed\n");
221 HeapFree(Win32CsrApiHeap
, 0, Console
);
222 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
228 /* Reuse our current console */
229 Console
= Request
->Data
.AllocConsoleRequest
.Console
;
232 /* Set the Process Console */
233 ProcessData
->Console
= Console
;
235 /* Return it to the caller */
236 Request
->Data
.AllocConsoleRequest
.Console
= Console
;
238 /* Add a reference count because the process is tied to the console */
239 _InterlockedIncrement(&Console
->ReferenceCount
);
241 if (NewConsole
|| !ProcessData
->bInheritHandles
)
243 /* Insert the Objects */
244 Status
= Win32CsrInsertObject(ProcessData
,
245 &Request
->Data
.AllocConsoleRequest
.InputHandle
,
247 GENERIC_READ
| GENERIC_WRITE
,
249 FILE_SHARE_READ
| FILE_SHARE_WRITE
);
250 if (! NT_SUCCESS(Status
))
252 DPRINT1("Failed to insert object\n");
253 ConioDeleteConsole((Object_t
*) Console
);
254 ProcessData
->Console
= 0;
255 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
259 Status
= Win32CsrInsertObject(ProcessData
,
260 &Request
->Data
.AllocConsoleRequest
.OutputHandle
,
261 &Console
->ActiveBuffer
->Header
,
262 GENERIC_READ
| GENERIC_WRITE
,
264 FILE_SHARE_READ
| FILE_SHARE_WRITE
);
265 if (!NT_SUCCESS(Status
))
267 DPRINT1("Failed to insert object\n");
268 ConioDeleteConsole((Object_t
*) Console
);
269 Win32CsrReleaseObject(ProcessData
,
270 Request
->Data
.AllocConsoleRequest
.InputHandle
);
271 ProcessData
->Console
= 0;
272 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
277 /* Duplicate the Event */
278 if (!DuplicateHandle(GetCurrentProcess(),
279 ProcessData
->Console
->ActiveEvent
,
280 ProcessData
->ProcessHandle
,
281 &ProcessData
->ConsoleEvent
,
286 DPRINT1("DuplicateHandle() failed: %lu\n", GetLastError());
287 ConioDeleteConsole((Object_t
*) Console
);
288 if (NewConsole
|| !ProcessData
->bInheritHandles
)
290 Win32CsrReleaseObject(ProcessData
,
291 Request
->Data
.AllocConsoleRequest
.OutputHandle
);
292 Win32CsrReleaseObject(ProcessData
,
293 Request
->Data
.AllocConsoleRequest
.InputHandle
);
295 ProcessData
->Console
= 0;
296 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
300 /* Set the Ctrl Dispatcher */
301 ProcessData
->CtrlDispatcher
= Request
->Data
.AllocConsoleRequest
.CtrlDispatcher
;
302 DPRINT("CSRSS:CtrlDispatcher address: %x\n", ProcessData
->CtrlDispatcher
);
306 /* Insert into the list if it has not been added */
307 InsertHeadList(&ProcessData
->Console
->ProcessList
, &ProcessData
->ConsoleLink
);
310 RtlLeaveCriticalSection(&ProcessData
->HandleTableLock
);
311 return STATUS_SUCCESS
;
314 CSR_API(CsrFreeConsole
)
316 Win32CsrReleaseConsole(ProcessData
);
317 return STATUS_SUCCESS
;
321 ConioDeleteConsole(Object_t
*Object
)
323 PCSRSS_CONSOLE Console
= (PCSRSS_CONSOLE
) Object
;
326 DPRINT("ConioDeleteConsole\n");
328 /* Drain input event queue */
329 while (Console
->InputEvents
.Flink
!= &Console
->InputEvents
)
331 Event
= (ConsoleInput
*) Console
->InputEvents
.Flink
;
332 Console
->InputEvents
.Flink
= Console
->InputEvents
.Flink
->Flink
;
333 Console
->InputEvents
.Flink
->Flink
->Blink
= &Console
->InputEvents
;
334 HeapFree(Win32CsrApiHeap
, 0, Event
);
337 ConioCleanupConsole(Console
);
338 if (Console
->LineBuffer
)
339 RtlFreeHeap(Win32CsrApiHeap
, 0, Console
->LineBuffer
);
340 while (!IsListEmpty(&Console
->HistoryBuffers
))
341 HistoryDeleteBuffer((struct tagHISTORY_BUFFER
*)Console
->HistoryBuffers
.Flink
);
343 ConioDeleteScreenBuffer(Console
->ActiveBuffer
);
344 if (!IsListEmpty(&Console
->BufferList
))
346 DPRINT1("BUG: screen buffer list not empty\n");
349 CloseHandle(Console
->ActiveEvent
);
350 if (Console
->UnpauseEvent
) CloseHandle(Console
->UnpauseEvent
);
351 DeleteCriticalSection(&Console
->Lock
);
352 RtlFreeUnicodeString(&Console
->Title
);
353 IntDeleteAllAliases(Console
->Aliases
);
354 HeapFree(Win32CsrApiHeap
, 0, Console
);
358 CsrInitConsoleSupport(VOID
)
360 DPRINT("CSR: CsrInitConsoleSupport()\n");
362 /* Should call LoadKeyboardLayout */
366 ConioPause(PCSRSS_CONSOLE Console
, UINT Flags
)
368 Console
->PauseFlags
|= Flags
;
369 if (!Console
->UnpauseEvent
)
370 Console
->UnpauseEvent
= CreateEvent(NULL
, TRUE
, FALSE
, NULL
);
374 ConioUnpause(PCSRSS_CONSOLE Console
, UINT Flags
)
376 Console
->PauseFlags
&= ~Flags
;
377 if (Console
->PauseFlags
== 0 && Console
->UnpauseEvent
)
379 SetEvent(Console
->UnpauseEvent
);
380 CloseHandle(Console
->UnpauseEvent
);
381 Console
->UnpauseEvent
= NULL
;
385 CSR_API(CsrSetConsoleMode
)
388 PCSRSS_CONSOLE Console
;
389 PCSRSS_SCREEN_BUFFER Buff
;
391 DPRINT("CsrSetConsoleMode\n");
393 Status
= Win32CsrLockObject(ProcessData
,
394 Request
->Data
.SetConsoleModeRequest
.ConsoleHandle
,
395 (Object_t
**) &Console
, GENERIC_WRITE
, 0);
396 if (! NT_SUCCESS(Status
))
401 Buff
= (PCSRSS_SCREEN_BUFFER
)Console
;
402 if (CONIO_CONSOLE_MAGIC
== Console
->Header
.Type
)
404 Console
->Mode
= Request
->Data
.SetConsoleModeRequest
.Mode
& CONSOLE_INPUT_MODE_VALID
;
406 else if (CONIO_SCREEN_BUFFER_MAGIC
== Console
->Header
.Type
)
408 Buff
->Mode
= Request
->Data
.SetConsoleModeRequest
.Mode
& CONSOLE_OUTPUT_MODE_VALID
;
412 Status
= STATUS_INVALID_HANDLE
;
415 Win32CsrUnlockObject((Object_t
*)Console
);
420 CSR_API(CsrGetConsoleMode
)
423 PCSRSS_CONSOLE Console
;
424 PCSRSS_SCREEN_BUFFER Buff
; /* gee, I really wish I could use an anonymous union here */
426 DPRINT("CsrGetConsoleMode\n");
428 Status
= Win32CsrLockObject(ProcessData
, Request
->Data
.GetConsoleModeRequest
.ConsoleHandle
,
429 (Object_t
**) &Console
, GENERIC_READ
, 0);
430 if (! NT_SUCCESS(Status
))
434 Status
= STATUS_SUCCESS
;
435 Buff
= (PCSRSS_SCREEN_BUFFER
) Console
;
436 if (CONIO_CONSOLE_MAGIC
== Console
->Header
.Type
)
438 Request
->Data
.GetConsoleModeRequest
.ConsoleMode
= Console
->Mode
;
440 else if (CONIO_SCREEN_BUFFER_MAGIC
== Buff
->Header
.Type
)
442 Request
->Data
.GetConsoleModeRequest
.ConsoleMode
= Buff
->Mode
;
446 Status
= STATUS_INVALID_HANDLE
;
449 Win32CsrUnlockObject((Object_t
*)Console
);
456 PCSRSS_CONSOLE Console
;
459 DPRINT("CsrSetTitle\n");
461 if (!Win32CsrValidateBuffer(ProcessData
, Request
->Data
.SetTitleRequest
.Title
,
462 Request
->Data
.SetTitleRequest
.Length
, 1))
464 return STATUS_ACCESS_VIOLATION
;
467 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
468 if(NT_SUCCESS(Status
))
470 Buffer
= RtlAllocateHeap(RtlGetProcessHeap(), 0, Request
->Data
.SetTitleRequest
.Length
);
473 /* copy title to console */
474 RtlFreeUnicodeString(&Console
->Title
);
475 Console
->Title
.Buffer
= Buffer
;
476 Console
->Title
.Length
= Console
->Title
.MaximumLength
= Request
->Data
.SetTitleRequest
.Length
;
477 memcpy(Console
->Title
.Buffer
, Request
->Data
.SetTitleRequest
.Title
, Console
->Title
.Length
);
478 if (! ConioChangeTitle(Console
))
480 Status
= STATUS_UNSUCCESSFUL
;
484 Status
= STATUS_SUCCESS
;
489 Status
= STATUS_NO_MEMORY
;
491 ConioUnlockConsole(Console
);
500 PCSRSS_CONSOLE Console
;
503 DPRINT("CsrGetTitle\n");
506 if (!Win32CsrValidateBuffer(ProcessData
, Request
->Data
.GetTitleRequest
.Title
,
507 Request
->Data
.GetTitleRequest
.Length
, 1))
509 return STATUS_ACCESS_VIOLATION
;
512 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
513 if (! NT_SUCCESS(Status
))
515 DPRINT1("Can't get console\n");
519 /* Copy title of the console to the user title buffer */
520 if (Request
->Data
.GetTitleRequest
.Length
>= sizeof(WCHAR
))
522 Length
= min(Request
->Data
.GetTitleRequest
.Length
- sizeof(WCHAR
), Console
->Title
.Length
);
523 memcpy(Request
->Data
.GetTitleRequest
.Title
, Console
->Title
.Buffer
, Length
);
524 Request
->Data
.GetTitleRequest
.Title
[Length
/ sizeof(WCHAR
)] = L
'\0';
527 Request
->Data
.GetTitleRequest
.Length
= Console
->Title
.Length
;
529 ConioUnlockConsole(Console
);
530 return STATUS_SUCCESS
;
533 /**********************************************************************
534 * HardwareStateProperty
537 * Set/Get the value of the HardwareState and switch
538 * between direct video buffer ouput and GDI windowed
541 * Client hands us a CSRSS_CONSOLE_HARDWARE_STATE
542 * object. We use the same object to Request.
544 * ConsoleHwState has the correct size to be compatible
545 * with NT's, but values are not.
547 static NTSTATUS FASTCALL
548 SetConsoleHardwareState (PCSRSS_CONSOLE Console
, DWORD ConsoleHwState
)
550 DPRINT1("Console Hardware State: %d\n", ConsoleHwState
);
552 if ((CONSOLE_HARDWARE_STATE_GDI_MANAGED
== ConsoleHwState
)
553 ||(CONSOLE_HARDWARE_STATE_DIRECT
== ConsoleHwState
))
555 if (Console
->HardwareState
!= ConsoleHwState
)
557 /* TODO: implement switching from full screen to windowed mode */
558 /* TODO: or back; now simply store the hardware state */
559 Console
->HardwareState
= ConsoleHwState
;
562 return STATUS_SUCCESS
;
565 return STATUS_INVALID_PARAMETER_3
; /* Client: (handle, set_get, [mode]) */
568 CSR_API(CsrHardwareStateProperty
)
570 PCSRSS_CONSOLE Console
;
573 DPRINT("CsrHardwareStateProperty\n");
575 Status
= ConioLockConsole(ProcessData
,
576 Request
->Data
.ConsoleHardwareStateRequest
.ConsoleHandle
,
579 if (! NT_SUCCESS(Status
))
581 DPRINT1("Failed to get console handle in SetConsoleHardwareState\n");
585 switch (Request
->Data
.ConsoleHardwareStateRequest
.SetGet
)
587 case CONSOLE_HARDWARE_STATE_GET
:
588 Request
->Data
.ConsoleHardwareStateRequest
.State
= Console
->HardwareState
;
591 case CONSOLE_HARDWARE_STATE_SET
:
592 DPRINT("Setting console hardware state.\n");
593 Status
= SetConsoleHardwareState(Console
, Request
->Data
.ConsoleHardwareStateRequest
.State
);
597 Status
= STATUS_INVALID_PARAMETER_2
; /* Client: (handle, [set_get], mode) */
601 ConioUnlockConsole(Console
);
606 CSR_API(CsrGetConsoleWindow
)
608 PCSRSS_CONSOLE Console
;
611 DPRINT("CsrGetConsoleWindow\n");
613 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
614 if (! NT_SUCCESS(Status
))
619 Request
->Data
.GetConsoleWindowRequest
.WindowHandle
= Console
->hWindow
;
620 ConioUnlockConsole(Console
);
622 return STATUS_SUCCESS
;
625 CSR_API(CsrSetConsoleIcon
)
627 PCSRSS_CONSOLE Console
;
630 DPRINT("CsrSetConsoleIcon\n");
632 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
633 if (! NT_SUCCESS(Status
))
638 Status
= (ConioChangeIcon(Console
, Request
->Data
.SetConsoleIconRequest
.WindowIcon
)
639 ? STATUS_SUCCESS
: STATUS_UNSUCCESSFUL
);
640 ConioUnlockConsole(Console
);
645 CSR_API(CsrGetConsoleCodePage
)
647 PCSRSS_CONSOLE Console
;
650 DPRINT("CsrGetConsoleCodePage\n");
652 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
653 if (! NT_SUCCESS(Status
))
658 Request
->Data
.GetConsoleCodePage
.CodePage
= Console
->CodePage
;
659 ConioUnlockConsole(Console
);
660 return STATUS_SUCCESS
;
663 CSR_API(CsrSetConsoleCodePage
)
665 PCSRSS_CONSOLE Console
;
668 DPRINT("CsrSetConsoleCodePage\n");
670 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
671 if (! NT_SUCCESS(Status
))
676 if (IsValidCodePage(Request
->Data
.SetConsoleCodePage
.CodePage
))
678 Console
->CodePage
= Request
->Data
.SetConsoleCodePage
.CodePage
;
679 ConioUnlockConsole(Console
);
680 return STATUS_SUCCESS
;
683 ConioUnlockConsole(Console
);
684 return STATUS_INVALID_PARAMETER
;
687 CSR_API(CsrGetConsoleOutputCodePage
)
689 PCSRSS_CONSOLE Console
;
692 DPRINT("CsrGetConsoleOutputCodePage\n");
694 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
695 if (! NT_SUCCESS(Status
))
700 Request
->Data
.GetConsoleOutputCodePage
.CodePage
= Console
->OutputCodePage
;
701 ConioUnlockConsole(Console
);
702 return STATUS_SUCCESS
;
705 CSR_API(CsrSetConsoleOutputCodePage
)
707 PCSRSS_CONSOLE Console
;
710 DPRINT("CsrSetConsoleOutputCodePage\n");
712 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
713 if (! NT_SUCCESS(Status
))
718 if (IsValidCodePage(Request
->Data
.SetConsoleOutputCodePage
.CodePage
))
720 Console
->OutputCodePage
= Request
->Data
.SetConsoleOutputCodePage
.CodePage
;
721 ConioUnlockConsole(Console
);
722 return STATUS_SUCCESS
;
725 ConioUnlockConsole(Console
);
726 return STATUS_INVALID_PARAMETER
;
729 CSR_API(CsrGetProcessList
)
732 PCSRSS_CONSOLE Console
;
733 PCSR_PROCESS current
;
734 PLIST_ENTRY current_entry
;
738 DPRINT("CsrGetProcessList\n");
740 Buffer
= Request
->Data
.GetProcessListRequest
.ProcessId
;
741 if (!Win32CsrValidateBuffer(ProcessData
, Buffer
, Request
->Data
.GetProcessListRequest
.nMaxIds
, sizeof(DWORD
)))
742 return STATUS_ACCESS_VIOLATION
;
744 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
745 if (! NT_SUCCESS(Status
))
750 for (current_entry
= Console
->ProcessList
.Flink
;
751 current_entry
!= &Console
->ProcessList
;
752 current_entry
= current_entry
->Flink
)
754 current
= CONTAINING_RECORD(current_entry
, CSR_PROCESS
, ConsoleLink
);
755 if (++nItems
<= Request
->Data
.GetProcessListRequest
.nMaxIds
)
757 *Buffer
++ = HandleToUlong(current
->ClientId
.UniqueProcess
);
761 ConioUnlockConsole(Console
);
763 Request
->Data
.GetProcessListRequest
.nProcessIdsTotal
= nItems
;
764 return STATUS_SUCCESS
;
767 CSR_API(CsrGenerateCtrlEvent
)
769 PCSRSS_CONSOLE Console
;
770 PCSR_PROCESS current
;
771 PLIST_ENTRY current_entry
;
775 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
776 if (! NT_SUCCESS(Status
))
781 Group
= Request
->Data
.GenerateCtrlEvent
.ProcessGroup
;
782 Status
= STATUS_INVALID_PARAMETER
;
783 for (current_entry
= Console
->ProcessList
.Flink
;
784 current_entry
!= &Console
->ProcessList
;
785 current_entry
= current_entry
->Flink
)
787 current
= CONTAINING_RECORD(current_entry
, CSR_PROCESS
, ConsoleLink
);
788 if (Group
== 0 || current
->ProcessGroupId
== Group
)
790 ConioConsoleCtrlEvent(Request
->Data
.GenerateCtrlEvent
.Event
, current
);
791 Status
= STATUS_SUCCESS
;
795 ConioUnlockConsole(Console
);
800 CSR_API(CsrGetConsoleSelectionInfo
)
803 PCSRSS_CONSOLE Console
;
805 Status
= ConioConsoleFromProcessData(ProcessData
, &Console
);
806 if (NT_SUCCESS(Status
))
808 memset(&Request
->Data
.GetConsoleSelectionInfo
.Info
, 0, sizeof(CONSOLE_SELECTION_INFO
));
809 if (Console
->Selection
.dwFlags
!= 0)
810 Request
->Data
.GetConsoleSelectionInfo
.Info
= Console
->Selection
;
811 ConioUnlockConsole(Console
);