- NDK 0.98, now with versionned headers. Too many changes to list, see the TinyKRNL...
[reactos.git] / reactos / dll / win32 / kernel32 / misc / console.c
1 /* $Id$
2 *
3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS system libraries
5 * FILE: lib/kernel32/misc/console.c
6 * PURPOSE: Win32 server console functions
7 * PROGRAMMER: James Tabor
8 * <jimtabor@adsl-64-217-116-74.dsl.hstntx.swbell.net>
9 * UPDATE HISTORY:
10 * 199901?? ?? Created
11 * 19990204 EA SetConsoleTitleA
12 * 19990306 EA Stubs
13 */
14
15 /* INCLUDES ******************************************************************/
16
17 /* File contains Vista Semantics */
18 #undef _WIN32_WINNT
19 #define _WIN32_WINNT 0x0600
20
21 #include <k32.h>
22
23 #define NDEBUG
24 #include "../include/debug.h"
25
26 extern BOOL WINAPI DefaultConsoleCtrlHandler(DWORD Event);
27 extern __declspec(noreturn) VOID CALLBACK ConsoleControlDispatcher(DWORD CodeAndFlag);
28 extern RTL_CRITICAL_SECTION ConsoleLock;
29 extern BOOL WINAPI IsDebuggerPresent(VOID);
30
31
32 /* GLOBALS *******************************************************************/
33
34 static BOOL IgnoreCtrlEvents = FALSE;
35
36 static PHANDLER_ROUTINE* CtrlHandlers = NULL;
37 static ULONG NrCtrlHandlers = 0;
38 static WCHAR InputExeName[MAX_PATH + 1] = L"";
39
40 /* Default Console Control Handler *******************************************/
41
42 BOOL WINAPI DefaultConsoleCtrlHandler(DWORD Event)
43 {
44 switch(Event)
45 {
46 case CTRL_C_EVENT:
47 DPRINT("Ctrl-C Event\n");
48 break;
49
50 case CTRL_BREAK_EVENT:
51 DPRINT("Ctrl-Break Event\n");
52 break;
53
54 case CTRL_SHUTDOWN_EVENT:
55 DPRINT("Ctrl Shutdown Event\n");
56 break;
57
58 case CTRL_CLOSE_EVENT:
59 DPRINT("Ctrl Close Event\n");
60 break;
61
62 case CTRL_LOGOFF_EVENT:
63 DPRINT("Ctrl Logoff Event\n");
64 break;
65 }
66 ExitProcess(0);
67 return TRUE;
68 }
69
70
71 __declspec(noreturn) VOID CALLBACK ConsoleControlDispatcher(DWORD CodeAndFlag)
72 {
73 DWORD nExitCode = 0;
74 DWORD nCode = CodeAndFlag & MAXLONG;
75 UINT i;
76
77 SetThreadPriority(GetCurrentThread(), THREAD_PRIORITY_HIGHEST);
78
79 switch(nCode)
80 {
81 case CTRL_C_EVENT:
82 case CTRL_BREAK_EVENT:
83 {
84 if(IsDebuggerPresent())
85 {
86 EXCEPTION_RECORD erException;
87 erException.ExceptionCode =
88 (nCode == CTRL_C_EVENT ? DBG_CONTROL_C : DBG_CONTROL_BREAK);
89 erException.ExceptionFlags = 0;
90 erException.ExceptionRecord = NULL;
91 erException.ExceptionAddress = &DefaultConsoleCtrlHandler;
92 erException.NumberParameters = 0;
93 RtlRaiseException(&erException);
94 }
95 RtlEnterCriticalSection(&ConsoleLock);
96
97 if(!(nCode == CTRL_C_EVENT &&
98 NtCurrentPeb()->ProcessParameters->ConsoleFlags & 1))
99 {
100 for(i = NrCtrlHandlers; i > 0; -- i)
101 if(CtrlHandlers[i - 1](nCode)) break;
102 }
103 RtlLeaveCriticalSection(&ConsoleLock);
104 ExitThread(0);
105 }
106 case CTRL_CLOSE_EVENT:
107 case CTRL_LOGOFF_EVENT:
108 case CTRL_SHUTDOWN_EVENT:
109 break;
110
111 default: ExitThread(0);
112 }
113
114 RtlEnterCriticalSection(&ConsoleLock);
115
116 if(!(nCode == CTRL_C_EVENT &&
117 NtCurrentPeb()->ProcessParameters->ConsoleFlags & 1))
118 {
119 i = NrCtrlHandlers;
120 while(i > 0)
121 {
122 if (i == 1 && (CodeAndFlag & MINLONG) &&
123 (nCode == CTRL_LOGOFF_EVENT || nCode == CTRL_SHUTDOWN_EVENT))
124 break;
125
126 if(CtrlHandlers[i - 1](nCode))
127 {
128 switch(nCode)
129 {
130 case CTRL_CLOSE_EVENT:
131 case CTRL_LOGOFF_EVENT:
132 case CTRL_SHUTDOWN_EVENT:
133 nExitCode = CodeAndFlag;
134 }
135 break;
136 }
137 --i;
138 }
139 }
140 RtlLeaveCriticalSection(&ConsoleLock);
141 ExitThread(nExitCode);
142 }
143
144
145 /* FUNCTIONS *****************************************************************/
146
147 /*
148 * @unimplemented
149 */
150 BOOL STDCALL
151 AddConsoleAliasA (LPSTR Source,
152 LPSTR Target,
153 LPSTR ExeName)
154 {
155 DPRINT1("AddConsoleAliasA(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Source, Target, ExeName);
156 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
157 return FALSE;
158 }
159
160
161 /*
162 * @unimplemented
163 */
164 BOOL STDCALL
165 AddConsoleAliasW (LPWSTR Source,
166 LPWSTR Target,
167 LPWSTR ExeName)
168 {
169 DPRINT1("AddConsoleAliasW(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Source, Target, ExeName);
170 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
171 return FALSE;
172 }
173
174
175 /*
176 * @unimplemented
177 */
178 BOOL STDCALL
179 ConsoleMenuControl (HANDLE hConsole,
180 DWORD Unknown1,
181 DWORD Unknown2)
182 /*
183 * Undocumented
184 */
185 {
186 DPRINT1("ConsoleMenuControl(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", hConsole, Unknown1, Unknown2);
187 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
188 return FALSE;
189 }
190
191
192 /*
193 * @implemented
194 */
195 HANDLE STDCALL
196 DuplicateConsoleHandle (HANDLE hConsole,
197 DWORD dwDesiredAccess,
198 BOOL bInheritHandle,
199 DWORD dwOptions)
200 {
201 CSR_API_MESSAGE Request;
202 ULONG CsrRequest;
203 NTSTATUS Status;
204
205 if (IsConsoleHandle (hConsole) == FALSE)
206 {
207 SetLastError (ERROR_INVALID_PARAMETER);
208 return INVALID_HANDLE_VALUE;
209 }
210
211 CsrRequest = MAKE_CSR_API(DUPLICATE_HANDLE, CSR_NATIVE);
212 Request.Data.DuplicateHandleRequest.Handle = hConsole;
213 Request.Data.DuplicateHandleRequest.ProcessId = GetTeb()->Cid.UniqueProcess;
214 Status = CsrClientCallServer(&Request,
215 NULL,
216 CsrRequest,
217 sizeof(CSR_API_MESSAGE));
218 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status=Request.Status))
219 {
220 SetLastErrorByStatus(Status);
221 return INVALID_HANDLE_VALUE;
222 }
223 return Request.Data.DuplicateHandleRequest.Handle;
224 }
225
226
227 /*
228 * @unimplemented
229 */
230 DWORD STDCALL
231 ExpungeConsoleCommandHistoryW (DWORD Unknown0)
232 /*
233 * Undocumented
234 */
235 {
236 DPRINT1("ExpungeConsoleCommandHistoryW(0x%x) UNIMPLEMENTED!\n", Unknown0);
237 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
238 return 0;
239 }
240
241
242 /*
243 * @unimplemented
244 */
245 DWORD STDCALL
246 ExpungeConsoleCommandHistoryA (DWORD Unknown0)
247 /*
248 * Undocumented
249 */
250 {
251
252 DPRINT1("ExpungeConsoleCommandHistoryW(0x%x) UNIMPLEMENTED!\n", Unknown0);
253 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
254 return 0;
255 }
256
257
258 /*
259 * @unimplemented
260 */
261 DWORD STDCALL
262 GetConsoleAliasW (LPWSTR lpSource,
263 LPWSTR lpTargetBuffer,
264 DWORD TargetBufferLength,
265 LPWSTR lpExeName)
266 /*
267 * Undocumented
268 */
269 {
270 DPRINT1("GetConsoleAliasW(0x%p, 0x%p, 0x%x, 0x%p) UNIMPLEMENTED!\n", lpSource, lpTargetBuffer, TargetBufferLength, lpExeName);
271 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
272 return 0;
273 }
274
275
276 /*
277 * @unimplemented
278 */
279 DWORD STDCALL
280 GetConsoleAliasA (LPSTR lpSource,
281 LPSTR lpTargetBuffer,
282 DWORD TargetBufferLength,
283 LPSTR lpExeName)
284 /*
285 * Undocumented
286 */
287 {
288 DPRINT1("GetConsoleAliasA(0x%p, 0x%p, 0x%x, 0x%p) UNIMPLEMENTED!\n", lpSource, lpTargetBuffer, TargetBufferLength, lpExeName);
289 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
290 return 0;
291 }
292
293
294 /*
295 * @unimplemented
296 */
297 DWORD STDCALL
298 GetConsoleAliasExesW (LPWSTR lpExeNameBuffer,
299 DWORD ExeNameBufferLength)
300 /*
301 * Undocumented
302 */
303 {
304 DPRINT1("GetConsoleAliasExesW(0x%p, 0x%x) UNIMPLEMENTED!\n", lpExeNameBuffer, ExeNameBufferLength);
305 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
306 return 0;
307 }
308
309
310 /*
311 * @unimplemented
312 */
313 DWORD STDCALL
314 GetConsoleAliasExesA (LPSTR lpExeNameBuffer,
315 DWORD ExeNameBufferLength)
316 /*
317 * Undocumented
318 */
319 {
320 DPRINT1("GetConsoleAliasExesA(0x%p, 0x%x) UNIMPLEMENTED!\n", lpExeNameBuffer, ExeNameBufferLength);
321 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
322 return 0;
323 }
324
325
326 /*
327 * @unimplemented
328 */
329 DWORD STDCALL
330 GetConsoleAliasExesLengthA (VOID)
331 /*
332 * Undocumented
333 */
334 {
335 DPRINT1("GetConsoleAliasExesLengthA() UNIMPLEMENTED!\n");
336 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
337 return 0;
338 }
339
340
341 /*
342 * @unimplemented
343 */
344 DWORD STDCALL
345 GetConsoleAliasExesLengthW (VOID)
346 /*
347 * Undocumented
348 */
349 {
350 DPRINT1("GetConsoleAliasExesLengthW() UNIMPLEMENTED!\n");
351 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
352 return 0;
353 }
354
355
356 /*
357 * @unimplemented
358 */
359 DWORD STDCALL
360 GetConsoleAliasesW (DWORD Unknown0,
361 DWORD Unknown1,
362 DWORD Unknown2)
363 /*
364 * Undocumented
365 */
366 {
367 DPRINT1("GetConsoleAliasesW(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2);
368 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
369 return 0;
370 }
371
372
373 /*
374 * @unimplemented
375 */
376 DWORD STDCALL
377 GetConsoleAliasesA (DWORD Unknown0,
378 DWORD Unknown1,
379 DWORD Unknown2)
380 /*
381 * Undocumented
382 */
383 {
384 DPRINT1("GetConsoleAliasesA(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2);
385 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
386 return 0;
387 }
388
389
390 /*
391 * @unimplemented
392 */
393 DWORD STDCALL
394 GetConsoleAliasesLengthW (LPWSTR lpExeName)
395 /*
396 * Undocumented
397 */
398 {
399 DPRINT1("GetConsoleAliasesLengthW(0x%p) UNIMPLEMENTED!\n", lpExeName);
400 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
401 return 0;
402 }
403
404
405 /*
406 * @unimplemented
407 */
408 DWORD STDCALL
409 GetConsoleAliasesLengthA (LPSTR lpExeName)
410 /*
411 * Undocumented
412 */
413 {
414 DPRINT1("GetConsoleAliasesLengthA(0x%p) UNIMPLEMENTED!\n", lpExeName);
415 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
416 return 0;
417 }
418
419
420 /*
421 * @unimplemented
422 */
423 DWORD STDCALL
424 GetConsoleCommandHistoryW (DWORD Unknown0,
425 DWORD Unknown1,
426 DWORD Unknown2)
427 /*
428 * Undocumented
429 */
430 {
431 DPRINT1("GetConsoleCommandHistoryW(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2);
432 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
433 return 0;
434 }
435
436
437 /*
438 * @unimplemented
439 */
440 DWORD STDCALL
441 GetConsoleCommandHistoryA (DWORD Unknown0,
442 DWORD Unknown1,
443 DWORD Unknown2)
444 /*
445 * Undocumented
446 */
447 {
448 DPRINT1("GetConsoleCommandHistoryA(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2);
449 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
450 return 0;
451 }
452
453
454 /*
455 * @unimplemented
456 */
457 DWORD STDCALL
458 GetConsoleCommandHistoryLengthW (DWORD Unknown0)
459 /*
460 * Undocumented
461 */
462 {
463 DPRINT1("GetConsoleCommandHistoryLengthW(0x%x) UNIMPLEMENTED!\n", Unknown0);
464 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
465 return 0;
466 }
467
468
469 /*
470 * @unimplemented
471 */
472 DWORD STDCALL
473 GetConsoleCommandHistoryLengthA (DWORD Unknown0)
474 /*
475 * Undocumented
476 */
477 {
478 DPRINT1("GetConsoleCommandHistoryLengthA(0x%x) UNIMPLEMENTED!\n", Unknown0);
479 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
480 return 0;
481 }
482
483 /*
484 * @unimplemented
485 */
486 DWORD STDCALL
487 GetConsoleDisplayMode (LPDWORD lpdwMode)
488 /*
489 * FUNCTION: Get the console display mode
490 * ARGUMENTS:
491 * lpdwMode - Address of variable that receives the current value
492 * of display mode
493 * STATUS: Undocumented
494 */
495 {
496 DPRINT1("GetConsoleDisplayMode(0x%x) UNIMPLEMENTED!\n", lpdwMode);
497 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
498 return 0;
499 }
500
501
502 /*
503 * @unimplemented
504 */
505 DWORD STDCALL
506 GetConsoleFontInfo (DWORD Unknown0,
507 DWORD Unknown1,
508 DWORD Unknown2,
509 DWORD Unknown3)
510 /*
511 * Undocumented
512 */
513 {
514 DPRINT1("GetConsoleFontInfo(0x%x, 0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2, Unknown3);
515 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
516 return 0;
517 }
518
519
520 /*
521 * @unimplemented
522 */
523 COORD STDCALL
524 GetConsoleFontSize(HANDLE hConsoleOutput,
525 DWORD nFont)
526 {
527 COORD Empty = {0, 0};
528 DPRINT1("GetConsoleFontSize(0x%x, 0x%x) UNIMPLEMENTED!\n", hConsoleOutput, nFont);
529 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
530 return Empty ;
531 }
532
533
534 /*
535 * @implemented
536 */
537 DWORD STDCALL
538 GetConsoleHardwareState (HANDLE hConsole,
539 DWORD Flags,
540 PDWORD State)
541 /*
542 * Undocumented
543 */
544 {
545 CSR_API_MESSAGE Request; ULONG CsrRequest;
546
547 NTSTATUS Status;
548
549 CsrRequest = MAKE_CSR_API(SETGET_CONSOLE_HW_STATE, CSR_CONSOLE);
550 Request.Data.ConsoleHardwareStateRequest.ConsoleHandle = hConsole;
551 Request.Data.ConsoleHardwareStateRequest.SetGet = CONSOLE_HARDWARE_STATE_GET;
552
553 Status = CsrClientCallServer(& Request,
554 NULL,
555 CsrRequest,
556 sizeof(CSR_API_MESSAGE));
557 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
558 {
559 SetLastErrorByStatus(Status);
560 return FALSE;
561 }
562 *State = Request.Data.ConsoleHardwareStateRequest.State;
563 return TRUE;
564 }
565
566
567 /*
568 * @implemented
569 */
570 DWORD STDCALL
571 GetConsoleInputWaitHandle (VOID)
572 /*
573 * Undocumented
574 */
575 {
576 CSR_API_MESSAGE Request; ULONG CsrRequest;
577
578 NTSTATUS Status;
579
580 CsrRequest = MAKE_CSR_API(GET_INPUT_WAIT_HANDLE, CSR_CONSOLE);
581 Status = CsrClientCallServer(&Request, NULL, CsrRequest,
582 sizeof(CSR_API_MESSAGE));
583 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
584 {
585 SetLastErrorByStatus(Status);
586 return 0;
587 }
588 return (DWORD) Request.Data.GetConsoleInputWaitHandle.InputWaitHandle;
589 }
590
591
592 /*
593 * @unimplemented
594 */
595 DWORD STDCALL
596 GetCurrentConsoleFont(HANDLE hConsoleOutput,
597 BOOL bMaximumWindow,
598 PCONSOLE_FONT_INFO lpConsoleCurrentFont)
599 {
600 DPRINT1("GetCurrentConsoleFont(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", hConsoleOutput, bMaximumWindow, lpConsoleCurrentFont);
601 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
602 return 0;
603 }
604
605
606 /*
607 * @unimplemented
608 */
609 ULONG STDCALL
610 GetNumberOfConsoleFonts (VOID)
611 /*
612 * Undocumented
613 */
614 {
615 DPRINT1("GetNumberOfConsoleFonts() UNIMPLEMENTED!\n");
616 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
617 return 1; /* FIXME: call csrss.exe */
618 }
619
620
621 /*
622 * @unimplemented
623 */
624 DWORD STDCALL
625 InvalidateConsoleDIBits (DWORD Unknown0,
626 DWORD Unknown1)
627 /*
628 * Undocumented
629 */
630 {
631 DPRINT1("InvalidateConsoleDIBits(0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1);
632 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
633 return 0;
634 }
635
636
637 /*
638 * @unimplemented
639 */
640 HANDLE STDCALL
641 OpenConsoleW (LPWSTR wsName,
642 DWORD dwDesiredAccess,
643 BOOL bInheritHandle,
644 DWORD dwCreationDistribution)
645 /*
646 * Undocumented
647 */
648 {
649 CSR_API_MESSAGE Request; ULONG CsrRequest;
650
651 PHANDLE phConsole = NULL;
652 NTSTATUS Status = STATUS_SUCCESS;
653
654 if(0 == _wcsicmp(wsName, L"CONIN$"))
655 {
656 CsrRequest = MAKE_CSR_API(GET_INPUT_HANDLE, CSR_NATIVE);
657 phConsole = & Request.Data.GetInputHandleRequest.InputHandle;
658 }
659 else if (0 == _wcsicmp(wsName, L"CONOUT$"))
660 {
661 CsrRequest = MAKE_CSR_API(GET_OUTPUT_HANDLE, CSR_NATIVE);
662 phConsole = & Request.Data.GetOutputHandleRequest.OutputHandle;
663 }
664 else
665 {
666 SetLastError(ERROR_INVALID_PARAMETER);
667 return(INVALID_HANDLE_VALUE);
668 }
669 if ((GENERIC_READ|GENERIC_WRITE) != dwDesiredAccess)
670 {
671 SetLastError(ERROR_INVALID_PARAMETER);
672 return(INVALID_HANDLE_VALUE);
673 }
674 if (OPEN_EXISTING != dwCreationDistribution)
675 {
676 SetLastError(ERROR_INVALID_PARAMETER);
677 return(INVALID_HANDLE_VALUE);
678 }
679 Status = CsrClientCallServer(& Request,
680 NULL,
681 CsrRequest,
682 sizeof(CSR_API_MESSAGE));
683 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
684 {
685 SetLastErrorByStatus(Status);
686 return INVALID_HANDLE_VALUE;
687 }
688 return(*phConsole);
689 }
690
691
692 /*
693 * @unimplemented
694 */
695 BOOL STDCALL
696 SetConsoleCommandHistoryMode (DWORD dwMode)
697 /*
698 * Undocumented
699 */
700 {
701 DPRINT1("SetConsoleCommandHistoryMode(0x%x) UNIMPLEMENTED!\n", dwMode);
702 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
703 return FALSE;
704 }
705
706
707 /*
708 * @unimplemented
709 */
710 BOOL STDCALL
711 SetConsoleCursor (DWORD Unknown0,
712 DWORD Unknown1)
713 /*
714 * Undocumented
715 */
716 {
717 DPRINT1("SetConsoleCursor(0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1);
718 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
719 return FALSE;
720 }
721
722
723 /*
724 * @unimplemented
725 */
726 BOOL STDCALL
727 SetConsoleDisplayMode (HANDLE hOut,
728 DWORD dwNewMode,
729 LPDWORD lpdwOldMode)
730 /*
731 * FUNCTION: Set the console display mode.
732 * ARGUMENTS:
733 * hOut - Standard output handle.
734 * dwNewMode - New mode.
735 * lpdwOldMode - Address of a variable that receives the old mode.
736 */
737 {
738 DPRINT1("SetConsoleDisplayMode(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", hOut, dwNewMode, lpdwOldMode);
739 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
740 return FALSE;
741 }
742
743
744 /*
745 * @unimplemented
746 */
747 BOOL STDCALL
748 SetConsoleFont (DWORD Unknown0,
749 DWORD Unknown1)
750 /*
751 * Undocumented
752 */
753 {
754 DPRINT1("SetConsoleFont(0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1);
755 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
756 return FALSE;
757 }
758
759
760 /*
761 * @implemented
762 */
763 BOOL STDCALL
764 SetConsoleHardwareState (HANDLE hConsole,
765 DWORD Flags,
766 DWORD State)
767 /*
768 * Undocumented
769 */
770 {
771 CSR_API_MESSAGE Request; ULONG CsrRequest;
772
773 NTSTATUS Status;
774
775 CsrRequest = MAKE_CSR_API(SETGET_CONSOLE_HW_STATE, CSR_CONSOLE);
776 Request.Data.ConsoleHardwareStateRequest.ConsoleHandle = hConsole;
777 Request.Data.ConsoleHardwareStateRequest.SetGet = CONSOLE_HARDWARE_STATE_SET;
778 Request.Data.ConsoleHardwareStateRequest.State = State;
779
780 Status = CsrClientCallServer(& Request,
781 NULL,
782 CsrRequest,
783 sizeof(CSR_API_MESSAGE));
784 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
785 {
786 SetLastErrorByStatus(Status);
787 return FALSE;
788 }
789 return TRUE;
790 }
791
792
793 /*
794 * @unimplemented
795 */
796 BOOL STDCALL
797 SetConsoleKeyShortcuts (DWORD Unknown0,
798 DWORD Unknown1,
799 DWORD Unknown2,
800 DWORD Unknown3)
801 /*
802 * Undocumented
803 */
804 {
805 DPRINT1("SetConsoleKeyShortcuts(0x%x, 0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2, Unknown3);
806 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
807 return FALSE;
808 }
809
810
811 /*
812 * @unimplemented
813 */
814 BOOL STDCALL
815 SetConsoleMaximumWindowSize (DWORD Unknown0,
816 DWORD Unknown1)
817 /*
818 * Undocumented
819 */
820 {
821 DPRINT1("SetConsoleMaximumWindowSize(0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1);
822 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
823 return FALSE;
824 }
825
826
827 /*
828 * @unimplemented
829 */
830 BOOL STDCALL
831 SetConsoleMenuClose (DWORD Unknown0)
832 /*
833 * Undocumented
834 */
835 {
836 DPRINT1("SetConsoleMenuClose(0x%x) UNIMPLEMENTED!\n", Unknown0);
837 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
838 return FALSE;
839 }
840
841
842 /*
843 * @unimplemented
844 */
845 BOOL STDCALL
846 SetConsoleNumberOfCommandsA (DWORD Unknown0,
847 DWORD Unknown1)
848 /*
849 * Undocumented
850 */
851 {
852 DPRINT1("SetConsoleNumberOfCommandsA(0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1);
853 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
854 return FALSE;
855 }
856
857
858 /*
859 * @unimplemented
860 */
861 BOOL STDCALL
862 SetConsoleNumberOfCommandsW (DWORD Unknown0,
863 DWORD Unknown1)
864 /*
865 * Undocumented
866 */
867 {
868 DPRINT1("SetConsoleNumberOfCommandsW(0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1);
869 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
870 return FALSE;
871 }
872
873
874 /*
875 * @unimplemented
876 */
877 BOOL STDCALL
878 SetConsolePalette (DWORD Unknown0,
879 DWORD Unknown1,
880 DWORD Unknown2)
881 /*
882 * Undocumented
883 */
884 {
885 DPRINT1("SetConsolePalette(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2);
886 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
887 return FALSE;
888 }
889
890
891 /*
892 * @unimplemented
893 */
894 BOOL STDCALL
895 SetLastConsoleEventActive (VOID)
896 /*
897 * Undocumented
898 */
899 {
900 DPRINT1("SetLastConsoleEventActive() UNIMPLEMENTED!\n");
901 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
902 return FALSE;
903 }
904
905
906 /*
907 * @unimplemented
908 */
909 DWORD STDCALL
910 ShowConsoleCursor (DWORD Unknown0,
911 DWORD Unknown1)
912 /*
913 * Undocumented
914 */
915 {
916 DPRINT1("ShowConsoleCursor(0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1);
917 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
918 return 0;
919 }
920
921
922 /*
923 * FUNCTION: Checks whether the given handle is a valid console handle.
924 * ARGUMENTS:
925 * Handle - Handle to be checked
926 * RETURNS:
927 * TRUE: Handle is a valid console handle
928 * FALSE: Handle is not a valid console handle.
929 * STATUS: Officially undocumented
930 *
931 * @implemented
932 */
933 BOOL STDCALL
934 VerifyConsoleIoHandle(HANDLE Handle)
935 {
936 CSR_API_MESSAGE Request; ULONG CsrRequest;
937
938 NTSTATUS Status;
939
940 CsrRequest = MAKE_CSR_API(VERIFY_HANDLE, CSR_NATIVE);
941 Request.Data.VerifyHandleRequest.Handle = Handle;
942 Status = CsrClientCallServer(&Request,
943 NULL,
944 CsrRequest,
945 sizeof(CSR_API_MESSAGE));
946 if (!NT_SUCCESS(Status))
947 {
948 SetLastErrorByStatus(Status);
949 return FALSE;
950 }
951
952 return (BOOL)NT_SUCCESS(Request.Status);
953 }
954
955
956 /*
957 * @unimplemented
958 */
959 DWORD STDCALL
960 WriteConsoleInputVDMA (DWORD Unknown0,
961 DWORD Unknown1,
962 DWORD Unknown2,
963 DWORD Unknown3)
964 {
965 DPRINT1("WriteConsoleInputVDMA(0x%x, 0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2, Unknown3);
966 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
967 return 0;
968 }
969
970
971 /*
972 * @unimplemented
973 */
974 DWORD STDCALL
975 WriteConsoleInputVDMW (DWORD Unknown0,
976 DWORD Unknown1,
977 DWORD Unknown2,
978 DWORD Unknown3)
979 {
980 DPRINT1("WriteConsoleInputVDMW(0x%x, 0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", Unknown0, Unknown1, Unknown2, Unknown3);
981 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
982 return 0;
983 }
984
985
986 /*
987 * @implemented
988 */
989 BOOL STDCALL
990 CloseConsoleHandle(HANDLE Handle)
991 /*
992 * Undocumented
993 */
994 {
995 CSR_API_MESSAGE Request; ULONG CsrRequest;
996
997 NTSTATUS Status;
998
999 if (IsConsoleHandle (Handle) == FALSE)
1000 {
1001 SetLastError (ERROR_INVALID_PARAMETER);
1002 return FALSE;
1003 }
1004
1005 CsrRequest = MAKE_CSR_API(CLOSE_HANDLE, CSR_NATIVE);
1006 Request.Data.CloseHandleRequest.Handle = Handle;
1007 Status = CsrClientCallServer(&Request,
1008 NULL,
1009 CsrRequest,
1010 sizeof(CSR_API_MESSAGE));
1011 if (!NT_SUCCESS(Status))
1012 {
1013 SetLastErrorByStatus(Status);
1014 return FALSE;
1015 }
1016
1017 return TRUE;
1018 }
1019
1020 /*
1021 * @implemented
1022 */
1023 HANDLE STDCALL
1024 GetStdHandle(DWORD nStdHandle)
1025 /*
1026 * FUNCTION: Get a handle for the standard input, standard output
1027 * and a standard error device.
1028 * ARGUMENTS:
1029 * nStdHandle - Specifies the device for which to return the handle.
1030 * RETURNS: If the function succeeds, the return value is the handle
1031 * of the specified device. Otherwise the value is INVALID_HANDLE_VALUE.
1032 */
1033 {
1034 PRTL_USER_PROCESS_PARAMETERS Ppb;
1035
1036 Ppb = NtCurrentPeb()->ProcessParameters;
1037 switch (nStdHandle)
1038 {
1039 case STD_INPUT_HANDLE:
1040 return Ppb->StandardInput;
1041
1042 case STD_OUTPUT_HANDLE:
1043 return Ppb->StandardOutput;
1044
1045 case STD_ERROR_HANDLE:
1046 return Ppb->StandardError;
1047 }
1048
1049 SetLastError (ERROR_INVALID_PARAMETER);
1050 return INVALID_HANDLE_VALUE;
1051 }
1052
1053
1054 /*
1055 * @implemented
1056 */
1057 BOOL WINAPI
1058 SetStdHandle(DWORD nStdHandle,
1059 HANDLE hHandle)
1060 /*
1061 * FUNCTION: Set the handle for the standard input, standard output or
1062 * the standard error device.
1063 * ARGUMENTS:
1064 * nStdHandle - Specifies the handle to be set.
1065 * hHandle - The handle to set.
1066 * RETURNS: TRUE if the function succeeds, FALSE otherwise.
1067 */
1068 {
1069 PRTL_USER_PROCESS_PARAMETERS Ppb;
1070
1071 /* no need to check if hHandle == INVALID_HANDLE_VALUE */
1072
1073 Ppb = NtCurrentPeb()->ProcessParameters;
1074
1075 switch (nStdHandle)
1076 {
1077 case STD_INPUT_HANDLE:
1078 Ppb->StandardInput = hHandle;
1079 return TRUE;
1080
1081 case STD_OUTPUT_HANDLE:
1082 Ppb->StandardOutput = hHandle;
1083 return TRUE;
1084
1085 case STD_ERROR_HANDLE:
1086 Ppb->StandardError = hHandle;
1087 return TRUE;
1088 }
1089
1090 /* windows for whatever reason sets the last error to ERROR_INVALID_HANDLE here */
1091 SetLastError (ERROR_INVALID_HANDLE);
1092 return FALSE;
1093 }
1094
1095
1096 static BOOL
1097 IntWriteConsole(HANDLE hConsoleOutput,
1098 PVOID lpBuffer,
1099 DWORD nNumberOfCharsToWrite,
1100 LPDWORD lpNumberOfCharsWritten,
1101 LPVOID lpReserved,
1102 BOOL bUnicode)
1103 {
1104 PCSR_API_MESSAGE Request;
1105 ULONG CsrRequest;
1106 NTSTATUS Status;
1107 USHORT nChars;
1108 ULONG SizeBytes, CharSize;
1109 DWORD Written = 0;
1110
1111 CharSize = (bUnicode ? sizeof(WCHAR) : sizeof(CHAR));
1112 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
1113 max(sizeof(CSR_API_MESSAGE),
1114 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_WRITE_CONSOLE)
1115 + min(nNumberOfCharsToWrite, CSRSS_MAX_WRITE_CONSOLE / CharSize) * CharSize));
1116 if (Request == NULL)
1117 {
1118 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
1119 return FALSE;
1120 }
1121
1122 CsrRequest = MAKE_CSR_API(WRITE_CONSOLE, CSR_CONSOLE);
1123
1124 while(nNumberOfCharsToWrite > 0)
1125 {
1126 Request->Data.WriteConsoleRequest.ConsoleHandle = hConsoleOutput;
1127 Request->Data.WriteConsoleRequest.Unicode = bUnicode;
1128
1129 nChars = min(nNumberOfCharsToWrite, CSRSS_MAX_WRITE_CONSOLE / CharSize);
1130 Request->Data.WriteConsoleRequest.NrCharactersToWrite = nChars;
1131
1132 SizeBytes = nChars * CharSize;
1133
1134 memcpy(Request->Data.WriteConsoleRequest.Buffer, lpBuffer, SizeBytes);
1135
1136 Status = CsrClientCallServer(Request,
1137 NULL,
1138 CsrRequest,
1139 max(sizeof(CSR_API_MESSAGE), CSR_API_MESSAGE_HEADER_SIZE(CSRSS_WRITE_CONSOLE) + SizeBytes));
1140
1141 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request->Status))
1142 {
1143 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
1144 SetLastErrorByStatus(Status);
1145 return FALSE;
1146 }
1147
1148 nNumberOfCharsToWrite -= nChars;
1149 lpBuffer = (PVOID)((ULONG_PTR)lpBuffer + (ULONG_PTR)SizeBytes);
1150 Written += Request->Data.WriteConsoleRequest.NrCharactersWritten;
1151 }
1152
1153 if(lpNumberOfCharsWritten != NULL)
1154 {
1155 *lpNumberOfCharsWritten = Written;
1156 }
1157 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
1158
1159 return TRUE;
1160 }
1161
1162
1163 /*--------------------------------------------------------------
1164 * WriteConsoleA
1165 *
1166 * @implemented
1167 */
1168 BOOL STDCALL
1169 WriteConsoleA(HANDLE hConsoleOutput,
1170 CONST VOID *lpBuffer,
1171 DWORD nNumberOfCharsToWrite,
1172 LPDWORD lpNumberOfCharsWritten,
1173 LPVOID lpReserved)
1174 {
1175 return IntWriteConsole(hConsoleOutput,
1176 (PVOID)lpBuffer,
1177 nNumberOfCharsToWrite,
1178 lpNumberOfCharsWritten,
1179 lpReserved,
1180 FALSE);
1181 }
1182
1183
1184 /*--------------------------------------------------------------
1185 * WriteConsoleW
1186 *
1187 * @implemented
1188 */
1189 BOOL STDCALL
1190 WriteConsoleW(
1191 HANDLE hConsoleOutput,
1192 CONST VOID *lpBuffer,
1193 DWORD nNumberOfCharsToWrite,
1194 LPDWORD lpNumberOfCharsWritten,
1195 LPVOID lpReserved
1196 )
1197 {
1198 return IntWriteConsole(hConsoleOutput,
1199 (PVOID)lpBuffer,
1200 nNumberOfCharsToWrite,
1201 lpNumberOfCharsWritten,
1202 lpReserved,
1203 TRUE);
1204 }
1205
1206
1207 static BOOL
1208 IntReadConsole(HANDLE hConsoleInput,
1209 PVOID lpBuffer,
1210 DWORD nNumberOfCharsToRead,
1211 LPDWORD lpNumberOfCharsRead,
1212 LPVOID lpReserved,
1213 BOOL bUnicode)
1214 {
1215 PCSR_API_MESSAGE Request;
1216 ULONG CsrRequest;
1217 NTSTATUS Status;
1218 ULONG CharSize, CharsRead = 0;
1219
1220 CharSize = (bUnicode ? sizeof(WCHAR) : sizeof(CHAR));
1221 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
1222 max(sizeof(CSR_API_MESSAGE),
1223 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE)
1224 + min(nNumberOfCharsToRead, CSRSS_MAX_READ_CONSOLE / CharSize) * CharSize));
1225 if (Request == NULL)
1226 {
1227 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
1228 return FALSE;
1229 }
1230
1231 Request->Status = STATUS_SUCCESS;
1232 CsrRequest = MAKE_CSR_API(READ_CONSOLE, CSR_CONSOLE);
1233
1234 do
1235 {
1236 if(Request->Status == STATUS_PENDING)
1237 {
1238 Status = NtWaitForSingleObject(Request->Data.ReadConsoleRequest.EventHandle, FALSE, 0);
1239 if(!NT_SUCCESS(Status))
1240 {
1241 DPRINT1("Wait for console input failed!\n");
1242 break;
1243 }
1244 }
1245
1246 Request->Data.ReadConsoleRequest.ConsoleHandle = hConsoleInput;
1247 Request->Data.ReadConsoleRequest.Unicode = bUnicode;
1248 Request->Data.ReadConsoleRequest.NrCharactersToRead = min(nNumberOfCharsToRead, CSRSS_MAX_READ_CONSOLE / CharSize);
1249 Request->Data.ReadConsoleRequest.nCharsCanBeDeleted = CharsRead;
1250 Status = CsrClientCallServer(Request,
1251 NULL,
1252 CsrRequest,
1253 max(sizeof(CSR_API_MESSAGE),
1254 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE)
1255 + Request->Data.ReadConsoleRequest.NrCharactersToRead * CharSize));
1256
1257 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request->Status))
1258 {
1259 DPRINT1("CSR returned error in ReadConsole\n");
1260 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
1261 SetLastErrorByStatus(Status);
1262 return FALSE;
1263 }
1264
1265 nNumberOfCharsToRead -= Request->Data.ReadConsoleRequest.NrCharactersRead;
1266 memcpy((PVOID)((ULONG_PTR)lpBuffer + (ULONG_PTR)(CharsRead * CharSize)),
1267 Request->Data.ReadConsoleRequest.Buffer,
1268 Request->Data.ReadConsoleRequest.NrCharactersRead * CharSize);
1269 CharsRead += Request->Data.ReadConsoleRequest.NrCharactersRead;
1270
1271 if(Request->Status == STATUS_NOTIFY_CLEANUP)
1272 {
1273 if(CharsRead > 0)
1274 {
1275 CharsRead--;
1276 nNumberOfCharsToRead++;
1277 }
1278 Request->Status = STATUS_PENDING;
1279 }
1280 } while(Request->Status == STATUS_PENDING && nNumberOfCharsToRead > 0);
1281
1282 if(lpNumberOfCharsRead != NULL)
1283 {
1284 *lpNumberOfCharsRead = CharsRead;
1285 }
1286
1287 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
1288
1289 return TRUE;
1290 }
1291
1292
1293 /*--------------------------------------------------------------
1294 * ReadConsoleA
1295 *
1296 * @implemented
1297 */
1298 BOOL STDCALL
1299 ReadConsoleA(HANDLE hConsoleInput,
1300 LPVOID lpBuffer,
1301 DWORD nNumberOfCharsToRead,
1302 LPDWORD lpNumberOfCharsRead,
1303 LPVOID lpReserved)
1304 {
1305 return IntReadConsole(hConsoleInput,
1306 lpBuffer,
1307 nNumberOfCharsToRead,
1308 lpNumberOfCharsRead,
1309 lpReserved,
1310 FALSE);
1311 }
1312
1313
1314 /*--------------------------------------------------------------
1315 * ReadConsoleW
1316 *
1317 * @implemented
1318 */
1319 BOOL STDCALL
1320 ReadConsoleW(HANDLE hConsoleInput,
1321 LPVOID lpBuffer,
1322 DWORD nNumberOfCharsToRead,
1323 LPDWORD lpNumberOfCharsRead,
1324 LPVOID lpReserved)
1325 {
1326 return IntReadConsole(hConsoleInput,
1327 lpBuffer,
1328 nNumberOfCharsToRead,
1329 lpNumberOfCharsRead,
1330 lpReserved,
1331 TRUE);
1332 }
1333
1334
1335 /*--------------------------------------------------------------
1336 * AllocConsole
1337 *
1338 * @implemented
1339 */
1340 BOOL STDCALL AllocConsole(VOID)
1341 {
1342 CSR_API_MESSAGE Request; ULONG CsrRequest;
1343
1344 NTSTATUS Status;
1345 HANDLE hStdError;
1346
1347 if(NtCurrentPeb()->ProcessParameters->ConsoleHandle)
1348 {
1349 DPRINT("AllocConsole: Allocate duplicate console to the same Process\n");
1350 SetLastErrorByStatus (STATUS_OBJECT_NAME_EXISTS);
1351 return FALSE;
1352 }
1353
1354 Request.Data.AllocConsoleRequest.CtrlDispatcher = ConsoleControlDispatcher;
1355 Request.Data.AllocConsoleRequest.ConsoleNeeded = TRUE;
1356
1357 CsrRequest = MAKE_CSR_API(ALLOC_CONSOLE, CSR_CONSOLE);
1358 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
1359 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
1360 {
1361 SetLastErrorByStatus ( Status );
1362 return FALSE;
1363 }
1364 NtCurrentPeb()->ProcessParameters->ConsoleHandle = Request.Data.AllocConsoleRequest.Console;
1365 SetStdHandle( STD_INPUT_HANDLE, Request.Data.AllocConsoleRequest.InputHandle );
1366 SetStdHandle( STD_OUTPUT_HANDLE, Request.Data.AllocConsoleRequest.OutputHandle );
1367 hStdError = DuplicateConsoleHandle(Request.Data.AllocConsoleRequest.OutputHandle,
1368 0,
1369 TRUE,
1370 DUPLICATE_SAME_ACCESS);
1371 SetStdHandle( STD_ERROR_HANDLE, hStdError );
1372 return TRUE;
1373 }
1374
1375
1376 /*--------------------------------------------------------------
1377 * FreeConsole
1378 *
1379 * @implemented
1380 */
1381 BOOL STDCALL FreeConsole(VOID)
1382 {
1383 // AG: I'm not sure if this is correct (what happens to std handles?)
1384 // but I just tried to reverse what AllocConsole() does...
1385
1386 CSR_API_MESSAGE Request; ULONG CsrRequest;
1387
1388 NTSTATUS Status;
1389
1390 CsrRequest = MAKE_CSR_API(FREE_CONSOLE, CSR_CONSOLE);
1391 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
1392 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
1393 {
1394 SetLastErrorByStatus ( Status );
1395 return FALSE;
1396 }
1397
1398 return TRUE;
1399 }
1400
1401
1402 /*--------------------------------------------------------------
1403 * GetConsoleScreenBufferInfo
1404 *
1405 * @implemented
1406 */
1407 BOOL
1408 STDCALL
1409 GetConsoleScreenBufferInfo(
1410 HANDLE hConsoleOutput,
1411 PCONSOLE_SCREEN_BUFFER_INFO lpConsoleScreenBufferInfo
1412 )
1413 {
1414 CSR_API_MESSAGE Request; ULONG CsrRequest;
1415
1416 NTSTATUS Status;
1417
1418 CsrRequest = MAKE_CSR_API(SCREEN_BUFFER_INFO, CSR_CONSOLE);
1419 Request.Data.ScreenBufferInfoRequest.ConsoleHandle = hConsoleOutput;
1420 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
1421 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
1422 {
1423 SetLastErrorByStatus ( Status );
1424 return FALSE;
1425 }
1426 *lpConsoleScreenBufferInfo = Request.Data.ScreenBufferInfoRequest.Info;
1427 return TRUE;
1428 }
1429
1430
1431 /*--------------------------------------------------------------
1432 * SetConsoleCursorPosition
1433 *
1434 * @implemented
1435 */
1436 BOOL
1437 STDCALL
1438 SetConsoleCursorPosition(
1439 HANDLE hConsoleOutput,
1440 COORD dwCursorPosition
1441 )
1442 {
1443 CSR_API_MESSAGE Request; ULONG CsrRequest;
1444
1445 NTSTATUS Status;
1446
1447 CsrRequest = MAKE_CSR_API(SET_CURSOR, CSR_CONSOLE);
1448 Request.Data.SetCursorRequest.ConsoleHandle = hConsoleOutput;
1449 Request.Data.SetCursorRequest.Position = dwCursorPosition;
1450 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
1451 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
1452 {
1453 SetLastErrorByStatus ( Status );
1454 return FALSE;
1455 }
1456 return TRUE;
1457 }
1458
1459
1460 static BOOL
1461 IntFillConsoleOutputCharacter(HANDLE hConsoleOutput,
1462 PVOID cCharacter,
1463 DWORD nLength,
1464 COORD dwWriteCoord,
1465 LPDWORD lpNumberOfCharsWritten,
1466 BOOL bUnicode)
1467 {
1468 CSR_API_MESSAGE Request; ULONG CsrRequest;
1469
1470 NTSTATUS Status;
1471
1472 CsrRequest = MAKE_CSR_API(FILL_OUTPUT, CSR_CONSOLE);
1473 Request.Data.FillOutputRequest.ConsoleHandle = hConsoleOutput;
1474 Request.Data.FillOutputRequest.Unicode = bUnicode;
1475 if(bUnicode)
1476 Request.Data.FillOutputRequest.Char.UnicodeChar = *((WCHAR*)cCharacter);
1477 else
1478 Request.Data.FillOutputRequest.Char.AsciiChar = *((CHAR*)cCharacter);
1479 Request.Data.FillOutputRequest.Position = dwWriteCoord;
1480 Request.Data.FillOutputRequest.Length = nLength;
1481 Status = CsrClientCallServer(&Request, NULL,
1482 CsrRequest,
1483 sizeof(CSR_API_MESSAGE));
1484
1485 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
1486 {
1487 SetLastErrorByStatus(Status);
1488 return FALSE;
1489 }
1490
1491 if(lpNumberOfCharsWritten != NULL)
1492 {
1493 *lpNumberOfCharsWritten = Request.Data.FillOutputRequest.NrCharactersWritten;
1494 }
1495
1496 return TRUE;
1497 }
1498
1499 /*--------------------------------------------------------------
1500 * FillConsoleOutputCharacterA
1501 *
1502 * @implemented
1503 */
1504 BOOL STDCALL
1505 FillConsoleOutputCharacterA(
1506 HANDLE hConsoleOutput,
1507 CHAR cCharacter,
1508 DWORD nLength,
1509 COORD dwWriteCoord,
1510 LPDWORD lpNumberOfCharsWritten
1511 )
1512 {
1513 return IntFillConsoleOutputCharacter(hConsoleOutput,
1514 &cCharacter,
1515 nLength,
1516 dwWriteCoord,
1517 lpNumberOfCharsWritten,
1518 FALSE);
1519 }
1520
1521
1522 /*--------------------------------------------------------------
1523 * FillConsoleOutputCharacterW
1524 *
1525 * @implemented
1526 */
1527 BOOL
1528 STDCALL
1529 FillConsoleOutputCharacterW(
1530 HANDLE hConsoleOutput,
1531 WCHAR cCharacter,
1532 DWORD nLength,
1533 COORD dwWriteCoord,
1534 LPDWORD lpNumberOfCharsWritten
1535 )
1536 {
1537 return IntFillConsoleOutputCharacter(hConsoleOutput,
1538 &cCharacter,
1539 nLength,
1540 dwWriteCoord,
1541 lpNumberOfCharsWritten,
1542 TRUE);
1543 }
1544
1545
1546 static BOOL
1547 IntPeekConsoleInput(HANDLE hConsoleInput,
1548 PINPUT_RECORD lpBuffer,
1549 DWORD nLength,
1550 LPDWORD lpNumberOfEventsRead,
1551 BOOL bUnicode)
1552 {
1553 CSR_API_MESSAGE Request; ULONG CsrRequest;
1554 PCSR_CAPTURE_BUFFER CaptureBuffer;
1555 NTSTATUS Status;
1556 ULONG Size;
1557
1558 if(lpBuffer == NULL)
1559 {
1560 SetLastError(ERROR_INVALID_PARAMETER);
1561 return FALSE;
1562 }
1563
1564 Size = nLength * sizeof(INPUT_RECORD);
1565
1566 /* Allocate a Capture Buffer */
1567 DPRINT("IntPeekConsoleInput: %lx %p\n", Size, lpNumberOfEventsRead);
1568 CaptureBuffer = CsrAllocateCaptureBuffer(1, Size);
1569
1570 /* Allocate space in the Buffer */
1571 CsrCaptureMessageBuffer(CaptureBuffer,
1572 NULL,
1573 Size,
1574 (PVOID*)&Request.Data.PeekConsoleInputRequest.InputRecord);
1575
1576 /* Set up the data to send to the Console Server */
1577 CsrRequest = MAKE_CSR_API(PEEK_CONSOLE_INPUT, CSR_CONSOLE);
1578 Request.Data.PeekConsoleInputRequest.ConsoleHandle = hConsoleInput;
1579 Request.Data.PeekConsoleInputRequest.Unicode = bUnicode;
1580 Request.Data.PeekConsoleInputRequest.Length = nLength;
1581
1582 /* Call the server */
1583 Status = CsrClientCallServer(&Request,
1584 CaptureBuffer,
1585 CsrRequest,
1586 sizeof(CSR_API_MESSAGE));
1587 DPRINT("Server returned: %x\n", Request.Status);
1588
1589 /* Check for success*/
1590 if (NT_SUCCESS(Request.Status))
1591 {
1592 /* Return the number of events read */
1593 DPRINT("Events read: %lx\n", Request.Data.PeekConsoleInputRequest.Length);
1594 *lpNumberOfEventsRead = Request.Data.PeekConsoleInputRequest.Length;
1595
1596 /* Copy into the buffer */
1597 DPRINT("Copying to buffer\n");
1598 RtlCopyMemory(lpBuffer,
1599 Request.Data.PeekConsoleInputRequest.InputRecord,
1600 sizeof(INPUT_RECORD) * *lpNumberOfEventsRead);
1601 }
1602 else
1603 {
1604 /* Error out */
1605 *lpNumberOfEventsRead = 0;
1606 SetLastErrorByStatus(Request.Status);
1607 }
1608
1609 /* Release the capture buffer */
1610 CsrFreeCaptureBuffer(CaptureBuffer);
1611
1612 /* Return TRUE or FALSE */
1613 return NT_SUCCESS(Request.Status);
1614 }
1615
1616 /*--------------------------------------------------------------
1617 * PeekConsoleInputA
1618 *
1619 * @implemented
1620 */
1621 BOOL
1622 WINAPI
1623 PeekConsoleInputA(
1624 HANDLE hConsoleInput,
1625 PINPUT_RECORD lpBuffer,
1626 DWORD nLength,
1627 LPDWORD lpNumberOfEventsRead
1628 )
1629 {
1630 return IntPeekConsoleInput(hConsoleInput, lpBuffer, nLength,
1631 lpNumberOfEventsRead, FALSE);
1632 }
1633
1634
1635 /*--------------------------------------------------------------
1636 * PeekConsoleInputW
1637 *
1638 * @implemented
1639 */
1640 BOOL
1641 WINAPI
1642 PeekConsoleInputW(
1643 HANDLE hConsoleInput,
1644 PINPUT_RECORD lpBuffer,
1645 DWORD nLength,
1646 LPDWORD lpNumberOfEventsRead
1647 )
1648 {
1649 return IntPeekConsoleInput(hConsoleInput, lpBuffer, nLength,
1650 lpNumberOfEventsRead, TRUE);
1651 }
1652
1653
1654 static BOOL
1655 IntReadConsoleInput(HANDLE hConsoleInput,
1656 PINPUT_RECORD lpBuffer,
1657 DWORD nLength,
1658 LPDWORD lpNumberOfEventsRead,
1659 BOOL bUnicode)
1660 {
1661 CSR_API_MESSAGE Request; ULONG CsrRequest;
1662
1663 ULONG Read;
1664 NTSTATUS Status;
1665
1666 CsrRequest = MAKE_CSR_API(READ_INPUT, CSR_CONSOLE);
1667 Read = 0;
1668 while(nLength > 0)
1669 {
1670 Request.Data.ReadInputRequest.ConsoleHandle = hConsoleInput;
1671 Request.Data.ReadInputRequest.Unicode = bUnicode;
1672 Status = CsrClientCallServer(&Request, NULL,
1673 CsrRequest,
1674 sizeof(CSR_API_MESSAGE));
1675 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
1676 {
1677 if(Read == 0)
1678 {
1679 /* we couldn't read a single record, fail */
1680 SetLastErrorByStatus(Status);
1681 return FALSE;
1682 }
1683 else
1684 {
1685 /* FIXME - fail gracefully in case we already read at least one record? */
1686 break;
1687 }
1688 }
1689 else if(Status == STATUS_PENDING)
1690 {
1691 if(Read == 0)
1692 {
1693 Status = NtWaitForSingleObject(Request.Data.ReadInputRequest.Event, FALSE, 0);
1694 if(!NT_SUCCESS(Status))
1695 {
1696 SetLastErrorByStatus(Status);
1697 break;
1698 }
1699 }
1700 else
1701 {
1702 /* nothing more to read (waiting for more input??), let's just bail */
1703 break;
1704 }
1705 }
1706 else
1707 {
1708 lpBuffer[Read++] = Request.Data.ReadInputRequest.Input;
1709 nLength--;
1710
1711 if(!Request.Data.ReadInputRequest.MoreEvents)
1712 {
1713 /* nothing more to read, bail */
1714 break;
1715 }
1716 }
1717 }
1718
1719 if(lpNumberOfEventsRead != NULL)
1720 {
1721 *lpNumberOfEventsRead = Read;
1722 }
1723
1724 return (Read > 0);
1725 }
1726
1727
1728 /*--------------------------------------------------------------
1729 * ReadConsoleInputA
1730 *
1731 * @implemented
1732 */
1733 BOOL WINAPI
1734 ReadConsoleInputA(HANDLE hConsoleInput,
1735 PINPUT_RECORD lpBuffer,
1736 DWORD nLength,
1737 LPDWORD lpNumberOfEventsRead)
1738 {
1739 return IntReadConsoleInput(hConsoleInput, lpBuffer, nLength,
1740 lpNumberOfEventsRead, FALSE);
1741 }
1742
1743
1744 /*--------------------------------------------------------------
1745 * ReadConsoleInputW
1746 *
1747 * @implemented
1748 */
1749 BOOL
1750 WINAPI
1751 ReadConsoleInputW(
1752 HANDLE hConsoleInput,
1753 PINPUT_RECORD lpBuffer,
1754 DWORD nLength,
1755 LPDWORD lpNumberOfEventsRead
1756 )
1757 {
1758 return IntReadConsoleInput(hConsoleInput, lpBuffer, nLength,
1759 lpNumberOfEventsRead, TRUE);
1760 }
1761
1762
1763 static BOOL
1764 IntWriteConsoleInput(HANDLE hConsoleInput,
1765 PINPUT_RECORD lpBuffer,
1766 DWORD nLength,
1767 LPDWORD lpNumberOfEventsWritten,
1768 BOOL bUnicode)
1769 {
1770 CSR_API_MESSAGE Request; ULONG CsrRequest;
1771 PCSR_CAPTURE_BUFFER CaptureBuffer;
1772 NTSTATUS Status;
1773 DWORD Size;
1774
1775 if(lpBuffer == NULL)
1776 {
1777 SetLastError(ERROR_INVALID_PARAMETER);
1778 return FALSE;
1779 }
1780
1781 Size = nLength * sizeof(INPUT_RECORD);
1782
1783 /* Allocate a Capture Buffer */
1784 DPRINT("IntWriteConsoleInput: %lx %p\n", Size, lpNumberOfEventsWritten);
1785 CaptureBuffer = CsrAllocateCaptureBuffer(1, Size);
1786
1787 /* Allocate space in the Buffer */
1788 CsrCaptureMessageBuffer(CaptureBuffer,
1789 NULL,
1790 Size,
1791 (PVOID*)&Request.Data.WriteConsoleInputRequest.InputRecord);
1792
1793 /* Set up the data to send to the Console Server */
1794 CsrRequest = MAKE_CSR_API(WRITE_CONSOLE_INPUT, CSR_CONSOLE);
1795 Request.Data.WriteConsoleInputRequest.ConsoleHandle = hConsoleInput;
1796 Request.Data.WriteConsoleInputRequest.Unicode = bUnicode;
1797 Request.Data.WriteConsoleInputRequest.Length = nLength;
1798
1799 /* Call the server */
1800 Status = CsrClientCallServer(&Request,
1801 CaptureBuffer,
1802 CsrRequest,
1803 sizeof(CSR_API_MESSAGE));
1804 DPRINT("Server returned: %x\n", Request.Status);
1805
1806 /* Check for success*/
1807 if (NT_SUCCESS(Request.Status))
1808 {
1809 /* Return the number of events read */
1810 DPRINT("Events read: %lx\n", Request.Data.WriteConsoleInputRequest.Length);
1811 *lpNumberOfEventsWritten = Request.Data.WriteConsoleInputRequest.Length;
1812
1813 /* Copy into the buffer */
1814 DPRINT("Copying to buffer\n");
1815 RtlCopyMemory(lpBuffer,
1816 Request.Data.WriteConsoleInputRequest.InputRecord,
1817 sizeof(INPUT_RECORD) * *lpNumberOfEventsWritten);
1818 }
1819 else
1820 {
1821 /* Error out */
1822 *lpNumberOfEventsWritten = 0;
1823 SetLastErrorByStatus(Request.Status);
1824 }
1825
1826 /* Release the capture buffer */
1827 CsrFreeCaptureBuffer(CaptureBuffer);
1828
1829 /* Return TRUE or FALSE */
1830 return NT_SUCCESS(Request.Status);
1831 }
1832
1833
1834 /*--------------------------------------------------------------
1835 * WriteConsoleInputA
1836 *
1837 * @implemented
1838 */
1839 BOOL
1840 WINAPI
1841 WriteConsoleInputA(
1842 HANDLE hConsoleInput,
1843 CONST INPUT_RECORD *lpBuffer,
1844 DWORD nLength,
1845 LPDWORD lpNumberOfEventsWritten
1846 )
1847 {
1848 return IntWriteConsoleInput(hConsoleInput,
1849 (PINPUT_RECORD)lpBuffer,
1850 nLength,
1851 lpNumberOfEventsWritten,
1852 FALSE);
1853 }
1854
1855
1856 /*--------------------------------------------------------------
1857 * WriteConsoleInputW
1858 *
1859 * @implemented
1860 */
1861 BOOL
1862 WINAPI
1863 WriteConsoleInputW(
1864 HANDLE hConsoleInput,
1865 CONST INPUT_RECORD *lpBuffer,
1866 DWORD nLength,
1867 LPDWORD lpNumberOfEventsWritten
1868 )
1869 {
1870 return IntWriteConsoleInput(hConsoleInput,
1871 (PINPUT_RECORD)lpBuffer,
1872 nLength,
1873 lpNumberOfEventsWritten,
1874 TRUE);
1875 }
1876
1877
1878 static BOOL
1879 IntReadConsoleOutput(HANDLE hConsoleOutput,
1880 PCHAR_INFO lpBuffer,
1881 COORD dwBufferSize,
1882 COORD dwBufferCoord,
1883 PSMALL_RECT lpReadRegion,
1884 BOOL bUnicode)
1885 {
1886 CSR_API_MESSAGE Request; ULONG CsrRequest;
1887 PCSR_CAPTURE_BUFFER CaptureBuffer;
1888 NTSTATUS Status;
1889 DWORD Size, SizeX, SizeY;
1890
1891 if(lpBuffer == NULL)
1892 {
1893 SetLastError(ERROR_INVALID_PARAMETER);
1894 return FALSE;
1895 }
1896
1897 Size = dwBufferSize.X * dwBufferSize.Y * sizeof(CHAR_INFO);
1898
1899 /* Allocate a Capture Buffer */
1900 DPRINT("IntReadConsoleOutput: %lx %p\n", Size, lpReadRegion);
1901 CaptureBuffer = CsrAllocateCaptureBuffer(1, Size);
1902
1903 /* Allocate space in the Buffer */
1904 CsrCaptureMessageBuffer(CaptureBuffer,
1905 NULL,
1906 Size,
1907 (PVOID*)&Request.Data.ReadConsoleOutputRequest.CharInfo);
1908
1909 /* Set up the data to send to the Console Server */
1910 CsrRequest = MAKE_CSR_API(READ_CONSOLE_OUTPUT, CSR_CONSOLE);
1911 Request.Data.ReadConsoleOutputRequest.ConsoleHandle = hConsoleOutput;
1912 Request.Data.ReadConsoleOutputRequest.Unicode = bUnicode;
1913 Request.Data.ReadConsoleOutputRequest.BufferSize = dwBufferSize;
1914 Request.Data.ReadConsoleOutputRequest.BufferCoord = dwBufferCoord;
1915 Request.Data.ReadConsoleOutputRequest.ReadRegion = *lpReadRegion;
1916
1917 /* Call the server */
1918 Status = CsrClientCallServer(&Request,
1919 CaptureBuffer,
1920 CsrRequest,
1921 sizeof(CSR_API_MESSAGE));
1922 DPRINT("Server returned: %x\n", Request.Status);
1923
1924 /* Check for success*/
1925 if (NT_SUCCESS(Request.Status))
1926 {
1927 /* Copy into the buffer */
1928 DPRINT("Copying to buffer\n");
1929 SizeX = Request.Data.ReadConsoleOutputRequest.ReadRegion.Right -
1930 Request.Data.ReadConsoleOutputRequest.ReadRegion.Left + 1;
1931 SizeY = Request.Data.ReadConsoleOutputRequest.ReadRegion.Bottom -
1932 Request.Data.ReadConsoleOutputRequest.ReadRegion.Top + 1;
1933 RtlCopyMemory(lpBuffer,
1934 Request.Data.ReadConsoleOutputRequest.CharInfo,
1935 sizeof(CHAR_INFO) * SizeX * SizeY);
1936 }
1937 else
1938 {
1939 /* Error out */
1940 SetLastErrorByStatus(Request.Status);
1941 }
1942
1943 /* Return the read region */
1944 DPRINT("read region: %lx\n", Request.Data.ReadConsoleOutputRequest.ReadRegion);
1945 *lpReadRegion = Request.Data.ReadConsoleOutputRequest.ReadRegion;
1946
1947 /* Release the capture buffer */
1948 CsrFreeCaptureBuffer(CaptureBuffer);
1949
1950 /* Return TRUE or FALSE */
1951 return NT_SUCCESS(Request.Status);
1952 }
1953
1954 /*--------------------------------------------------------------
1955 * ReadConsoleOutputA
1956 *
1957 * @implemented
1958 */
1959 BOOL
1960 WINAPI
1961 ReadConsoleOutputA(
1962 HANDLE hConsoleOutput,
1963 PCHAR_INFO lpBuffer,
1964 COORD dwBufferSize,
1965 COORD dwBufferCoord,
1966 PSMALL_RECT lpReadRegion
1967 )
1968 {
1969 return IntReadConsoleOutput(hConsoleOutput, lpBuffer, dwBufferSize,
1970 dwBufferCoord, lpReadRegion, FALSE);
1971 }
1972
1973
1974 /*--------------------------------------------------------------
1975 * ReadConsoleOutputW
1976 *
1977 * @implemented
1978 */
1979 BOOL
1980 WINAPI
1981 ReadConsoleOutputW(
1982 HANDLE hConsoleOutput,
1983 PCHAR_INFO lpBuffer,
1984 COORD dwBufferSize,
1985 COORD dwBufferCoord,
1986 PSMALL_RECT lpReadRegion
1987 )
1988 {
1989 return IntReadConsoleOutput(hConsoleOutput, lpBuffer, dwBufferSize,
1990 dwBufferCoord, lpReadRegion, TRUE);
1991 }
1992
1993
1994 static BOOL
1995 IntWriteConsoleOutput(HANDLE hConsoleOutput,
1996 CONST CHAR_INFO *lpBuffer,
1997 COORD dwBufferSize,
1998 COORD dwBufferCoord,
1999 PSMALL_RECT lpWriteRegion,
2000 BOOL bUnicode)
2001 {
2002 CSR_API_MESSAGE Request; ULONG CsrRequest;
2003 PCSR_CAPTURE_BUFFER CaptureBuffer;
2004 NTSTATUS Status;
2005 ULONG Size;
2006
2007 Size = dwBufferSize.Y * dwBufferSize.X * sizeof(CHAR_INFO);
2008
2009 /* Allocate a Capture Buffer */
2010 DPRINT("IntWriteConsoleOutput: %lx %p\n", Size, lpWriteRegion);
2011 CaptureBuffer = CsrAllocateCaptureBuffer(1, Size);
2012
2013 /* Allocate space in the Buffer */
2014 CsrCaptureMessageBuffer(CaptureBuffer,
2015 NULL,
2016 Size,
2017 (PVOID*)&Request.Data.WriteConsoleOutputRequest.CharInfo);
2018
2019 /* Copy from the buffer */
2020 RtlCopyMemory(Request.Data.WriteConsoleOutputRequest.CharInfo, lpBuffer, Size);
2021
2022 /* Set up the data to send to the Console Server */
2023 CsrRequest = MAKE_CSR_API(WRITE_CONSOLE_OUTPUT, CSR_CONSOLE);
2024 Request.Data.WriteConsoleOutputRequest.ConsoleHandle = hConsoleOutput;
2025 Request.Data.WriteConsoleOutputRequest.Unicode = bUnicode;
2026 Request.Data.WriteConsoleOutputRequest.BufferSize = dwBufferSize;
2027 Request.Data.WriteConsoleOutputRequest.BufferCoord = dwBufferCoord;
2028 Request.Data.WriteConsoleOutputRequest.WriteRegion = *lpWriteRegion;
2029
2030 /* Call the server */
2031 Status = CsrClientCallServer(&Request,
2032 CaptureBuffer,
2033 CsrRequest,
2034 sizeof(CSR_API_MESSAGE));
2035 DPRINT("Server returned: %x\n", Request.Status);
2036
2037 /* Check for success*/
2038 if (!NT_SUCCESS(Request.Status))
2039 {
2040 /* Error out */
2041 SetLastErrorByStatus(Request.Status);
2042 }
2043
2044 /* Return the read region */
2045 DPRINT("read region: %lx\n", Request.Data.WriteConsoleOutputRequest.WriteRegion);
2046 *lpWriteRegion = Request.Data.WriteConsoleOutputRequest.WriteRegion;
2047
2048 /* Release the capture buffer */
2049 CsrFreeCaptureBuffer(CaptureBuffer);
2050
2051 /* Return TRUE or FALSE */
2052 return NT_SUCCESS(Request.Status);
2053 }
2054
2055 /*--------------------------------------------------------------
2056 * WriteConsoleOutputA
2057 *
2058 * @implemented
2059 */
2060 BOOL WINAPI
2061 WriteConsoleOutputA(HANDLE hConsoleOutput,
2062 CONST CHAR_INFO *lpBuffer,
2063 COORD dwBufferSize,
2064 COORD dwBufferCoord,
2065 PSMALL_RECT lpWriteRegion)
2066 {
2067 return IntWriteConsoleOutput(hConsoleOutput, lpBuffer, dwBufferSize,
2068 dwBufferCoord, lpWriteRegion, FALSE);
2069 }
2070
2071
2072 /*--------------------------------------------------------------
2073 * WriteConsoleOutputW
2074 *
2075 * @implemented
2076 */
2077 BOOL
2078 WINAPI
2079 WriteConsoleOutputW(
2080 HANDLE hConsoleOutput,
2081 CONST CHAR_INFO *lpBuffer,
2082 COORD dwBufferSize,
2083 COORD dwBufferCoord,
2084 PSMALL_RECT lpWriteRegion
2085 )
2086 {
2087 return IntWriteConsoleOutput(hConsoleOutput, lpBuffer, dwBufferSize,
2088 dwBufferCoord, lpWriteRegion, TRUE);
2089 }
2090
2091
2092 static BOOL
2093 IntReadConsoleOutputCharacter(HANDLE hConsoleOutput,
2094 PVOID lpCharacter,
2095 DWORD nLength,
2096 COORD dwReadCoord,
2097 LPDWORD lpNumberOfCharsRead,
2098 BOOL bUnicode)
2099 {
2100 PCSR_API_MESSAGE Request; ULONG CsrRequest;
2101 NTSTATUS Status;
2102 ULONG nChars, SizeBytes, CharSize;
2103 DWORD CharsRead = 0;
2104
2105 CharSize = (bUnicode ? sizeof(WCHAR) : sizeof(CHAR));
2106
2107 nChars = min(nLength, CSRSS_MAX_READ_CONSOLE_OUTPUT_CHAR) / CharSize;
2108 SizeBytes = nChars * CharSize;
2109
2110 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
2111 max(sizeof(CSR_API_MESSAGE),
2112 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE_OUTPUT_CHAR)
2113 + min (nChars, CSRSS_MAX_READ_CONSOLE_OUTPUT_CHAR / CharSize) * CharSize));
2114 if (Request == NULL)
2115 {
2116 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
2117 return FALSE;
2118 }
2119
2120 CsrRequest = MAKE_CSR_API(READ_CONSOLE_OUTPUT_CHAR, CSR_CONSOLE);
2121 Request->Data.ReadConsoleOutputCharRequest.ReadCoord = dwReadCoord;
2122
2123 while(nLength > 0)
2124 {
2125 DWORD BytesRead;
2126
2127 Request->Data.ReadConsoleOutputCharRequest.ConsoleHandle = hConsoleOutput;
2128 Request->Data.ReadConsoleOutputCharRequest.Unicode = bUnicode;
2129 Request->Data.ReadConsoleOutputCharRequest.NumCharsToRead = min(nLength, nChars);
2130 SizeBytes = Request->Data.ReadConsoleOutputCharRequest.NumCharsToRead * CharSize;
2131
2132 Status = CsrClientCallServer(Request,
2133 NULL,
2134 CsrRequest,
2135 max (sizeof(CSR_API_MESSAGE),
2136 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE_OUTPUT_CHAR) + SizeBytes));
2137 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Request->Status))
2138 {
2139 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2140 SetLastErrorByStatus(Status);
2141 break;
2142 }
2143
2144 BytesRead = Request->Data.ReadConsoleOutputCharRequest.CharsRead * CharSize;
2145 memcpy(lpCharacter, Request->Data.ReadConsoleOutputCharRequest.String, BytesRead);
2146 lpCharacter = (PVOID)((ULONG_PTR)lpCharacter + (ULONG_PTR)BytesRead);
2147 CharsRead += Request->Data.ReadConsoleOutputCharRequest.CharsRead;
2148 nLength -= Request->Data.ReadConsoleOutputCharRequest.CharsRead;
2149
2150 Request->Data.ReadConsoleOutputCharRequest.ReadCoord = Request->Data.ReadConsoleOutputCharRequest.EndCoord;
2151 }
2152
2153 if(lpNumberOfCharsRead != NULL)
2154 {
2155 *lpNumberOfCharsRead = CharsRead;
2156 }
2157
2158 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2159
2160 return TRUE;
2161 }
2162
2163
2164 /*--------------------------------------------------------------
2165 * ReadConsoleOutputCharacterA
2166 *
2167 * @implemented
2168 */
2169 BOOL
2170 WINAPI
2171 ReadConsoleOutputCharacterA(
2172 HANDLE hConsoleOutput,
2173 LPSTR lpCharacter,
2174 DWORD nLength,
2175 COORD dwReadCoord,
2176 LPDWORD lpNumberOfCharsRead
2177 )
2178 {
2179 return IntReadConsoleOutputCharacter(hConsoleOutput,
2180 (PVOID)lpCharacter,
2181 nLength,
2182 dwReadCoord,
2183 lpNumberOfCharsRead,
2184 FALSE);
2185 }
2186
2187
2188 /*--------------------------------------------------------------
2189 * ReadConsoleOutputCharacterW
2190 *
2191 * @implemented
2192 */
2193 BOOL
2194 WINAPI
2195 ReadConsoleOutputCharacterW(
2196 HANDLE hConsoleOutput,
2197 LPWSTR lpCharacter,
2198 DWORD nLength,
2199 COORD dwReadCoord,
2200 LPDWORD lpNumberOfCharsRead
2201 )
2202 {
2203 return IntReadConsoleOutputCharacter(hConsoleOutput,
2204 (PVOID)lpCharacter,
2205 nLength,
2206 dwReadCoord,
2207 lpNumberOfCharsRead,
2208 TRUE);
2209 }
2210
2211
2212 /*--------------------------------------------------------------
2213 * ReadConsoleOutputAttribute
2214 *
2215 * @implemented
2216 */
2217 BOOL
2218 WINAPI
2219 ReadConsoleOutputAttribute(
2220 HANDLE hConsoleOutput,
2221 LPWORD lpAttribute,
2222 DWORD nLength,
2223 COORD dwReadCoord,
2224 LPDWORD lpNumberOfAttrsRead
2225 )
2226 {
2227 PCSR_API_MESSAGE Request; ULONG CsrRequest;
2228 NTSTATUS Status;
2229 DWORD Size;
2230
2231 if (lpNumberOfAttrsRead != NULL)
2232 *lpNumberOfAttrsRead = nLength;
2233
2234 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
2235 max(sizeof(CSR_API_MESSAGE),
2236 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE_OUTPUT_ATTRIB)
2237 + min (nLength, CSRSS_MAX_READ_CONSOLE_OUTPUT_ATTRIB / sizeof(WORD)) * sizeof(WORD)));
2238 if (Request == NULL)
2239 {
2240 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
2241 return FALSE;
2242 }
2243
2244 CsrRequest = MAKE_CSR_API(READ_CONSOLE_OUTPUT_ATTRIB, CSR_CONSOLE);
2245
2246 while (nLength != 0)
2247 {
2248 Request->Data.ReadConsoleOutputAttribRequest.ConsoleHandle = hConsoleOutput;
2249 Request->Data.ReadConsoleOutputAttribRequest.ReadCoord = dwReadCoord;
2250
2251 if (nLength > CSRSS_MAX_READ_CONSOLE_OUTPUT_ATTRIB / sizeof(WORD))
2252 Size = CSRSS_MAX_READ_CONSOLE_OUTPUT_ATTRIB / sizeof(WCHAR);
2253 else
2254 Size = nLength;
2255
2256 Request->Data.ReadConsoleOutputAttribRequest.NumAttrsToRead = Size;
2257
2258 Status = CsrClientCallServer(Request,
2259 NULL,
2260 CsrRequest,
2261 max (sizeof(CSR_API_MESSAGE),
2262 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE_OUTPUT_ATTRIB) + Size * sizeof(WORD)));
2263 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Request->Status))
2264 {
2265 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2266 SetLastErrorByStatus(Status);
2267 return(FALSE);
2268 }
2269
2270 memcpy(lpAttribute, Request->Data.ReadConsoleOutputAttribRequest.Attribute, Size * sizeof(WORD));
2271 lpAttribute += Size;
2272 nLength -= Size;
2273 Request->Data.ReadConsoleOutputAttribRequest.ReadCoord = Request->Data.ReadConsoleOutputAttribRequest.EndCoord;
2274 }
2275
2276 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2277
2278 return(TRUE);
2279 }
2280
2281
2282 static BOOL
2283 IntWriteConsoleOutputCharacter(HANDLE hConsoleOutput,
2284 PVOID lpCharacter,
2285 DWORD nLength,
2286 COORD dwWriteCoord,
2287 LPDWORD lpNumberOfCharsWritten,
2288 BOOL bUnicode)
2289 {
2290 PCSR_API_MESSAGE Request; ULONG CsrRequest;
2291 NTSTATUS Status;
2292 ULONG SizeBytes, CharSize, nChars;
2293 DWORD Written = 0;
2294
2295 CharSize = (bUnicode ? sizeof(WCHAR) : sizeof(CHAR));
2296
2297 nChars = min(nLength, CSRSS_MAX_WRITE_CONSOLE_OUTPUT_CHAR / CharSize);
2298 SizeBytes = nChars * CharSize;
2299
2300 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
2301 max (sizeof(CSR_API_MESSAGE),
2302 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_WRITE_CONSOLE_OUTPUT_CHAR)
2303 + min (nChars, CSRSS_MAX_WRITE_CONSOLE_OUTPUT_CHAR / CharSize) * CharSize));
2304 if (Request == NULL)
2305 {
2306 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
2307 return FALSE;
2308 }
2309
2310 CsrRequest = MAKE_CSR_API(WRITE_CONSOLE_OUTPUT_CHAR, CSR_CONSOLE);
2311 Request->Data.WriteConsoleOutputCharRequest.Coord = dwWriteCoord;
2312
2313 while(nLength > 0)
2314 {
2315 DWORD BytesWrite;
2316
2317 Request->Data.WriteConsoleOutputCharRequest.ConsoleHandle = hConsoleOutput;
2318 Request->Data.WriteConsoleOutputCharRequest.Unicode = bUnicode;
2319 Request->Data.WriteConsoleOutputCharRequest.Length = min(nLength, nChars);
2320 BytesWrite = Request->Data.WriteConsoleOutputCharRequest.Length * CharSize;
2321
2322 memcpy(Request->Data.WriteConsoleOutputCharRequest.String, lpCharacter, BytesWrite);
2323
2324 Status = CsrClientCallServer(Request,
2325 NULL,
2326 CsrRequest,
2327 max (sizeof(CSR_API_MESSAGE),
2328 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_WRITE_CONSOLE_OUTPUT_CHAR) + BytesWrite));
2329
2330 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request->Status))
2331 {
2332 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2333 SetLastErrorByStatus(Status);
2334 return FALSE;
2335 }
2336
2337 nLength -= Request->Data.WriteConsoleOutputCharRequest.NrCharactersWritten;
2338 lpCharacter = (PVOID)((ULONG_PTR)lpCharacter + (ULONG_PTR)(Request->Data.WriteConsoleOutputCharRequest.NrCharactersWritten * CharSize));
2339 Written += Request->Data.WriteConsoleOutputCharRequest.NrCharactersWritten;
2340
2341 Request->Data.WriteConsoleOutputCharRequest.Coord = Request->Data.WriteConsoleOutputCharRequest.EndCoord;
2342 }
2343
2344 if(lpNumberOfCharsWritten != NULL)
2345 {
2346 *lpNumberOfCharsWritten = Written;
2347 }
2348
2349 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2350
2351 return TRUE;
2352 }
2353
2354
2355 /*--------------------------------------------------------------
2356 * WriteConsoleOutputCharacterA
2357 *
2358 * @implemented
2359 */
2360 BOOL WINAPI
2361 WriteConsoleOutputCharacterA(HANDLE hConsoleOutput,
2362 LPCSTR lpCharacter,
2363 DWORD nLength,
2364 COORD dwWriteCoord,
2365 LPDWORD lpNumberOfCharsWritten)
2366 {
2367 return IntWriteConsoleOutputCharacter(hConsoleOutput,
2368 (PVOID)lpCharacter,
2369 nLength,
2370 dwWriteCoord,
2371 lpNumberOfCharsWritten,
2372 FALSE);
2373 }
2374
2375
2376 /*--------------------------------------------------------------
2377 * WriteConsoleOutputCharacterW
2378 *
2379 * @implemented
2380 */
2381 BOOL WINAPI
2382 WriteConsoleOutputCharacterW(HANDLE hConsoleOutput,
2383 LPCWSTR lpCharacter,
2384 DWORD nLength,
2385 COORD dwWriteCoord,
2386 LPDWORD lpNumberOfCharsWritten)
2387 {
2388 return IntWriteConsoleOutputCharacter(hConsoleOutput,
2389 (PVOID)lpCharacter,
2390 nLength,
2391 dwWriteCoord,
2392 lpNumberOfCharsWritten,
2393 TRUE);
2394 }
2395
2396
2397 /*--------------------------------------------------------------
2398 * WriteConsoleOutputAttribute
2399 *
2400 * @implemented
2401 */
2402 BOOL
2403 WINAPI
2404 WriteConsoleOutputAttribute(
2405 HANDLE hConsoleOutput,
2406 CONST WORD *lpAttribute,
2407 DWORD nLength,
2408 COORD dwWriteCoord,
2409 LPDWORD lpNumberOfAttrsWritten
2410 )
2411 {
2412 PCSR_API_MESSAGE Request; ULONG CsrRequest;
2413 NTSTATUS Status;
2414 WORD Size;
2415
2416 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
2417 max (sizeof(CSR_API_MESSAGE),
2418 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_WRITE_CONSOLE_OUTPUT_ATTRIB)
2419 + min(nLength, CSRSS_MAX_WRITE_CONSOLE_OUTPUT_ATTRIB / sizeof(WORD)) * sizeof(WORD)));
2420 if (Request == NULL)
2421 {
2422 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
2423 return FALSE;
2424 }
2425
2426 CsrRequest = MAKE_CSR_API(WRITE_CONSOLE_OUTPUT_ATTRIB, CSR_CONSOLE);
2427 Request->Data.WriteConsoleOutputAttribRequest.Coord = dwWriteCoord;
2428
2429 if( lpNumberOfAttrsWritten )
2430 *lpNumberOfAttrsWritten = nLength;
2431 while( nLength )
2432 {
2433 Size = min(nLength, CSRSS_MAX_WRITE_CONSOLE_OUTPUT_ATTRIB / sizeof(WORD));
2434 Request->Data.WriteConsoleOutputAttribRequest.ConsoleHandle = hConsoleOutput;
2435 Request->Data.WriteConsoleOutputAttribRequest.Length = Size;
2436 memcpy(Request->Data.WriteConsoleOutputAttribRequest.Attribute, lpAttribute, Size * sizeof(WORD));
2437
2438 Status = CsrClientCallServer( Request,
2439 NULL,
2440 CsrRequest,
2441 max (sizeof(CSR_API_MESSAGE),
2442 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_WRITE_CONSOLE_OUTPUT_ATTRIB) + Size * sizeof(WORD)));
2443
2444 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request->Status ) )
2445 {
2446 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2447 SetLastErrorByStatus ( Status );
2448 return FALSE;
2449 }
2450 nLength -= Size;
2451 lpAttribute += Size;
2452 Request->Data.WriteConsoleOutputAttribRequest.Coord = Request->Data.WriteConsoleOutputAttribRequest.EndCoord;
2453 }
2454
2455 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
2456
2457 return TRUE;
2458 }
2459
2460
2461 /*--------------------------------------------------------------
2462 * FillConsoleOutputAttribute
2463 *
2464 * @implemented
2465 */
2466 BOOL
2467 WINAPI
2468 FillConsoleOutputAttribute(
2469 HANDLE hConsoleOutput,
2470 WORD wAttribute,
2471 DWORD nLength,
2472 COORD dwWriteCoord,
2473 LPDWORD lpNumberOfAttrsWritten
2474 )
2475 {
2476 CSR_API_MESSAGE Request; ULONG CsrRequest;
2477
2478 NTSTATUS Status;
2479
2480 CsrRequest = MAKE_CSR_API(FILL_OUTPUT_ATTRIB, CSR_CONSOLE);
2481 Request.Data.FillOutputAttribRequest.ConsoleHandle = hConsoleOutput;
2482 Request.Data.FillOutputAttribRequest.Attribute = wAttribute;
2483 Request.Data.FillOutputAttribRequest.Coord = dwWriteCoord;
2484 Request.Data.FillOutputAttribRequest.Length = nLength;
2485 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2486 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2487 {
2488 SetLastErrorByStatus ( Status );
2489 return FALSE;
2490 }
2491 if( lpNumberOfAttrsWritten )
2492 *lpNumberOfAttrsWritten = nLength;
2493 return TRUE;
2494 }
2495
2496
2497 /*--------------------------------------------------------------
2498 * GetConsoleMode
2499 *
2500 * @implemented
2501 */
2502 BOOL
2503 WINAPI
2504 GetConsoleMode(
2505 HANDLE hConsoleHandle,
2506 LPDWORD lpMode
2507 )
2508 {
2509 CSR_API_MESSAGE Request; ULONG CsrRequest;
2510
2511 NTSTATUS Status;
2512
2513 CsrRequest = MAKE_CSR_API(GET_CONSOLE_MODE, CSR_CONSOLE);
2514 Request.Data.GetConsoleModeRequest.ConsoleHandle = hConsoleHandle;
2515 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2516 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2517 {
2518 SetLastErrorByStatus ( Status );
2519 return FALSE;
2520 }
2521 *lpMode = Request.Data.GetConsoleModeRequest.ConsoleMode;
2522 return TRUE;
2523 }
2524
2525
2526 /*--------------------------------------------------------------
2527 * GetNumberOfConsoleInputEvents
2528 *
2529 * @implemented
2530 */
2531 BOOL
2532 WINAPI
2533 GetNumberOfConsoleInputEvents(
2534 HANDLE hConsoleInput,
2535 LPDWORD lpNumberOfEvents
2536 )
2537 {
2538 CSR_API_MESSAGE Request; ULONG CsrRequest;
2539
2540 NTSTATUS Status;
2541
2542 if(lpNumberOfEvents == NULL)
2543 {
2544 SetLastError(ERROR_INVALID_PARAMETER);
2545 return FALSE;
2546 }
2547
2548 CsrRequest = MAKE_CSR_API(GET_NUM_INPUT_EVENTS, CSR_CONSOLE);
2549 Request.Data.GetNumInputEventsRequest.ConsoleHandle = hConsoleInput;
2550 Status = CsrClientCallServer(&Request, NULL, CsrRequest, sizeof(CSR_API_MESSAGE));
2551 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
2552 {
2553 SetLastErrorByStatus(Status);
2554 return FALSE;
2555 }
2556
2557 *lpNumberOfEvents = Request.Data.GetNumInputEventsRequest.NumInputEvents;
2558
2559 return TRUE;
2560 }
2561
2562
2563 /*--------------------------------------------------------------
2564 * GetLargestConsoleWindowSize
2565 *
2566 * @unimplemented
2567 */
2568 COORD
2569 WINAPI
2570 GetLargestConsoleWindowSize(
2571 HANDLE hConsoleOutput
2572 )
2573 {
2574 COORD Coord = {80,25};
2575 DPRINT1("GetLargestConsoleWindowSize(0x%x) UNIMPLEMENTED!\n", hConsoleOutput);
2576 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
2577 return Coord;
2578 }
2579
2580
2581 /*--------------------------------------------------------------
2582 * GetConsoleCursorInfo
2583 *
2584 * @implemented
2585 */
2586 BOOL
2587 WINAPI
2588 GetConsoleCursorInfo(
2589 HANDLE hConsoleOutput,
2590 PCONSOLE_CURSOR_INFO lpConsoleCursorInfo
2591 )
2592 {
2593 CSR_API_MESSAGE Request; ULONG CsrRequest;
2594
2595 NTSTATUS Status;
2596
2597 CsrRequest = MAKE_CSR_API(GET_CURSOR_INFO, CSR_CONSOLE);
2598 Request.Data.GetCursorInfoRequest.ConsoleHandle = hConsoleOutput;
2599 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2600
2601 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2602 {
2603 SetLastErrorByStatus ( Status );
2604 return FALSE;
2605 }
2606 *lpConsoleCursorInfo = Request.Data.GetCursorInfoRequest.Info;
2607 return TRUE;
2608 }
2609
2610
2611 /*--------------------------------------------------------------
2612 * GetNumberOfConsoleMouseButtons
2613 *
2614 * @unimplemented
2615 */
2616 BOOL
2617 WINAPI
2618 GetNumberOfConsoleMouseButtons(
2619 LPDWORD lpNumberOfMouseButtons
2620 )
2621 {
2622 DPRINT1("GetNumberOfConsoleMouseButtons(0x%x) UNIMPLEMENTED!\n", lpNumberOfMouseButtons);
2623 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
2624 return FALSE;
2625 }
2626
2627
2628 /*--------------------------------------------------------------
2629 * SetConsoleMode
2630 *
2631 * @implemented
2632 */
2633 BOOL
2634 WINAPI
2635 SetConsoleMode(
2636 HANDLE hConsoleHandle,
2637 DWORD dwMode
2638 )
2639 {
2640 CSR_API_MESSAGE Request; ULONG CsrRequest;
2641
2642 NTSTATUS Status;
2643
2644 if (!IsConsoleHandle (hConsoleHandle))
2645 {
2646 DPRINT("SetConsoleMode was called with a non console handle\n");
2647 SetLastError (ERROR_INVALID_PARAMETER);
2648 return FALSE;
2649 }
2650
2651
2652 CsrRequest = MAKE_CSR_API(SET_CONSOLE_MODE, CSR_CONSOLE);
2653 Request.Data.SetConsoleModeRequest.ConsoleHandle = hConsoleHandle;
2654 Request.Data.SetConsoleModeRequest.Mode = dwMode;
2655 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2656 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2657 {
2658 SetLastErrorByStatus ( Status );
2659 return FALSE;
2660 }
2661 return TRUE;
2662 }
2663
2664
2665 /*--------------------------------------------------------------
2666 * SetConsoleActiveScreenBuffer
2667 *
2668 * @implemented
2669 */
2670 BOOL
2671 WINAPI
2672 SetConsoleActiveScreenBuffer(
2673 HANDLE hConsoleOutput
2674 )
2675 {
2676 CSR_API_MESSAGE Request; ULONG CsrRequest;
2677
2678 NTSTATUS Status;
2679
2680 CsrRequest = MAKE_CSR_API(SET_SCREEN_BUFFER, CSR_CONSOLE);
2681 Request.Data.SetScreenBufferRequest.OutputHandle = hConsoleOutput;
2682 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2683 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2684 {
2685 SetLastErrorByStatus ( Status );
2686 return FALSE;
2687 }
2688 return TRUE;
2689 }
2690
2691
2692 /*--------------------------------------------------------------
2693 * FlushConsoleInputBuffer
2694 *
2695 * @implemented
2696 */
2697 BOOL
2698 WINAPI
2699 FlushConsoleInputBuffer(
2700 HANDLE hConsoleInput
2701 )
2702 {
2703 CSR_API_MESSAGE Request; ULONG CsrRequest;
2704
2705 NTSTATUS Status;
2706
2707 CsrRequest = MAKE_CSR_API(FLUSH_INPUT_BUFFER, CSR_CONSOLE);
2708 Request.Data.FlushInputBufferRequest.ConsoleInput = hConsoleInput;
2709 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2710 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2711 {
2712 SetLastErrorByStatus ( Status );
2713 return FALSE;
2714 }
2715 return TRUE;
2716 }
2717
2718
2719 /*--------------------------------------------------------------
2720 * SetConsoleScreenBufferSize
2721 *
2722 * @unimplemented
2723 */
2724 BOOL
2725 WINAPI
2726 SetConsoleScreenBufferSize(
2727 HANDLE hConsoleOutput,
2728 COORD dwSize
2729 )
2730 {
2731 DPRINT1("SetConsoleScreenBufferSize(0x%x, 0x%x) UNIMPLEMENTED!\n", hConsoleOutput, dwSize);
2732 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
2733 return FALSE;
2734 }
2735
2736 /*--------------------------------------------------------------
2737 * SetConsoleCursorInfo
2738 *
2739 * @implemented
2740 */
2741 BOOL
2742 WINAPI
2743 SetConsoleCursorInfo(
2744 HANDLE hConsoleOutput,
2745 CONST CONSOLE_CURSOR_INFO *lpConsoleCursorInfo
2746 )
2747 {
2748 CSR_API_MESSAGE Request; ULONG CsrRequest;
2749
2750 NTSTATUS Status;
2751
2752 CsrRequest = MAKE_CSR_API(SET_CURSOR_INFO, CSR_CONSOLE);
2753 Request.Data.SetCursorInfoRequest.ConsoleHandle = hConsoleOutput;
2754 Request.Data.SetCursorInfoRequest.Info = *lpConsoleCursorInfo;
2755 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2756
2757 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2758 {
2759 SetLastErrorByStatus ( Status );
2760 return FALSE;
2761 }
2762 return TRUE;
2763 }
2764
2765
2766 static BOOL
2767 IntScrollConsoleScreenBuffer(HANDLE hConsoleOutput,
2768 PSMALL_RECT lpScrollRectangle,
2769 PSMALL_RECT lpClipRectangle,
2770 COORD dwDestinationOrigin,
2771 PCHAR_INFO lpFill,
2772 BOOL bUnicode)
2773 {
2774 CSR_API_MESSAGE Request; ULONG CsrRequest;
2775
2776 NTSTATUS Status;
2777
2778 CsrRequest = MAKE_CSR_API(SCROLL_CONSOLE_SCREEN_BUFFER, CSR_CONSOLE);
2779 Request.Data.ScrollConsoleScreenBufferRequest.ConsoleHandle = hConsoleOutput;
2780 Request.Data.ScrollConsoleScreenBufferRequest.Unicode = bUnicode;
2781 Request.Data.ScrollConsoleScreenBufferRequest.ScrollRectangle = *lpScrollRectangle;
2782
2783 if(lpClipRectangle != NULL)
2784 {
2785 Request.Data.ScrollConsoleScreenBufferRequest.UseClipRectangle = TRUE;
2786 Request.Data.ScrollConsoleScreenBufferRequest.ClipRectangle = *lpClipRectangle;
2787 }
2788 else
2789 {
2790 Request.Data.ScrollConsoleScreenBufferRequest.UseClipRectangle = FALSE;
2791 }
2792
2793 Request.Data.ScrollConsoleScreenBufferRequest.DestinationOrigin = dwDestinationOrigin;
2794 Request.Data.ScrollConsoleScreenBufferRequest.Fill = *lpFill;
2795 Status = CsrClientCallServer(&Request, NULL,
2796 CsrRequest,
2797 sizeof(CSR_API_MESSAGE));
2798
2799 if(!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
2800 {
2801 SetLastErrorByStatus(Status);
2802 return FALSE;
2803 }
2804
2805 return TRUE;
2806 }
2807
2808
2809 /*--------------------------------------------------------------
2810 * ScrollConsoleScreenBufferA
2811 *
2812 * @implemented
2813 */
2814 BOOL
2815 WINAPI
2816 ScrollConsoleScreenBufferA(
2817 HANDLE hConsoleOutput,
2818 CONST SMALL_RECT *lpScrollRectangle,
2819 CONST SMALL_RECT *lpClipRectangle,
2820 COORD dwDestinationOrigin,
2821 CONST CHAR_INFO *lpFill
2822 )
2823 {
2824 return IntScrollConsoleScreenBuffer(hConsoleOutput,
2825 (PSMALL_RECT)lpScrollRectangle,
2826 (PSMALL_RECT)lpClipRectangle,
2827 dwDestinationOrigin,
2828 (PCHAR_INFO)lpFill,
2829 FALSE);
2830 }
2831
2832
2833 /*--------------------------------------------------------------
2834 * ScrollConsoleScreenBufferW
2835 *
2836 * @implemented
2837 */
2838 BOOL
2839 WINAPI
2840 ScrollConsoleScreenBufferW(
2841 HANDLE hConsoleOutput,
2842 CONST SMALL_RECT *lpScrollRectangle,
2843 CONST SMALL_RECT *lpClipRectangle,
2844 COORD dwDestinationOrigin,
2845 CONST CHAR_INFO *lpFill
2846 )
2847 {
2848 return IntScrollConsoleScreenBuffer(hConsoleOutput,
2849 (PSMALL_RECT)lpScrollRectangle,
2850 (PSMALL_RECT)lpClipRectangle,
2851 dwDestinationOrigin,
2852 (PCHAR_INFO)lpFill,
2853 TRUE);
2854 }
2855
2856
2857 /*--------------------------------------------------------------
2858 * SetConsoleWindowInfo
2859 *
2860 * @unimplemented
2861 */
2862 BOOL
2863 WINAPI
2864 SetConsoleWindowInfo(
2865 HANDLE hConsoleOutput,
2866 BOOL bAbsolute,
2867 CONST SMALL_RECT *lpConsoleWindow
2868 )
2869 {
2870 DPRINT1("SetConsoleWindowInfo(0x%x, 0x%x, 0x%x) UNIMPLEMENTED!\n", hConsoleOutput, bAbsolute, lpConsoleWindow);
2871 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
2872 return FALSE;
2873 }
2874
2875
2876 /*--------------------------------------------------------------
2877 * SetConsoleTextAttribute
2878 *
2879 * @implemented
2880 */
2881 BOOL
2882 WINAPI
2883 SetConsoleTextAttribute(
2884 HANDLE hConsoleOutput,
2885 WORD wAttributes
2886 )
2887 {
2888 CSR_API_MESSAGE Request; ULONG CsrRequest;
2889
2890 NTSTATUS Status;
2891
2892 CsrRequest = MAKE_CSR_API(SET_ATTRIB, CSR_CONSOLE);
2893 Request.Data.SetAttribRequest.ConsoleHandle = hConsoleOutput;
2894 Request.Data.SetAttribRequest.Attrib = wAttributes;
2895 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
2896 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
2897 {
2898 SetLastErrorByStatus ( Status );
2899 return FALSE;
2900 }
2901 return TRUE;
2902 }
2903
2904
2905 static BOOL
2906 AddConsoleCtrlHandler(PHANDLER_ROUTINE HandlerRoutine)
2907 {
2908 if (HandlerRoutine == NULL)
2909 {
2910 IgnoreCtrlEvents = TRUE;
2911 return(TRUE);
2912 }
2913 else
2914 {
2915 NrCtrlHandlers++;
2916 if (CtrlHandlers == NULL)
2917 {
2918 CtrlHandlers = RtlAllocateHeap(RtlGetProcessHeap(), HEAP_ZERO_MEMORY,
2919 NrCtrlHandlers * sizeof(PHANDLER_ROUTINE));
2920 }
2921 else
2922 {
2923 CtrlHandlers = RtlReAllocateHeap(RtlGetProcessHeap(), HEAP_ZERO_MEMORY,
2924 (PVOID)CtrlHandlers,
2925 NrCtrlHandlers * sizeof(PHANDLER_ROUTINE));
2926 }
2927 if (CtrlHandlers == NULL)
2928 {
2929 NrCtrlHandlers = 0;
2930 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
2931 return(FALSE);
2932 }
2933 CtrlHandlers[NrCtrlHandlers - 1] = HandlerRoutine;
2934 return(TRUE);
2935 }
2936 }
2937
2938
2939 static BOOL
2940 RemoveConsoleCtrlHandler(PHANDLER_ROUTINE HandlerRoutine)
2941 {
2942 ULONG i;
2943
2944 if (HandlerRoutine == NULL)
2945 {
2946 IgnoreCtrlEvents = FALSE;
2947 return(TRUE);
2948 }
2949 else
2950 {
2951 for (i = 0; i < NrCtrlHandlers; i++)
2952 {
2953 if ( ((void*)(CtrlHandlers[i])) == (void*)HandlerRoutine)
2954 {
2955 NrCtrlHandlers--;
2956 memmove(CtrlHandlers + i, CtrlHandlers + i + 1,
2957 (NrCtrlHandlers - i) * sizeof(PHANDLER_ROUTINE));
2958 CtrlHandlers =
2959 RtlReAllocateHeap(RtlGetProcessHeap(),
2960 HEAP_ZERO_MEMORY,
2961 (PVOID)CtrlHandlers,
2962 NrCtrlHandlers * sizeof(PHANDLER_ROUTINE));
2963 return(TRUE);
2964 }
2965 }
2966 }
2967 return(FALSE);
2968 }
2969
2970
2971 /*
2972 * @implemented
2973 */
2974 BOOL WINAPI
2975 SetConsoleCtrlHandler(PHANDLER_ROUTINE HandlerRoutine,
2976 BOOL Add)
2977 {
2978 BOOLEAN Ret;
2979
2980 RtlEnterCriticalSection(&DllLock);
2981 if (Add)
2982 {
2983 Ret = AddConsoleCtrlHandler(HandlerRoutine);
2984 }
2985 else
2986 {
2987 Ret = RemoveConsoleCtrlHandler(HandlerRoutine);
2988 }
2989 RtlLeaveCriticalSection(&DllLock);
2990 return(Ret);
2991 }
2992
2993
2994 /*--------------------------------------------------------------
2995 * GenerateConsoleCtrlEvent
2996 *
2997 * @unimplemented
2998 */
2999 BOOL WINAPI
3000 GenerateConsoleCtrlEvent(
3001 DWORD dwCtrlEvent,
3002 DWORD dwProcessGroupId
3003 )
3004 {
3005 DPRINT1("GenerateConsoleCtrlEvent(0x%x, 0x%x) UNIMPLEMENTED!\n", dwCtrlEvent, dwProcessGroupId);
3006 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
3007 return FALSE;
3008 }
3009
3010
3011 /*--------------------------------------------------------------
3012 * GetConsoleTitleW
3013 *
3014 * @implemented
3015 */
3016 DWORD
3017 WINAPI
3018 GetConsoleTitleW(
3019 LPWSTR lpConsoleTitle,
3020 DWORD nSize
3021 )
3022 {
3023 PCSR_API_MESSAGE Request; ULONG CsrRequest;
3024 NTSTATUS Status;
3025 HANDLE hConsole;
3026
3027 hConsole = CreateFileW(L"CONIN$", GENERIC_READ, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
3028 if (hConsole == INVALID_HANDLE_VALUE)
3029 {
3030 return 0;
3031 }
3032
3033 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
3034 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_GET_TITLE) + CSRSS_MAX_TITLE_LENGTH * sizeof(WCHAR));
3035 if (Request == NULL)
3036 {
3037 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
3038 return FALSE;
3039 }
3040
3041 CsrRequest = MAKE_CSR_API(GET_TITLE, CSR_CONSOLE);
3042 Request->Data.GetTitleRequest.ConsoleHandle = hConsole;
3043
3044 Status = CsrClientCallServer(Request,
3045 NULL,
3046 CsrRequest,
3047 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_GET_TITLE) + CSRSS_MAX_TITLE_LENGTH * sizeof(WCHAR));
3048 CloseHandle(hConsole);
3049 if(!NT_SUCCESS(Status) || !(NT_SUCCESS(Status = Request->Status)))
3050 {
3051 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
3052 SetLastErrorByStatus(Status);
3053 return 0;
3054 }
3055
3056 if(nSize * sizeof(WCHAR) <= Request->Data.GetTitleRequest.Length)
3057 {
3058 nSize--;
3059 }
3060 else
3061 {
3062 nSize = Request->Data.GetTitleRequest.Length / sizeof (WCHAR);
3063 }
3064 memcpy(lpConsoleTitle, Request->Data.GetTitleRequest.Title, nSize * sizeof(WCHAR));
3065 lpConsoleTitle[nSize] = L'\0';
3066
3067 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
3068
3069 return nSize;
3070 }
3071
3072
3073 /*--------------------------------------------------------------
3074 * GetConsoleTitleA
3075 *
3076 * 19990306 EA
3077 *
3078 * @implemented
3079 */
3080 DWORD
3081 WINAPI
3082 GetConsoleTitleA(
3083 LPSTR lpConsoleTitle,
3084 DWORD nSize
3085 )
3086 {
3087 WCHAR WideTitle [CSRSS_MAX_TITLE_LENGTH + 1];
3088 DWORD nWideTitle = CSRSS_MAX_TITLE_LENGTH + 1;
3089 DWORD nWritten;
3090
3091 if (!lpConsoleTitle || !nSize) return 0;
3092 nWideTitle = GetConsoleTitleW( (LPWSTR) WideTitle, nWideTitle );
3093 if (!nWideTitle) return 0;
3094
3095 if ( (nWritten = WideCharToMultiByte(
3096 CP_ACP, // ANSI code page
3097 0, // performance and mapping flags
3098 (LPWSTR) WideTitle, // address of wide-character string
3099 nWideTitle, // number of characters in string
3100 lpConsoleTitle, // address of buffer for new string
3101 nSize - 1, // size of buffer
3102 NULL, // FAST
3103 NULL // FAST
3104 )))
3105 {
3106 lpConsoleTitle[nWritten] = '\0';
3107 return nWritten;
3108 }
3109
3110 return 0;
3111 }
3112
3113
3114 /*--------------------------------------------------------------
3115 * SetConsoleTitleW
3116 *
3117 * @implemented
3118 */
3119 BOOL
3120 WINAPI
3121 SetConsoleTitleW(
3122 LPCWSTR lpConsoleTitle
3123 )
3124 {
3125 PCSR_API_MESSAGE Request; ULONG CsrRequest;
3126 NTSTATUS Status;
3127 unsigned int c;
3128 HANDLE hConsole;
3129
3130 hConsole = CreateFileW(L"CONIN$", GENERIC_WRITE, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
3131 if (hConsole == INVALID_HANDLE_VALUE)
3132 {
3133 return FALSE;
3134 }
3135
3136 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
3137 max (sizeof(CSR_API_MESSAGE),
3138 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) +
3139 min (wcslen(lpConsoleTitle), CSRSS_MAX_TITLE_LENGTH) * sizeof(WCHAR)));
3140 if (Request == NULL)
3141 {
3142 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
3143 return FALSE;
3144 }
3145
3146 CsrRequest = MAKE_CSR_API(SET_TITLE, CSR_CONSOLE);
3147 Request->Data.SetTitleRequest.Console = hConsole;
3148
3149 for( c = 0; lpConsoleTitle[c] && c < CSRSS_MAX_TITLE_LENGTH; c++ )
3150 Request->Data.SetTitleRequest.Title[c] = lpConsoleTitle[c];
3151 Request->Data.SetTitleRequest.Length = c * sizeof(WCHAR);
3152 Status = CsrClientCallServer(Request,
3153 NULL,
3154 CsrRequest,
3155 max (sizeof(CSR_API_MESSAGE), CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) + c * sizeof(WCHAR)));
3156 CloseHandle(hConsole);
3157 if (!NT_SUCCESS(Status) || !NT_SUCCESS( Status = Request->Status ) )
3158 {
3159 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
3160 SetLastErrorByStatus (Status);
3161 return(FALSE);
3162 }
3163
3164 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
3165
3166 return TRUE;
3167 }
3168
3169
3170 /*--------------------------------------------------------------
3171 * SetConsoleTitleA
3172 *
3173 * 19990204 EA Added
3174 *
3175 * @implemented
3176 */
3177 BOOL
3178 WINAPI
3179 SetConsoleTitleA(
3180 LPCSTR lpConsoleTitle
3181 )
3182 {
3183 PCSR_API_MESSAGE Request; ULONG CsrRequest;
3184 NTSTATUS Status;
3185 unsigned int c;
3186 HANDLE hConsole;
3187
3188 hConsole = CreateFileW(L"CONIN$", GENERIC_WRITE, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
3189 if (hConsole == INVALID_HANDLE_VALUE)
3190 {
3191 return FALSE;
3192 }
3193
3194 Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
3195 max (sizeof(CSR_API_MESSAGE),
3196 CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) +
3197 min (strlen(lpConsoleTitle), CSRSS_MAX_TITLE_LENGTH) * sizeof(WCHAR)));
3198 if (Request == NULL)
3199 {
3200 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
3201 return FALSE;
3202 }
3203
3204 CsrRequest = MAKE_CSR_API(SET_TITLE, CSR_CONSOLE);
3205 Request->Data.SetTitleRequest.Console = hConsole;
3206
3207 for( c = 0; lpConsoleTitle[c] && c < CSRSS_MAX_TITLE_LENGTH; c++ )
3208 Request->Data.SetTitleRequest.Title[c] = lpConsoleTitle[c];
3209 Request->Data.SetTitleRequest.Length = c * sizeof(WCHAR);
3210 Status = CsrClientCallServer(Request,
3211 NULL,
3212 CsrRequest,
3213 max (sizeof(CSR_API_MESSAGE), CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) + c * sizeof(WCHAR)));
3214 CloseHandle(hConsole);
3215 if (!NT_SUCCESS(Status) || !NT_SUCCESS( Status = Request->Status ) )
3216 {
3217 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
3218 SetLastErrorByStatus (Status);
3219 return(FALSE);
3220 }
3221
3222 RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
3223
3224 return TRUE;
3225 }
3226
3227
3228 /*--------------------------------------------------------------
3229 * CreateConsoleScreenBuffer
3230 *
3231 * @implemented
3232 */
3233 HANDLE
3234 WINAPI
3235 CreateConsoleScreenBuffer(
3236 DWORD dwDesiredAccess,
3237 DWORD dwShareMode,
3238 CONST SECURITY_ATTRIBUTES *lpSecurityAttributes,
3239 DWORD dwFlags,
3240 LPVOID lpScreenBufferData
3241 )
3242 {
3243 // FIXME: don't ignore access, share mode, and security
3244 CSR_API_MESSAGE Request; ULONG CsrRequest;
3245
3246 NTSTATUS Status;
3247
3248 CsrRequest = MAKE_CSR_API(CREATE_SCREEN_BUFFER, CSR_CONSOLE);
3249 Status = CsrClientCallServer( &Request, NULL, CsrRequest, sizeof( CSR_API_MESSAGE ) );
3250 if( !NT_SUCCESS( Status ) || !NT_SUCCESS( Status = Request.Status ) )
3251 {
3252 SetLastErrorByStatus ( Status );
3253 return FALSE;
3254 }
3255 return Request.Data.CreateScreenBufferRequest.OutputHandle;
3256 }
3257
3258
3259 /*--------------------------------------------------------------
3260 * GetConsoleCP
3261 *
3262 * @implemented
3263 */
3264 UINT
3265 WINAPI
3266 GetConsoleCP( VOID )
3267 {
3268 CSR_API_MESSAGE Request; ULONG CsrRequest;
3269
3270 NTSTATUS Status;
3271
3272 CsrRequest = MAKE_CSR_API(GET_CONSOLE_CP, CSR_CONSOLE);
3273 Status = CsrClientCallServer(&Request, NULL, CsrRequest,
3274 sizeof(CSR_API_MESSAGE));
3275 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
3276 {
3277 SetLastErrorByStatus (Status);
3278 return 0;
3279 }
3280 return Request.Data.GetConsoleCodePage.CodePage;
3281 }
3282
3283
3284 /*--------------------------------------------------------------
3285 * SetConsoleCP
3286 *
3287 * @implemented
3288 */
3289 BOOL
3290 WINAPI
3291 SetConsoleCP(
3292 UINT wCodePageID
3293 )
3294 {
3295 CSR_API_MESSAGE Request; ULONG CsrRequest;
3296
3297 NTSTATUS Status;
3298
3299 CsrRequest = MAKE_CSR_API(SET_CONSOLE_CP, CSR_CONSOLE);
3300 Request.Data.SetConsoleCodePage.CodePage = wCodePageID;
3301 Status = CsrClientCallServer(&Request, NULL, CsrRequest,
3302 sizeof(CSR_API_MESSAGE));
3303 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
3304 {
3305 SetLastErrorByStatus (Status);
3306 }
3307 return NT_SUCCESS(Status);
3308 }
3309
3310
3311 /*--------------------------------------------------------------
3312 * GetConsoleOutputCP
3313 *
3314 * @implemented
3315 */
3316 UINT
3317 WINAPI
3318 GetConsoleOutputCP( VOID )
3319 {
3320 CSR_API_MESSAGE Request; ULONG CsrRequest;
3321
3322 NTSTATUS Status;
3323
3324 CsrRequest = MAKE_CSR_API(GET_CONSOLE_OUTPUT_CP, CSR_CONSOLE);
3325 Status = CsrClientCallServer(&Request, NULL, CsrRequest,
3326 sizeof(CSR_API_MESSAGE));
3327 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
3328 {
3329 SetLastErrorByStatus (Status);
3330 return 0;
3331 }
3332 return Request.Data.GetConsoleOutputCodePage.CodePage;
3333 }
3334
3335
3336 /*--------------------------------------------------------------
3337 * SetConsoleOutputCP
3338 *
3339 * @implemented
3340 */
3341 BOOL
3342 WINAPI
3343 SetConsoleOutputCP(
3344 UINT wCodePageID
3345 )
3346 {
3347 CSR_API_MESSAGE Request; ULONG CsrRequest;
3348
3349 NTSTATUS Status;
3350
3351 CsrRequest = MAKE_CSR_API(SET_CONSOLE_OUTPUT_CP, CSR_CONSOLE);
3352 Request.Data.SetConsoleOutputCodePage.CodePage = wCodePageID;
3353 Status = CsrClientCallServer(&Request, NULL, CsrRequest,
3354 sizeof(CSR_API_MESSAGE));
3355 if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
3356 {
3357 SetLastErrorByStatus (Status);
3358 }
3359 return NT_SUCCESS(Status);
3360 }