1 /* $Id: init.c,v 1.34 2002/05/22 15:55:51 ekohl Exp $
3 * init.c - Session Manager initialization
5 * ReactOS Operating System
7 * --------------------------------------------------------------------
9 * This software is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU General Public License as
11 * published by the Free Software Foundation; either version 2 of the
12 * License, or (at your option) any later version.
14 * This software is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this software; see the file COPYING.LIB. If not, write
21 * to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge,
24 * --------------------------------------------------------------------
26 * 19990530 (Emanuele Aliberti)
27 * Compiled successfully with egcs 1.1.2
30 #include <ntdll/rtl.h>
37 /* TYPES ********************************************************************/
40 /* GLOBAL VARIABLES *********************************************************/
42 HANDLE SmApiPort
= INVALID_HANDLE_VALUE
;
43 HANDLE DbgSsApiPort
= INVALID_HANDLE_VALUE
;
44 HANDLE DbgUiApiPort
= INVALID_HANDLE_VALUE
;
46 PWSTR SmSystemEnvironment
= NULL
;
49 /* FUNCTIONS ****************************************************************/
52 static NTSTATUS STDCALL
53 SmObjectDirectoryQueryRoutine(PWSTR ValueName
,
60 OBJECT_ATTRIBUTES ObjectAttributes
;
61 UNICODE_STRING UnicodeString
;
62 HANDLE WindowsDirectory
;
66 PrintString("ValueName '%S' Type %lu Length %lu\n", ValueName
, ValueType
, ValueLength
);
67 PrintString("ValueData '%S'\n", (PWSTR
)ValueData
);
70 RtlInitUnicodeString(&UnicodeString
,
73 InitializeObjectAttributes(&ObjectAttributes
,
79 Status
= ZwCreateDirectoryObject(&WindowsDirectory
,
88 SmCreateObjectDirectories(VOID
)
90 RTL_QUERY_REGISTRY_TABLE QueryTable
[2];
93 RtlZeroMemory(&QueryTable
,
96 QueryTable
[0].Name
= L
"ObjectDirectories";
97 QueryTable
[0].QueryRoutine
= SmObjectDirectoryQueryRoutine
;
99 Status
= RtlQueryRegistryValues(RTL_REGISTRY_CONTROL
,
100 L
"\\Session Manager",
109 static NTSTATUS STDCALL
110 SmDosDevicesQueryRoutine(PWSTR ValueName
,
117 OBJECT_ATTRIBUTES ObjectAttributes
;
118 UNICODE_STRING DeviceName
;
119 UNICODE_STRING LinkName
;
121 WCHAR LinkBuffer
[80];
122 NTSTATUS Status
= STATUS_SUCCESS
;
125 PrintString("ValueName '%S' Type %lu Length %lu\n", ValueName
, ValueType
, ValueLength
);
126 PrintString("ValueData '%S'\n", (PWSTR
)ValueData
);
129 if (ValueType
= REG_SZ
)
131 swprintf(LinkBuffer
, L
"\\??\\%s",
133 RtlInitUnicodeString(&LinkName
,
135 RtlInitUnicodeString(&DeviceName
,
139 PrintString("SM: Linking %wZ --> %wZ\n",
144 /* create symbolic link */
145 InitializeObjectAttributes(&ObjectAttributes
,
150 Status
= NtCreateSymbolicLinkObject(&LinkHandle
,
151 SYMBOLIC_LINK_ALL_ACCESS
,
154 if (!NT_SUCCESS(Status
))
156 PrintString("SmDosDevicesQueryRoutine: NtCreateSymbolicLink( %wZ --> %wZ ) failed!\n",
168 SmInitDosDevices(VOID
)
170 RTL_QUERY_REGISTRY_TABLE QueryTable
[2];
173 RtlZeroMemory(&QueryTable
,
176 QueryTable
[0].QueryRoutine
= SmDosDevicesQueryRoutine
;
178 Status
= RtlQueryRegistryValues(RTL_REGISTRY_CONTROL
,
179 L
"\\Session Manager\\DOS Devices",
187 static NTSTATUS STDCALL
188 SmRunBootAppsQueryRoutine(PWSTR ValueName
,
196 PRTL_USER_PROCESS_PARAMETERS ProcessParameters
;
197 RTL_PROCESS_INFO ProcessInfo
;
198 WCHAR Description
[256];
199 WCHAR ImagePath
[256];
200 WCHAR CommandLine
[256];
203 NTSTATUS Status
= STATUS_SUCCESS
;
206 PrintString("ValueName '%S' Type %lu Length %lu\n", ValueName
, ValueType
, ValueLength
);
207 PrintString("ValueData '%S'\n", (PWSTR
)ValueData
);
210 /* Extract the description */
211 p1
= wcschr((PWSTR
)ValueData
, L
' ');
212 len
= p1
- (PWSTR
)ValueData
;
213 memcpy(Description
,ValueData
, len
* sizeof(WCHAR
));
214 Description
[len
] = 0;
216 /* Extract the full image path */
218 p2
= wcschr(p1
, L
' ');
223 memcpy(ImagePath
, p1
, len
* sizeof(WCHAR
));
226 /* Extract the command line */
234 wcscpy(CommandLine
, p2
);
238 PrintString("Running %S...\n", Description
);
239 PrintString("Executable: '%S'\n", ImagePath
);
240 PrintString("CommandLine: '%S'\n", CommandLine
);
244 /* initialize executable path */
245 wcscpy(UnicodeBuffer
, L
"\\??\\");
246 wcscat(UnicodeBuffer
, SharedUserData
->NtSystemRoot
);
247 wcscat(UnicodeBuffer
, L
"\\system32\\csrss.exe");
248 RtlInitUnicodeString(&ImagePathString
,
251 RtlInitUnicodeString(&CommandLineString
,
254 RtlCreateProcessParameters(&ProcessParameters
,
265 Status
= RtlCreateUserProcess(&UnicodeString
,
266 OBJ_CASE_INSENSITIVE
,
276 RtlDestroyProcessParameters (ProcessParameters
);
278 /* FIXME: wait for process termination */
284 return(STATUS_SUCCESS
);
289 * Run native applications listed in the registry.
292 * \Registry\Machine\SYSTEM\CurrentControlSet\Control\Session Manager
294 * Value (format: "<description> <executable> <command line>":
295 * BootExecute = "autocheck autochk *"
300 RTL_QUERY_REGISTRY_TABLE QueryTable
[2];
303 RtlZeroMemory(&QueryTable
,
306 QueryTable
[0].Name
= L
"BootExecute";
307 QueryTable
[0].QueryRoutine
= SmRunBootAppsQueryRoutine
;
309 Status
= RtlQueryRegistryValues(RTL_REGISTRY_CONTROL
,
310 L
"\\Session Manager",
314 if (!NT_SUCCESS(Status
))
316 PrintString("SmRunBootApps: RtlQueryRegistryValues() failed! (Status %lx)\n", Status
);
319 // PrintString("*** System stopped ***\n");
327 SmProcessFileRenameList(VOID
)
330 PrintString("SmProcessFileRenameList() called\n");
334 PrintString("SmProcessFileRenameList() done\n");
337 return(STATUS_SUCCESS
);
341 static NTSTATUS STDCALL
342 SmPagingFilesQueryRoutine(PWSTR ValueName
,
349 UNICODE_STRING FileName
;
350 LARGE_INTEGER InitialSize
;
351 LARGE_INTEGER MaximumSize
;
355 PrintString("ValueName '%S' Type %lu Length %lu\n", ValueName
, ValueType
, ValueLength
);
356 PrintString("ValueData '%S'\n", (PWSTR
)ValueData
);
359 RtlInitUnicodeString(&FileName
,
364 * read initial and maximum size from the registry or use default values
366 * Format: "<path>[ <initial_size>[ <maximum_size>]]"
369 InitialSize
.QuadPart
= 50 * 4096;
370 MaximumSize
.QuadPart
= 80 * 4096;
372 Status
= NtCreatePagingFile(&FileName
,
377 return(STATUS_SUCCESS
);
382 SmCreatePagingFiles(VOID
)
384 RTL_QUERY_REGISTRY_TABLE QueryTable
[2];
387 RtlZeroMemory(&QueryTable
,
390 QueryTable
[0].Name
= L
"PagingFiles";
391 QueryTable
[0].QueryRoutine
= SmPagingFilesQueryRoutine
;
393 Status
= RtlQueryRegistryValues(RTL_REGISTRY_CONTROL
,
394 L
"\\Session Manager\\Memory Management",
404 SmSetEnvironmentVariables(VOID
)
406 UNICODE_STRING EnvVariable
;
407 UNICODE_STRING EnvValue
;
408 UNICODE_STRING EnvExpandedValue
;
409 ULONG ExpandedLength
;
410 WCHAR ExpandBuffer
[512];
411 WCHAR ValueBuffer
[MAX_PATH
];
414 * The following environment variables are read from the registry.
415 * Because the registry does not work yet, the environment variables
416 * are set one by one, using information from the shared user page.
418 * Variables (example):
419 * SystemRoot = C:\reactos
423 * Path = %SystemRoot%\system32;%SystemRoot%
424 * windir = %SystemRoot%
427 /* copy system root into value buffer */
428 wcscpy (ValueBuffer
, SharedUserData
->NtSystemRoot
);
430 /* set "SystemRoot = C:\reactos" */
431 RtlInitUnicodeString (&EnvVariable
,
433 RtlInitUnicodeString (&EnvValue
,
435 RtlSetEnvironmentVariable (&SmSystemEnvironment
,
439 /* cut off trailing path */
442 /* Set "SystemDrive = C:" */
443 RtlInitUnicodeString (&EnvVariable
,
445 RtlInitUnicodeString (&EnvValue
,
447 RtlSetEnvironmentVariable (&SmSystemEnvironment
,
452 /* Set "OS = ReactOS" */
453 RtlInitUnicodeString (&EnvVariable
,
455 RtlInitUnicodeString (&EnvValue
,
457 RtlSetEnvironmentVariable (&SmSystemEnvironment
,
462 /* Set "Path = %SystemRoot%\system32;%SystemRoot%" */
463 RtlInitUnicodeString (&EnvVariable
,
465 RtlInitUnicodeString (&EnvValue
,
466 L
"%SystemRoot%\\system32;%SystemRoot%");
467 EnvExpandedValue
.Length
= 0;
468 EnvExpandedValue
.MaximumLength
= 512 * sizeof(WCHAR
);
469 EnvExpandedValue
.Buffer
= ExpandBuffer
;
471 RtlExpandEnvironmentStrings_U (SmSystemEnvironment
,
475 RtlSetEnvironmentVariable (&SmSystemEnvironment
,
479 /* Set "windir = %SystemRoot%" */
480 RtlInitUnicodeString (&EnvVariable
,
482 RtlInitUnicodeString (&EnvValue
,
484 EnvExpandedValue
.Length
= 0;
485 EnvExpandedValue
.MaximumLength
= 512 * sizeof(WCHAR
);
486 EnvExpandedValue
.Buffer
= ExpandBuffer
;
488 RtlExpandEnvironmentStrings_U (SmSystemEnvironment
,
492 RtlSetEnvironmentVariable (&SmSystemEnvironment
,
496 return(STATUS_SUCCESS
);
501 InitSessionManager(HANDLE Children
[])
504 UNICODE_STRING UnicodeString
;
505 OBJECT_ATTRIBUTES ObjectAttributes
;
506 UNICODE_STRING CmdLineW
;
507 PRTL_USER_PROCESS_PARAMETERS ProcessParameters
;
508 RTL_PROCESS_INFO ProcessInfo
;
509 HANDLE CsrssInitEvent
;
510 WCHAR UnicodeBuffer
[MAX_PATH
];
512 /* Create object directories */
513 Status
= SmCreateObjectDirectories();
514 if (!NT_SUCCESS(Status
))
516 PrintString("SM: Failed to create object directories! (Status %lx)\n", Status
);
520 /* Create the "\SmApiPort" object (LPC) */
521 RtlInitUnicodeString(&UnicodeString
,
523 InitializeObjectAttributes(&ObjectAttributes
,
529 Status
= NtCreatePort(&SmApiPort
,
534 if (!NT_SUCCESS(Status
))
540 DisplayString (L
"SM: \\SmApiPort created...\n");
543 /* Create two threads for "\SmApiPort" */
544 RtlCreateUserThread(NtCurrentProcess(),
550 (PTHREAD_START_ROUTINE
)SmApiThread
,
555 RtlCreateUserThread(NtCurrentProcess(),
561 (PTHREAD_START_ROUTINE
)SmApiThread
,
566 /* Create the system environment */
567 Status
= RtlCreateEnvironment(FALSE
,
568 &SmSystemEnvironment
);
569 if (!NT_SUCCESS(Status
))
574 DisplayString(L
"SM: System Environment created\n");
577 /* Define symbolic links to kernel devices (MS-DOS names) */
578 Status
= SmInitDosDevices();
579 if (!NT_SUCCESS(Status
))
581 PrintString("SM: Failed to create dos device links! (Status %lx)\n", Status
);
585 /* Run all programs in the boot execution list */
586 Status
= SmRunBootApps();
587 if (!NT_SUCCESS(Status
))
589 PrintString("SM: Failed to run boot applications! (Status %lx)\n", Status
);
593 /* Process the file rename list */
594 Status
= SmProcessFileRenameList();
595 if (!NT_SUCCESS(Status
))
597 PrintString("SM: Failed to process the file rename list (Status %lx)\n", Status
);
601 /* FIXME: Load the well known DLLs */
604 /* Create paging files */
605 Status
= SmCreatePagingFiles();
606 if (!NT_SUCCESS(Status
))
608 PrintString("SM: Failed to create paging files (Status %lx)\n", Status
);
612 /* Load remaining registry hives */
613 NtInitializeRegistry(FALSE
);
615 /* Set environment variables from registry */
616 Status
= SmSetEnvironmentVariables();
617 if (!NT_SUCCESS(Status
))
619 PrintString("SM: Failed to initialize the system environment (Status %lx)\n", Status
);
623 /* Load the kernel mode driver win32k.sys */
624 RtlInitUnicodeString(&CmdLineW
,
625 L
"\\SystemRoot\\system32\\drivers\\win32k.sys");
626 Status
= NtLoadDriver(&CmdLineW
);
628 if (!NT_SUCCESS(Status
))
635 RtlInitUnicodeString(&UnicodeString
,
637 InitializeObjectAttributes(&ObjectAttributes
,
642 Status
= NtCreateEvent(&CsrssInitEvent
,
647 if (!NT_SUCCESS(Status
))
649 DbgPrint("Failed to create csrss notification event\n");
653 * Start the Win32 subsystem (csrss.exe)
656 /* initialize executable path */
657 wcscpy(UnicodeBuffer
, L
"\\??\\");
658 wcscat(UnicodeBuffer
, SharedUserData
->NtSystemRoot
);
659 wcscat(UnicodeBuffer
, L
"\\system32\\csrss.exe");
660 RtlInitUnicodeString(&UnicodeString
,
663 RtlCreateProcessParameters(&ProcessParameters
,
674 Status
= RtlCreateUserProcess(&UnicodeString
,
675 OBJ_CASE_INSENSITIVE
,
685 RtlDestroyProcessParameters (ProcessParameters
);
687 if (!NT_SUCCESS(Status
))
689 DisplayString(L
"SM: Loading csrss.exe failed!\n");
693 NtWaitForSingleObject(CsrssInitEvent
,
697 Children
[CHILD_CSRSS
] = ProcessInfo
.ProcessHandle
;
700 * Start the logon process (winlogon.exe)
703 /* initialize executable path */
704 wcscpy(UnicodeBuffer
, L
"\\??\\");
705 wcscat(UnicodeBuffer
, SharedUserData
->NtSystemRoot
);
706 wcscat(UnicodeBuffer
, L
"\\system32\\winlogon.exe");
707 RtlInitUnicodeString(&UnicodeString
,
710 RtlCreateProcessParameters(&ProcessParameters
,
721 Status
= RtlCreateUserProcess(&UnicodeString
,
722 OBJ_CASE_INSENSITIVE
,
732 RtlDestroyProcessParameters(ProcessParameters
);
734 if (!NT_SUCCESS(Status
))
736 DisplayString(L
"SM: Loading winlogon.exe failed!\n");
737 NtTerminateProcess(Children
[CHILD_CSRSS
],
741 Children
[CHILD_WINLOGON
] = ProcessInfo
.ProcessHandle
;
743 /* Create the \DbgSsApiPort object (LPC) */
744 RtlInitUnicodeString(&UnicodeString
,
746 InitializeObjectAttributes(&ObjectAttributes
,
752 Status
= NtCreatePort(&DbgSsApiPort
,
758 if (!NT_SUCCESS(Status
))
763 DisplayString(L
"SM: DbgSsApiPort created...\n");
766 /* Create the \DbgUiApiPort object (LPC) */
767 RtlInitUnicodeString(&UnicodeString
,
769 InitializeObjectAttributes(&ObjectAttributes
,
775 Status
= NtCreatePort(&DbgUiApiPort
,
780 if (!NT_SUCCESS(Status
))
785 DisplayString (L
"SM: DbgUiApiPort created...\n");
788 return(STATUS_SUCCESS
);