2 * ReactOS W32 Subsystem
3 * Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005 ReactOS Team
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 * Entry Point for win32k.sys
26 #include <win32k/debug1.h>
30 typedef NTSTATUS (STDCALL
*PW32_PROCESS_CALLBACK
)(
31 struct _EPROCESS
*Process
,
34 typedef NTSTATUS (STDCALL
*PW32_THREAD_CALLBACK
)(
35 struct _ETHREAD
*Thread
,
39 * Callbacks used for Win32 objects... this define won't be needed after the Object Manager
44 typedef NTSTATUS STDCALL_FUNC
45 (*OBJECT_CREATE_ROUTINE
)(PVOID ObjectBody
,
48 struct _OBJECT_ATTRIBUTES
* ObjectAttributes
);
50 typedef NTSTATUS STDCALL_FUNC
51 (*OBJECT_OPEN_ROUTINE
)(ULONG Reason
,
55 ACCESS_MASK GrantedAccess
);
57 typedef NTSTATUS STDCALL_FUNC
58 (*OBJECT_PARSE_ROUTINE
)(PVOID Object
,
60 PUNICODE_STRING FullPath
,
64 typedef VOID STDCALL_FUNC
65 (*OBJECT_DELETE_ROUTINE
)(PVOID DeletedObject
);
67 typedef PVOID STDCALL_FUNC
68 (*OBJECT_FIND_ROUTINE
)(PVOID WinStaObject
,
72 typedef struct _W32_OBJECT_CALLBACK
{
73 OBJECT_OPEN_ROUTINE WinStaCreate
;
74 OBJECT_PARSE_ROUTINE WinStaParse
;
75 OBJECT_DELETE_ROUTINE WinStaDelete
;
76 OBJECT_FIND_ROUTINE WinStaFind
;
77 OBJECT_CREATE_ROUTINE DesktopCreate
;
78 OBJECT_DELETE_ROUTINE DesktopDelete
;
79 } W32_OBJECT_CALLBACK
, *PW32_OBJECT_CALLBACK
;
82 PsEstablishWin32Callouts(
83 PW32_PROCESS_CALLBACK W32ProcessCallback
,
84 PW32_THREAD_CALLBACK W32ThreadCallback
,
85 PW32_OBJECT_CALLBACK W32ObjectCallback
,
88 ULONG W32ProcessSize
);
91 BOOL INTERNAL_CALL
GDI_CleanupForProcess (struct _EPROCESS
*Process
);
93 extern SSDT Win32kSSDT
[];
94 extern SSPT Win32kSSPT
[];
95 extern ULONG Win32kNumberOfSysCalls
;
97 PSHARED_SECTION_POOL SessionSharedSectionPool
= NULL
;
100 Win32kProcessCallback (struct _EPROCESS
*Process
,
103 PW32PROCESS Win32Process
;
105 Win32Process
= (PW32PROCESS
)Process
->Win32Process
;
108 DPRINT("Creating W32 process PID:%d at IRQ level: %lu\n", Process
->UniqueProcessId
, KeGetCurrentIrql());
110 InitializeListHead(&Win32Process
->ClassListHead
);
111 ExInitializeFastMutex(&Win32Process
->ClassListLock
);
113 InitializeListHead(&Win32Process
->MenuListHead
);
114 ExInitializeFastMutex(&Win32Process
->MenuListLock
);
116 InitializeListHead(&Win32Process
->PrivateFontListHead
);
117 ExInitializeFastMutex(&Win32Process
->PrivateFontListLock
);
119 InitializeListHead(&Win32Process
->DriverObjListHead
);
120 ExInitializeFastMutex(&Win32Process
->DriverObjListLock
);
122 Win32Process
->KeyboardLayout
= W32kGetDefaultKeyLayout();
124 if(Process
->Peb
!= NULL
)
126 /* map the gdi handle table to user land */
127 Process
->Peb
->GdiSharedHandleTable
= GDI_MapHandleTable(Process
);
130 /* setup process flags */
131 Win32Process
->Flags
= 0;
135 DPRINT("Destroying W32 process PID:%d at IRQ level: %lu\n", Process
->UniqueProcessId
, KeGetCurrentIrql());
136 IntRemoveProcessWndProcHandles((HANDLE
)Process
->UniqueProcessId
);
137 IntCleanupMenus(Process
, Win32Process
);
138 IntCleanupCurIcons(Process
, Win32Process
);
139 IntEngCleanupDriverObjs(Process
, Win32Process
);
140 CleanupMonitorImpl();
143 GDI_CleanupForProcess(Process
);
145 IntGraphicsCheck(FALSE
);
148 * Deregister logon application automatically
150 if(LogonProcess
== Win32Process
)
156 return STATUS_SUCCESS
;
161 Win32kThreadCallback (struct _ETHREAD
*Thread
,
164 struct _EPROCESS
*Process
;
165 PW32THREAD Win32Thread
;
167 Process
= Thread
->ThreadsProcess
;
168 Win32Thread
= Thread
->Tcb
.Win32Thread
;
171 HWINSTA hWinSta
= NULL
;
174 PUNICODE_STRING DesktopPath
;
175 PRTL_USER_PROCESS_PARAMETERS ProcessParams
= (Process
->Peb
? Process
->Peb
->ProcessParameters
: NULL
);
177 DPRINT("Creating W32 thread TID:%d at IRQ level: %lu\n", Thread
->Cid
.UniqueThread
, KeGetCurrentIrql());
180 * inherit the thread desktop and process window station (if not yet inherited) from the process startup
181 * info structure. See documentation of CreateProcess()
183 DesktopPath
= (ProcessParams
? ((ProcessParams
->DesktopInfo
.Length
> 0) ? &ProcessParams
->DesktopInfo
: NULL
) : NULL
);
184 Status
= IntParseDesktopPath(Process
,
188 if(NT_SUCCESS(Status
))
192 if(Process
!= CsrProcess
)
194 HWINSTA hProcessWinSta
= (HWINSTA
)InterlockedCompareExchangePointer((PVOID
)&Process
->Win32WindowStation
, (PVOID
)hWinSta
, NULL
);
195 if(hProcessWinSta
!= NULL
)
197 /* our process is already assigned to a different window station, we don't need the handle anymore */
209 Status
= ObReferenceObjectByHandle(hDesk
,
213 (PVOID
*)&Win32Thread
->Desktop
,
216 if(!NT_SUCCESS(Status
))
218 DPRINT1("Unable to reference thread desktop handle 0x%x\n", hDesk
);
219 Win32Thread
->Desktop
= NULL
;
223 Win32Thread
->IsExiting
= FALSE
;
224 IntDestroyCaret(Win32Thread
);
225 Win32Thread
->MessageQueue
= MsqCreateMessageQueue(Thread
);
226 Win32Thread
->KeyboardLayout
= W32kGetDefaultKeyLayout();
227 Win32Thread
->MessagePumpHookValue
= 0;
228 InitializeListHead(&Win32Thread
->WindowListHead
);
229 ExInitializeFastMutex(&Win32Thread
->WindowListLock
);
230 InitializeListHead(&Win32Thread
->W32CallbackListHead
);
234 DPRINT("Destroying W32 thread TID:%d at IRQ level: %lu\n", Thread
->Cid
.UniqueThread
, KeGetCurrentIrql());
236 Win32Thread
->IsExiting
= TRUE
;
237 HOOK_DestroyThreadHooks(Thread
);
238 UnregisterThreadHotKeys(Thread
);
239 DestroyThreadWindows(Thread
);
240 IntBlockInput(Win32Thread
, FALSE
);
241 MsqDestroyMessageQueue(Win32Thread
->MessageQueue
);
242 IntCleanupThreadCallbacks(Win32Thread
);
243 if(Win32Thread
->Desktop
!= NULL
)
245 ObDereferenceObject(Win32Thread
->Desktop
);
249 return STATUS_SUCCESS
;
252 /* Only used in ntuser/input.c KeyboardThreadMain(). If it's
253 not called there anymore, please delete */
255 Win32kInitWin32Thread(PETHREAD Thread
)
259 Process
= Thread
->ThreadsProcess
;
261 if (Process
->Win32Process
== NULL
)
263 /* FIXME - lock the process */
264 Process
->Win32Process
= ExAllocatePool(NonPagedPool
, sizeof(W32PROCESS
));
266 if (Process
->Win32Process
== NULL
)
267 return STATUS_NO_MEMORY
;
269 RtlZeroMemory(Process
->Win32Process
, sizeof(W32PROCESS
));
270 /* FIXME - unlock the process */
272 Win32kProcessCallback(Process
, TRUE
);
275 if (Thread
->Tcb
.Win32Thread
== NULL
)
277 Thread
->Tcb
.Win32Thread
= ExAllocatePool (NonPagedPool
, sizeof(W32THREAD
));
278 if (Thread
->Tcb
.Win32Thread
== NULL
)
279 return STATUS_NO_MEMORY
;
281 RtlZeroMemory(Thread
->Tcb
.Win32Thread
, sizeof(W32THREAD
));
283 Win32kThreadCallback(Thread
, TRUE
);
286 return(STATUS_SUCCESS
);
291 * This definition doesn't work
293 // BOOL STDCALL DllMain(VOID)
296 IN PDRIVER_OBJECT DriverObject
,
297 IN PUNICODE_STRING RegistryPath
)
301 W32_OBJECT_CALLBACK Win32kObjectCallbacks
;
304 * Register user mode call interface
305 * (system service table index = 1)
307 Result
= KeAddSystemServiceTable (Win32kSSDT
,
309 Win32kNumberOfSysCalls
,
314 DPRINT1("Adding system services failed!\n");
315 return STATUS_UNSUCCESSFUL
;
319 * Register Object Manager Callbacks
321 Win32kObjectCallbacks
.WinStaCreate
= IntWinStaObjectOpen
;
322 Win32kObjectCallbacks
.WinStaParse
= IntWinStaObjectParse
;
323 Win32kObjectCallbacks
.WinStaDelete
= IntWinStaObjectDelete
;
324 Win32kObjectCallbacks
.WinStaFind
= IntWinStaObjectFind
;
325 Win32kObjectCallbacks
.DesktopCreate
= IntDesktopObjectCreate
;
326 Win32kObjectCallbacks
.DesktopDelete
= IntDesktopObjectDelete
;
328 * Register our per-process and per-thread structures.
330 PsEstablishWin32Callouts (Win32kProcessCallback
,
331 Win32kThreadCallback
,
332 &Win32kObjectCallbacks
,
337 Status
= IntUserCreateSharedSectionPool(48 * 1024 * 1024, /* 48 MB by default */
338 &SessionSharedSectionPool
);
339 if (!NT_SUCCESS(Status
))
341 DPRINT1("Failed to initialize the shared section pool: Status 0x%x\n", Status
);
344 Status
= InitWindowStationImpl();
345 if (!NT_SUCCESS(Status
))
347 DPRINT1("Failed to initialize window station implementation!\n");
348 return STATUS_UNSUCCESSFUL
;
351 Status
= InitClassImpl();
352 if (!NT_SUCCESS(Status
))
354 DPRINT1("Failed to initialize window class implementation!\n");
355 return STATUS_UNSUCCESSFUL
;
358 Status
= InitDesktopImpl();
359 if (!NT_SUCCESS(Status
))
361 DPRINT1("Failed to initialize desktop implementation!\n");
362 return STATUS_UNSUCCESSFUL
;
365 Status
= InitWindowImpl();
366 if (!NT_SUCCESS(Status
))
368 DPRINT1("Failed to initialize window implementation!\n");
369 return STATUS_UNSUCCESSFUL
;
372 Status
= InitMenuImpl();
373 if (!NT_SUCCESS(Status
))
375 DPRINT1("Failed to initialize menu implementation!\n");
376 return STATUS_UNSUCCESSFUL
;
379 Status
= InitInputImpl();
380 if (!NT_SUCCESS(Status
))
382 DPRINT1("Failed to initialize input implementation.\n");
386 Status
= InitKeyboardImpl();
387 if (!NT_SUCCESS(Status
))
389 DPRINT1("Failed to initialize keyboard implementation.\n");
393 Status
= InitMonitorImpl();
394 if (!NT_SUCCESS(Status
))
396 DbgPrint("Failed to initialize monitor implementation!\n");
397 return STATUS_UNSUCCESSFUL
;
400 Status
= MsqInitializeImpl();
401 if (!NT_SUCCESS(Status
))
403 DPRINT1("Failed to initialize message queue implementation.\n");
407 Status
= InitTimerImpl();
408 if (!NT_SUCCESS(Status
))
410 DPRINT1("Failed to initialize timer implementation.\n");
414 Status
= InitAcceleratorImpl();
415 if (!NT_SUCCESS(Status
))
417 DPRINT1("Failed to initialize accelerator implementation.\n");
421 Status
= InitGuiCheckImpl();
422 if (!NT_SUCCESS(Status
))
424 DPRINT1("Failed to initialize GUI check implementation.\n");
428 InitGdiObjectHandleTable ();
430 /* Initialize FreeType library */
431 if (! InitFontSupport())
433 DPRINT1("Unable to initialize font support\n");
434 return STATUS_UNSUCCESSFUL
;
437 /* Create stock objects, ie. precreated objects commonly
438 used by win32 applications */
439 CreateStockObjects();
440 CreateSysColorObjects();
444 return STATUS_SUCCESS
;
449 Win32kInitialize (VOID
)