1 /* 2 * COPYRIGHT: See COPYING in the top level directory 3 * PROJECT: ReactOS Win32k subsystem 4 * PURPOSE: Console support functions for CONSRV 5 * FILE: win32ss/user/ntuser/console.c 6 * PROGRAMMER: Hermes Belusca-Maito (hermes.belusca@sfr.fr) 7 */ 8 9 #include <win32k.h> 10 DBG_DEFAULT_CHANNEL(UserMisc); 11 12 NTSTATUS 13 APIENTRY 14 NtUserConsoleControl( 15 IN CONSOLECONTROL ConsoleCtrl, 16 IN PVOID ConsoleCtrlInfo, 17 IN ULONG ConsoleCtrlInfoLength) 18 { 19 NTSTATUS Status = STATUS_SUCCESS; 20 21 /* Allow only the Console Server to perform this operation (via CSRSS) */ 22 if (PsGetCurrentProcess() != gpepCSRSS) 23 return STATUS_ACCESS_DENIED; 24 25 UserEnterExclusive(); 26 27 switch (ConsoleCtrl) 28 { 29 case ConsoleCtrlDesktopConsoleThread: 30 { 31 DESKTOP_CONSOLE_THREAD DesktopConsoleThreadInfo; 32 PDESKTOP Desktop = NULL; 33 ULONG_PTR OldThreadId; 34 35 if (ConsoleCtrlInfoLength != sizeof(DesktopConsoleThreadInfo)) 36 { 37 Status = STATUS_INFO_LENGTH_MISMATCH; 38 break; 39 } 40 41 _SEH2_TRY 42 { 43 ProbeForWrite(ConsoleCtrlInfo, ConsoleCtrlInfoLength, sizeof(USHORT)); 44 DesktopConsoleThreadInfo = *(PDESKTOP_CONSOLE_THREAD)ConsoleCtrlInfo; 45 } 46 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 47 { 48 Status = _SEH2_GetExceptionCode(); 49 _SEH2_YIELD(break); 50 } 51 _SEH2_END; 52 53 /* Reference the desktop */ 54 Status = ObReferenceObjectByHandle(DesktopConsoleThreadInfo.DesktopHandle, 55 0, 56 ExDesktopObjectType, 57 UserMode, 58 (PVOID*)&Desktop, 59 NULL); 60 if (!NT_SUCCESS(Status)) break; 61 62 /* Save the old thread ID, it is always returned to the caller */ 63 OldThreadId = Desktop->dwConsoleThreadId; 64 65 /* Set the new console input thread ID for this desktop if required */ 66 if (DesktopConsoleThreadInfo.ThreadId != (ULONG_PTR)INVALID_HANDLE_VALUE) 67 { 68 Desktop->dwConsoleThreadId = DesktopConsoleThreadInfo.ThreadId; 69 } 70 71 /* Always return the old thread ID */ 72 DesktopConsoleThreadInfo.ThreadId = OldThreadId; 73 74 /* Dereference the desktop */ 75 ObDereferenceObject(Desktop); 76 77 /* Return the information back to the caller */ 78 _SEH2_TRY 79 { 80 *(PDESKTOP_CONSOLE_THREAD)ConsoleCtrlInfo = DesktopConsoleThreadInfo; 81 } 82 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 83 { 84 Status = _SEH2_GetExceptionCode(); 85 } 86 _SEH2_END; 87 88 break; 89 } 90 91 case GuiConsoleWndClassAtom: 92 { 93 if (ConsoleCtrlInfoLength != sizeof(ATOM)) 94 { 95 Status = STATUS_INFO_LENGTH_MISMATCH; 96 break; 97 } 98 99 _SEH2_TRY 100 { 101 ProbeForRead(ConsoleCtrlInfo, ConsoleCtrlInfoLength, sizeof(USHORT)); 102 gaGuiConsoleWndClass = *(ATOM*)ConsoleCtrlInfo; 103 } 104 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 105 { 106 Status = _SEH2_GetExceptionCode(); 107 } 108 _SEH2_END; 109 110 break; 111 } 112 113 case ConsoleMakePalettePublic: 114 { 115 HPALETTE hPalette; 116 117 if (ConsoleCtrlInfoLength != sizeof(hPalette)) 118 { 119 Status = STATUS_INFO_LENGTH_MISMATCH; 120 break; 121 } 122 123 _SEH2_TRY 124 { 125 ProbeForRead(ConsoleCtrlInfo, ConsoleCtrlInfoLength, sizeof(USHORT)); 126 hPalette = *(HPALETTE*)ConsoleCtrlInfo; 127 } 128 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 129 { 130 Status = _SEH2_GetExceptionCode(); 131 _SEH2_YIELD(break); 132 } 133 _SEH2_END; 134 135 /* Make the palette handle public */ 136 GreSetObjectOwnerEx(hPalette, 137 GDI_OBJ_HMGR_PUBLIC, 138 GDIOBJFLAG_IGNOREPID); 139 break; 140 } 141 142 case ConsoleAcquireDisplayOwnership: 143 { 144 ERR("NtUserConsoleControl - ConsoleAcquireDisplayOwnership is UNIMPLEMENTED\n"); 145 Status = STATUS_NOT_IMPLEMENTED; 146 break; 147 } 148 149 default: 150 ERR("Calling invalid control %d in NtUserConsoleControl\n", ConsoleCtrl); 151 Status = STATUS_INVALID_INFO_CLASS; 152 break; 153 } 154 155 UserLeave(); 156 157 return Status; 158 } 159 160 /* EOF */ 161