1 #pragma once 2 3 typedef struct _DESKTOP 4 { 5 /* Must be the first member */ 6 DWORD dwSessionId; 7 8 PDESKTOPINFO pDeskInfo; 9 LIST_ENTRY ListEntry; 10 /* Pointer to the associated window station. */ 11 struct _WINSTATION_OBJECT *rpwinstaParent; 12 DWORD dwDTFlags; 13 DWORD_PTR dwDesktopId; 14 PMENU spmenuSys; 15 PMENU spmenuDialogSys; 16 PMENU spmenuHScroll; 17 PMENU spmenuVScroll; 18 PWND spwndForeground; 19 PWND spwndTray; 20 PWND spwndMessage; 21 PWND spwndTooltip; 22 PVOID hsectionDesktop; 23 PWIN32HEAP pheapDesktop; 24 ULONG_PTR ulHeapSize; 25 LIST_ENTRY PtiList; 26 27 /* One console input thread per desktop, maintained by CONSRV */ 28 DWORD dwConsoleThreadId; 29 30 /* Use for tracking mouse moves. */ 31 PWND spwndTrack; 32 DWORD htEx; 33 RECT rcMouseHover; 34 DWORD dwMouseHoverTime; 35 36 /* ReactOS */ 37 /* Pointer to the active queue. */ 38 struct _USER_MESSAGE_QUEUE *ActiveMessageQueue; 39 /* Handle of the desktop window. */ 40 HWND DesktopWindow; 41 /* Thread blocking input */ 42 PVOID BlockInputThread; 43 LIST_ENTRY ShellHookWindows; 44 } DESKTOP, *PDESKTOP; 45 46 // Desktop flags 47 #define DF_TME_HOVER 0x00000400 48 #define DF_TME_LEAVE 0x00000800 49 #define DF_HOTTRACK 0x00004000 50 #define DF_DESTROYED 0x00008000 51 #define DF_DESKWNDDESTROYED 0x00010000 52 #define DF_DYING 0x00020000 53 54 // Index offset for Desktop data. Should these be global? 55 #define DT_GWL_PROCESSID 0 56 #define DT_GWL_THREADID 4 57 58 #define DESKTOP_READ STANDARD_RIGHTS_READ | \ 59 DESKTOP_ENUMERATE | \ 60 DESKTOP_READOBJECTS 61 62 #define DESKTOP_WRITE STANDARD_RIGHTS_WRITE | \ 63 DESKTOP_CREATEMENU | \ 64 DESKTOP_CREATEWINDOW | \ 65 DESKTOP_HOOKCONTROL | \ 66 DESKTOP_JOURNALPLAYBACK | \ 67 DESKTOP_JOURNALRECORD | \ 68 DESKTOP_WRITEOBJECTS 69 70 #define DESKTOP_EXECUTE STANDARD_RIGHTS_EXECUTE | \ 71 DESKTOP_SWITCHDESKTOP 72 73 #define DESKTOP_ALL_ACCESS STANDARD_RIGHTS_REQUIRED | \ 74 DESKTOP_CREATEMENU | \ 75 DESKTOP_CREATEWINDOW | \ 76 DESKTOP_ENUMERATE | \ 77 DESKTOP_HOOKCONTROL | \ 78 DESKTOP_JOURNALPLAYBACK | \ 79 DESKTOP_JOURNALRECORD | \ 80 DESKTOP_READOBJECTS | \ 81 DESKTOP_SWITCHDESKTOP | \ 82 DESKTOP_WRITEOBJECTS 83 84 extern PDESKTOP gpdeskInputDesktop; 85 extern PCLS DesktopWindowClass; 86 extern HDC ScreenDeviceContext; 87 extern PTHREADINFO gptiForeground; 88 extern PTHREADINFO gptiDesktopThread; 89 extern PKEVENT gpDesktopThreadStartedEvent; 90 91 typedef struct _SHELL_HOOK_WINDOW 92 { 93 LIST_ENTRY ListEntry; 94 HWND hWnd; 95 } SHELL_HOOK_WINDOW, *PSHELL_HOOK_WINDOW; 96 97 INIT_FUNCTION 98 NTSTATUS 99 NTAPI 100 InitDesktopImpl(VOID); 101 102 NTSTATUS 103 APIENTRY 104 IntDesktopObjectParse(IN PVOID ParseObject, 105 IN PVOID ObjectType, 106 IN OUT PACCESS_STATE AccessState, 107 IN KPROCESSOR_MODE AccessMode, 108 IN ULONG Attributes, 109 IN OUT PUNICODE_STRING CompleteName, 110 IN OUT PUNICODE_STRING RemainingName, 111 IN OUT PVOID Context OPTIONAL, 112 IN PSECURITY_QUALITY_OF_SERVICE SecurityQos OPTIONAL, 113 OUT PVOID *Object); 114 115 NTSTATUS 116 NTAPI 117 IntDesktopObjectDelete( 118 _In_ PVOID Parameters); 119 120 NTSTATUS 121 NTAPI 122 IntDesktopOkToClose( 123 _In_ PVOID Parameters); 124 125 NTSTATUS 126 NTAPI 127 IntDesktopObjectOpen( 128 _In_ PVOID Parameters); 129 130 NTSTATUS 131 NTAPI 132 IntDesktopObjectClose( 133 _In_ PVOID Parameters); 134 135 HDC FASTCALL 136 IntGetScreenDC(VOID); 137 138 HWND FASTCALL 139 IntGetDesktopWindow (VOID); 140 141 PWND FASTCALL 142 UserGetDesktopWindow(VOID); 143 144 HWND FASTCALL 145 IntGetCurrentThreadDesktopWindow(VOID); 146 147 PUSER_MESSAGE_QUEUE FASTCALL 148 IntGetFocusMessageQueue(VOID); 149 150 VOID FASTCALL 151 IntSetFocusMessageQueue(PUSER_MESSAGE_QUEUE NewQueue); 152 153 PDESKTOP FASTCALL 154 IntGetActiveDesktop(VOID); 155 156 NTSTATUS FASTCALL 157 co_IntShowDesktop(PDESKTOP Desktop, ULONG Width, ULONG Height, BOOL Redraw); 158 159 NTSTATUS FASTCALL 160 IntHideDesktop(PDESKTOP Desktop); 161 162 BOOL IntSetThreadDesktop(IN HDESK hDesktop, 163 IN BOOL FreeOnFailure); 164 165 NTSTATUS 166 FASTCALL 167 IntResolveDesktop( 168 IN PEPROCESS Process, 169 IN PUNICODE_STRING DesktopPath, 170 IN BOOL bInherit, 171 OUT HWINSTA* phWinSta, 172 OUT HDESK* phDesktop); 173 174 NTSTATUS FASTCALL 175 IntValidateDesktopHandle( 176 HDESK Desktop, 177 KPROCESSOR_MODE AccessMode, 178 ACCESS_MASK DesiredAccess, 179 PDESKTOP *Object); 180 181 NTSTATUS 182 FASTCALL 183 IntCreateDesktop( 184 OUT HDESK* phDesktop, 185 IN POBJECT_ATTRIBUTES ObjectAttributes, 186 IN KPROCESSOR_MODE AccessMode, 187 IN PUNICODE_STRING lpszDesktopDevice OPTIONAL, 188 IN LPDEVMODEW lpdmw OPTIONAL, 189 IN DWORD dwFlags, 190 IN ACCESS_MASK dwDesiredAccess); 191 192 VOID APIENTRY UserRedrawDesktop(VOID); 193 BOOL IntRegisterShellHookWindow(HWND hWnd); 194 BOOL IntDeRegisterShellHookWindow(HWND hWnd); 195 VOID co_IntShellHookNotify(WPARAM Message, WPARAM wParam, LPARAM lParam); 196 HDC FASTCALL UserGetDesktopDC(ULONG,BOOL,BOOL); 197 198 #define IntIsActiveDesktop(Desktop) \ 199 ((Desktop)->rpwinstaParent->ActiveDesktop == (Desktop)) 200 201 HWND FASTCALL IntGetMessageWindow(VOID); 202 PWND FASTCALL UserGetMessageWindow(VOID); 203 204 #if 0 205 static __inline BOOL 206 UserIsDesktopWindow(IN PWND pWnd) 207 { 208 // return (pWnd == UserGetDesktopWindow()); 209 return (pWnd && (pWnd->fnid == FNID_DESKTOP)); 210 } 211 212 static __inline BOOL 213 UserIsMessageWindow(IN PWND pWnd) 214 { 215 // return (pWnd == UserGetMessageWindow()); 216 return (pWnd && (pWnd->fnid == FNID_MESSAGEWND)); 217 } 218 #else 219 220 #define UserIsDesktopWindow(pWnd) \ 221 ((pWnd) && ((pWnd)->fnid == FNID_DESKTOP)) 222 223 #define UserIsMessageWindow(pWnd) \ 224 ((pWnd) && ((pWnd)->fnid == FNID_MESSAGEWND)) 225 226 #endif 227 228 229 static __inline PVOID 230 DesktopHeapAlloc(IN PDESKTOP Desktop, 231 IN SIZE_T Bytes) 232 { 233 return RtlAllocateHeap(Desktop->pheapDesktop, 234 HEAP_NO_SERIALIZE, 235 Bytes); 236 } 237 238 static __inline BOOL 239 DesktopHeapFree(IN PDESKTOP Desktop, 240 IN PVOID lpMem) 241 { 242 return RtlFreeHeap(Desktop->pheapDesktop, 243 HEAP_NO_SERIALIZE, 244 lpMem); 245 } 246 247 static __inline PVOID 248 DesktopHeapReAlloc(IN PDESKTOP Desktop, 249 IN PVOID lpMem, 250 IN SIZE_T Bytes) 251 { 252 #if 0 253 /* NOTE: ntoskrnl doesn't export RtlReAllocateHeap... */ 254 return RtlReAllocateHeap(Desktop->pheapDesktop, 255 HEAP_NO_SERIALIZE, 256 lpMem, 257 Bytes); 258 #else 259 SIZE_T PrevSize; 260 PVOID pNew; 261 262 PrevSize = RtlSizeHeap(Desktop->pheapDesktop, 263 HEAP_NO_SERIALIZE, 264 lpMem); 265 266 if (PrevSize == Bytes) 267 return lpMem; 268 269 pNew = RtlAllocateHeap(Desktop->pheapDesktop, 270 HEAP_NO_SERIALIZE, 271 Bytes); 272 if (pNew != NULL) 273 { 274 if (PrevSize < Bytes) 275 Bytes = PrevSize; 276 277 RtlCopyMemory(pNew, 278 lpMem, 279 Bytes); 280 281 RtlFreeHeap(Desktop->pheapDesktop, 282 HEAP_NO_SERIALIZE, 283 lpMem); 284 } 285 286 return pNew; 287 #endif 288 } 289 290 static __inline ULONG_PTR 291 DesktopHeapGetUserDelta(VOID) 292 { 293 PW32HEAP_USER_MAPPING Mapping; 294 PTHREADINFO pti; 295 PPROCESSINFO W32Process; 296 PWIN32HEAP pheapDesktop; 297 ULONG_PTR Delta = 0; 298 299 pti = PsGetCurrentThreadWin32Thread(); 300 if (!pti->rpdesk) 301 return 0; 302 303 pheapDesktop = pti->rpdesk->pheapDesktop; 304 305 W32Process = PsGetCurrentProcessWin32Process(); 306 307 /* 308 * Start the search at the next mapping: skip the first entry 309 * as it must be the global user heap mapping. 310 */ 311 Mapping = W32Process->HeapMappings.Next; 312 while (Mapping != NULL) 313 { 314 if (Mapping->KernelMapping == (PVOID)pheapDesktop) 315 { 316 Delta = (ULONG_PTR)Mapping->KernelMapping - (ULONG_PTR)Mapping->UserMapping; 317 break; 318 } 319 320 Mapping = Mapping->Next; 321 } 322 323 return Delta; 324 } 325 326 static __inline PVOID 327 DesktopHeapAddressToUser(PVOID lpMem) 328 { 329 PW32HEAP_USER_MAPPING Mapping; 330 PPROCESSINFO W32Process; 331 332 W32Process = PsGetCurrentProcessWin32Process(); 333 334 /* 335 * Start the search at the next mapping: skip the first entry 336 * as it must be the global user heap mapping. 337 */ 338 Mapping = W32Process->HeapMappings.Next; 339 while (Mapping != NULL) 340 { 341 if ((ULONG_PTR)lpMem >= (ULONG_PTR)Mapping->KernelMapping && 342 (ULONG_PTR)lpMem < (ULONG_PTR)Mapping->KernelMapping + Mapping->Limit) 343 { 344 return (PVOID)(((ULONG_PTR)lpMem - (ULONG_PTR)Mapping->KernelMapping) + 345 (ULONG_PTR)Mapping->UserMapping); 346 } 347 348 Mapping = Mapping->Next; 349 } 350 351 return NULL; 352 } 353 354 PWND FASTCALL IntGetThreadDesktopWindow(PTHREADINFO); 355 PWND FASTCALL co_GetDesktopWindow(PWND); 356 BOOL FASTCALL IntPaintDesktop(HDC); 357 BOOL FASTCALL DesktopWindowProc(PWND, UINT, WPARAM, LPARAM, LRESULT *); 358 BOOL FASTCALL UserMessageWindowProc(PWND pwnd, UINT Msg, WPARAM wParam, LPARAM lParam, LRESULT *lResult); 359 VOID NTAPI DesktopThreadMain(VOID); 360 HDESK UserOpenInputDesktop(DWORD dwFlags, BOOL fInherit, ACCESS_MASK dwDesiredAccess); 361 362 /* EOF */ 363