From 5ea38c2861ab080d6b28f5451b21f8b0589ef190 Mon Sep 17 00:00:00 2001 From: Emanuele Aliberti Date: Sat, 19 Feb 2005 22:58:18 +0000 Subject: [PATCH] SM: subsystem registration (partial) - merged duplicate code in process creation - experimental implementation of env subsystem registration svn path=/trunk/; revision=13654 --- reactos/subsys/smss/client.c | 84 +++++++++- reactos/subsys/smss/initdosdev.c | 2 +- reactos/subsys/smss/initreg.c | 2 +- reactos/subsys/smss/initrun.c | 68 +++----- reactos/subsys/smss/initss.c | 92 ++++------- reactos/subsys/smss/makefile | 6 +- reactos/subsys/smss/print.c | 56 +++++++ reactos/subsys/smss/smapi.c | 266 ++++++++++++++++++++----------- reactos/subsys/smss/smapicomp.c | 27 ++++ reactos/subsys/smss/smapiexec.c | 113 +++++++++++++ reactos/subsys/smss/smss.c | 6 + reactos/subsys/smss/smss.h | 24 ++- 12 files changed, 520 insertions(+), 226 deletions(-) create mode 100644 reactos/subsys/smss/print.c create mode 100644 reactos/subsys/smss/smapicomp.c create mode 100644 reactos/subsys/smss/smapiexec.c diff --git a/reactos/subsys/smss/client.c b/reactos/subsys/smss/client.c index 78d101147a8..66e9050a827 100644 --- a/reactos/subsys/smss/client.c +++ b/reactos/subsys/smss/client.c @@ -26,6 +26,7 @@ #define NTOS_MODE_USER #include #include "smss.h" +#include #define NDEBUG #include @@ -41,6 +42,39 @@ struct _SM_CLIENT_DIRECTORY } SmpClientDirectory; +#if 0 +/********************************************************************** + * SmpRegisterSmss/0 + */ +static NTSTATUS +SmpRegisterSmss(VOID) +{ + NTSTATUS Status = STATUS_SUCCESS; + UNICODE_STRING SbApiPortName = {0,0,NULL}; + HANDLE hSmApiPort = (HANDLE) 0; + + DPRINT("SM: %s called\n",__FUNCTION__); + + Status = SmConnectApiPort(& SbApiPortName, + (HANDLE) -1, + IMAGE_SUBSYSTEM_NATIVE, + & hSmApiPort); + if(!NT_SUCCESS(Status)) + { + DPRINT("SM: %s: SMDLL!SmConnectApiPort failed (Status=0x%08lx)\n",__FUNCTION__,Status); + return Status; + } + Status = SmCompleteSession (hSmApiPort, (HANDLE)0, hSmApiPort); + if(!NT_SUCCESS(Status)) + { + DPRINT("SM: %s: SMDLL!SmCompleteSession failed (Status=0x%08lx)\n",__FUNCTION__,Status); + return Status; + } + NtClose(hSmApiPort); + return Status; +} +#endif + /********************************************************************** * SmInitializeClientManagement/0 */ @@ -51,11 +85,22 @@ SmInitializeClientManagement (VOID) RtlInitializeCriticalSection(& SmpClientDirectory.Lock); SmpClientDirectory.Count = 0; SmpClientDirectory.Client = NULL; +#if 0 + /* Register IMAGE_SUBSYSTE_NATIVE to be managed by SM */ + return SmpRegisterSmss(); +#endif return STATUS_SUCCESS; + } /********************************************************************** * SmpLookupClient/1 + * + * DESCRIPTION + * Lookup the subsystem server descriptor given its image ID. + * + * SIDE EFFECTS + * SmpClientDirectory.Lock is released only on success. */ static PSM_CLIENT_DATA STDCALL SmpLookupClient (USHORT SubsystemId) @@ -70,22 +115,31 @@ SmpLookupClient (USHORT SubsystemId) Client = SmpClientDirectory.Client; while (NULL != Client) { - if (SubsystemId == Client->SubsystemId) break; + if (SubsystemId == Client->SubsystemId) + { + RtlLeaveCriticalSection (& SmpClientDirectory.Lock); + return Client; + } Client = Client->Next; } } - RtlLeaveCriticalSection (& SmpClientDirectory.Lock); + /* + * Note that we do *not* release SmpClientDirectory.Lock here + * because SmpLookupClient is called to FAIL when SubsystemId + * is not registered yet. + */ return Client; } /********************************************************************** - * SmpCreateClient/1 + * SmpCreateClient/2 */ NTSTATUS STDCALL SmCreateClient(PSM_PORT_MESSAGE Request, PSM_CLIENT_DATA * ClientData) { PSM_CLIENT_DATA pClient = NULL; PSM_CONNECT_DATA ConnectData = (PSM_CONNECT_DATA) ((PBYTE) Request) + sizeof (LPC_REQUEST); + ULONG SbApiPortNameSize = SM_CONNECT_DATA_SIZE(*Request); DPRINT("SM: %s called\n", __FUNCTION__); @@ -94,9 +148,12 @@ SmCreateClient(PSM_PORT_MESSAGE Request, PSM_CLIENT_DATA * ClientData) */ if (SmpLookupClient(ConnectData->Subsystem)) { - DbgPrint("SMSS: %s: attempt to register again subsystem %d.\n",__FUNCTION__,0); + DPRINT("SMSS: %s: attempt to register again subsystem %d.\n", + __FUNCTION__, + ConnectData->Subsystem); return STATUS_UNSUCCESSFUL; } + DPRINT("SM: %s: registering subsystem %d \n", __FUNCTION__, ConnectData->Subsystem); /* * Allocate the storage for client data */ @@ -112,13 +169,17 @@ SmCreateClient(PSM_PORT_MESSAGE Request, PSM_CLIENT_DATA * ClientData) * Initialize the client data */ pClient->SubsystemId = ConnectData->Subsystem; - pClient->Initialized = FALSE; - // TODO + pClient->Initialized = (IMAGE_SUBSYSTEM_NATIVE == pClient->SubsystemId); + if (SbApiPortNameSize > 0) + { + RtlCopyMemory (pClient->SbApiPortName, + ConnectData->SbName, + SbApiPortNameSize); + } /* * Insert the new descriptor in the * client directory. */ - RtlEnterCriticalSection (& SmpClientDirectory.Lock); if (NULL == SmpClientDirectory.Client) { SmpClientDirectory.Client = pClient; @@ -132,8 +193,15 @@ SmCreateClient(PSM_PORT_MESSAGE Request, PSM_CLIENT_DATA * ClientData) } pClient->Next = NULL; ++ SmpClientDirectory.Count; + /* + * Note we unlock the client directory here, because + * it was locked by SmpLookupClient on failure. + */ RtlLeaveCriticalSection (& SmpClientDirectory.Lock); - if (ClientData) *ClientData = pClient; + if (ClientData) + { + *ClientData = pClient; + } return STATUS_SUCCESS; } diff --git a/reactos/subsys/smss/initdosdev.c b/reactos/subsys/smss/initdosdev.c index 30e839f6720..f2698e94f57 100644 --- a/reactos/subsys/smss/initdosdev.c +++ b/reactos/subsys/smss/initdosdev.c @@ -1,6 +1,6 @@ /* $Id: init.c 13449 2005-02-06 21:55:07Z ea $ * - * initdosdev.c - Define symbolic links to kernel devices (MS-DOS names) + * initdosdev.c - Define symbolic links to kernel devices (MS-DOS names). * * ReactOS Operating System * diff --git a/reactos/subsys/smss/initreg.c b/reactos/subsys/smss/initreg.c index 6bfbfacf7be..76ab72014c7 100644 --- a/reactos/subsys/smss/initreg.c +++ b/reactos/subsys/smss/initreg.c @@ -1,6 +1,6 @@ /* $Id: init.c 13449 2005-02-06 21:55:07Z ea $ * - * initenv.c - Environment initialization + * initenv.c - Hive loading * * ReactOS Operating System * diff --git a/reactos/subsys/smss/initrun.c b/reactos/subsys/smss/initrun.c index 841c988b844..1c0ecdc01bc 100644 --- a/reactos/subsys/smss/initrun.c +++ b/reactos/subsys/smss/initrun.c @@ -32,6 +32,9 @@ HANDLE Children[2] = {0, 0}; /* csrss, winlogon */ +/********************************************************************** + * SmpRunBootAppsQueryRoutine/6 + */ static NTSTATUS STDCALL SmpRunBootAppsQueryRoutine(PWSTR ValueName, ULONG ValueType, @@ -40,14 +43,10 @@ SmpRunBootAppsQueryRoutine(PWSTR ValueName, PVOID Context, PVOID EntryContext) { - PRTL_USER_PROCESS_PARAMETERS ProcessParameters; - RTL_PROCESS_INFO ProcessInfo; - UNICODE_STRING ImagePathString; - UNICODE_STRING CommandLineString; - WCHAR Description[256]; - WCHAR ImageName[256]; - WCHAR ImagePath[256]; - WCHAR CommandLine[256]; + WCHAR Description [MAX_PATH]; + WCHAR ImageName [MAX_PATH]; + WCHAR ImagePath [MAX_PATH]; + WCHAR CommandLine [MAX_PATH]; PWSTR p1, p2; ULONG len; NTSTATUS Status; @@ -96,54 +95,23 @@ SmpRunBootAppsQueryRoutine(PWSTR ValueName, wcscat(ImagePath, ImageName); wcscat(ImagePath, L".exe"); - RtlInitUnicodeString(&ImagePathString, - ImagePath); - - RtlInitUnicodeString(&CommandLineString, - CommandLine); - - RtlCreateProcessParameters(&ProcessParameters, - &ImagePathString, - NULL, - NULL, - &CommandLineString, - NULL, - NULL, - NULL, - NULL, - NULL); - - Status = RtlCreateUserProcess(&ImagePathString, - OBJ_CASE_INSENSITIVE, - ProcessParameters, + /* Create NT process */ + Status = SmCreateUserProcess (ImagePath, + CommandLine, + TRUE, /* wait */ NULL, - NULL, - NULL, - FALSE, - NULL, - NULL, - &ProcessInfo); - if (!NT_SUCCESS(Status)) - { - DPRINT1("Running %s failed (Status %lx)\n", Description, Status); - return(STATUS_SUCCESS); - } - - RtlDestroyProcessParameters(ProcessParameters); - - /* Wait for process termination */ - NtWaitForSingleObject(ProcessInfo.ProcessHandle, - FALSE, - NULL); - - NtClose(ProcessInfo.ThreadHandle); - NtClose(ProcessInfo.ProcessHandle); + TRUE, /* terminate */ + NULL); return(STATUS_SUCCESS); } -/* +/********************************************************************** + * SmRunBootApplications/0 + * + * DESCRIPTION + * * Run native applications listed in the registry. * * Key: diff --git a/reactos/subsys/smss/initss.c b/reactos/subsys/smss/initss.c index 0f804563e24..12085922c1e 100644 --- a/reactos/subsys/smss/initss.c +++ b/reactos/subsys/smss/initss.c @@ -26,6 +26,7 @@ #include "smss.h" + #include #define NDEBUG @@ -49,6 +50,9 @@ * e) make optional subsystems loadable (again: they must be described in the registry * key Optional="Posix Os2" to be allowed to run) */ + +/********************************************************************** + */ NTSTATUS SmLoadSubsystems(VOID) { @@ -56,7 +60,7 @@ SmLoadSubsystems(VOID) NTSTATUS Status; DPRINT("SM: loading subsystems\n"); - + /* Load kernel mode subsystem (aka win32k.sys) */ RtlRosInitUnicodeStringFromLiteral(&ImageInfo.ModuleName, L"\\SystemRoot\\system32\\win32k.sys"); @@ -84,10 +88,9 @@ SmRunCsrss(VOID) NTSTATUS Status; UNICODE_STRING UnicodeString; OBJECT_ATTRIBUTES ObjectAttributes; - PRTL_USER_PROCESS_PARAMETERS ProcessParameters; RTL_PROCESS_INFO ProcessInfo; HANDLE CsrssInitEvent; - WCHAR UnicodeBuffer[MAX_PATH]; + WCHAR ImagePath [MAX_PATH]; DPRINT("SM: initializing csrss\n"); @@ -114,36 +117,17 @@ SmRunCsrss(VOID) */ /* initialize executable path */ - wcscpy(UnicodeBuffer, L"\\??\\"); - wcscat(UnicodeBuffer, SharedUserData->NtSystemRoot); - wcscat(UnicodeBuffer, L"\\system32\\csrss.exe"); - RtlInitUnicodeString(&UnicodeString, - UnicodeBuffer); + wcscpy(ImagePath, L"\\??\\"); + wcscat(ImagePath, SharedUserData->NtSystemRoot); + wcscat(ImagePath, L"\\system32\\csrss.exe"); - RtlCreateProcessParameters(&ProcessParameters, - &UnicodeString, - NULL, - NULL, - NULL, - SmSystemEnvironment, - NULL, - NULL, - NULL, - NULL); - - Status = RtlCreateUserProcess(&UnicodeString, - OBJ_CASE_INSENSITIVE, - ProcessParameters, + Status = SmCreateUserProcess(ImagePath, + L"", + FALSE, /* wait */ NULL, - NULL, - NULL, - FALSE, - NULL, - NULL, - &ProcessInfo); - - RtlDestroyProcessParameters (ProcessParameters); - + FALSE, /* terminate */ + & ProcessInfo); + if (!NT_SUCCESS(Status)) { DPRINT("SM: %s: Loading csrss.exe failed!\n", __FUNCTION__); @@ -162,11 +146,9 @@ SmRunCsrss(VOID) NTSTATUS SmRunWinlogon(VOID) { - NTSTATUS Status; - UNICODE_STRING UnicodeString; - PRTL_USER_PROCESS_PARAMETERS ProcessParameters; + NTSTATUS Status = STATUS_SUCCESS; RTL_PROCESS_INFO ProcessInfo; - WCHAR UnicodeBuffer[MAX_PATH]; + WCHAR ImagePath [MAX_PATH]; /* * Start the logon process (winlogon.exe) @@ -175,43 +157,23 @@ SmRunWinlogon(VOID) DPRINT("SM: starting winlogon\n"); /* initialize executable path */ - wcscpy(UnicodeBuffer, L"\\??\\"); - wcscat(UnicodeBuffer, SharedUserData->NtSystemRoot); - wcscat(UnicodeBuffer, L"\\system32\\winlogon.exe"); - RtlInitUnicodeString(&UnicodeString, - UnicodeBuffer); + wcscpy(ImagePath, L"\\??\\"); + wcscat(ImagePath, SharedUserData->NtSystemRoot); + wcscat(ImagePath, L"\\system32\\winlogon.exe"); - RtlCreateProcessParameters(&ProcessParameters, - &UnicodeString, - NULL, - NULL, - NULL, - SmSystemEnvironment, - NULL, - NULL, - NULL, - NULL); - - Status = RtlCreateUserProcess(&UnicodeString, - OBJ_CASE_INSENSITIVE, - ProcessParameters, + Status = SmCreateUserProcess(ImagePath, + L"", + FALSE, /* wait */ NULL, - NULL, - NULL, - FALSE, - NULL, - NULL, - &ProcessInfo); - - RtlDestroyProcessParameters(ProcessParameters); - + FALSE, /* terminate */ + & ProcessInfo); if (!NT_SUCCESS(Status)) { DPRINT("SM: %s: Loading winlogon.exe failed!\n", __FUNCTION__); - NtTerminateProcess(Children[CHILD_CSRSS], - 0); + NtTerminateProcess(Children[CHILD_CSRSS], 0); return(Status); } + Children[CHILD_WINLOGON] = ProcessInfo.ProcessHandle; return Status; diff --git a/reactos/subsys/smss/makefile b/reactos/subsys/smss/makefile index 12af5d6800f..823310ec167 100644 --- a/reactos/subsys/smss/makefile +++ b/reactos/subsys/smss/makefile @@ -6,6 +6,8 @@ TARGET_TYPE = program TARGET_APPTYPE = native +TARGET_SDKLIBS = ntdll.a smdll.a + TARGET_NAME = smss TARGET_INSTALLDIR = system32 @@ -19,8 +21,8 @@ TARGET_OBJECTS = $(TARGET_NAME).o \ init.o initheap.o initenv.o initobdir.o initdosdev.o \ initrun.o initmv.o initwkdll.o initpage.o initss.o \ initreg.o \ - smapi.o \ - client.o debug.o + smapi.o smapicomp.o smapiexec.o \ + client.o debug.o print.o include $(PATH_TO_TOP)/rules.mak diff --git a/reactos/subsys/smss/print.c b/reactos/subsys/smss/print.c new file mode 100644 index 00000000000..fccc3ac37d6 --- /dev/null +++ b/reactos/subsys/smss/print.c @@ -0,0 +1,56 @@ +/* $Id: print.c 12852 2005-01-06 13:58:04Z mf $ + * + * print.c - Print on the blue screen + * + * ReactOS Operating System + * + * -------------------------------------------------------------------- + * + * This software is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of the + * License, or (at your option) any later version. + * + * This software is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this software; see the file COPYING.LIB. If not, write + * to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, + * MA 02139, USA. + * + * -------------------------------------------------------------------- + */ +#define NTOS_MODE_USER +#include + +VOID STDCALL DisplayString(LPCWSTR lpwString) +{ + UNICODE_STRING us; + + RtlInitUnicodeString (&us, lpwString); + ZwDisplayString (&us); +} + +VOID STDCALL PrintString (char* fmt, ...) +{ + char buffer[512]; + va_list ap; + UNICODE_STRING UnicodeString; + ANSI_STRING AnsiString; + + va_start(ap, fmt); + vsprintf(buffer, fmt, ap); + va_end(ap); + + RtlInitAnsiString (&AnsiString, buffer); + RtlAnsiStringToUnicodeString (&UnicodeString, + &AnsiString, + TRUE); + NtDisplayString(&UnicodeString); + RtlFreeUnicodeString (&UnicodeString); +} + +/* EOF */ diff --git a/reactos/subsys/smss/smapi.c b/reactos/subsys/smss/smapi.c index 05be26a1e62..33a062deb9c 100644 --- a/reactos/subsys/smss/smapi.c +++ b/reactos/subsys/smss/smapi.c @@ -9,7 +9,7 @@ #include "smss.h" #include -#define NDEBUG +//#define NDEBUG #include /* GLOBAL VARIABLES *********************************************************/ @@ -18,9 +18,6 @@ static HANDLE SmApiPort = INVALID_HANDLE_VALUE; /* SM API *******************************************************************/ -#define SMAPI(n) \ -NTSTATUS FASTCALL n (PSM_PORT_MESSAGE Request) - SMAPI(SmInvalid) { DPRINT("SM: %s called\n",__FUNCTION__); @@ -28,101 +25,33 @@ SMAPI(SmInvalid) return STATUS_SUCCESS; } -SMAPI(SmCompSes) -{ - DPRINT("SM: %s called\n",__FUNCTION__); - Request->Status = STATUS_NOT_IMPLEMENTED; - return STATUS_SUCCESS; -} -SMAPI(SmExecPgm) -{ - DPRINT("SM: %s called\n",__FUNCTION__); - Request->Status = STATUS_NOT_IMPLEMENTED; - return STATUS_SUCCESS; -} - /* SM API Table */ typedef NTSTATUS (FASTCALL * SM_PORT_API)(PSM_PORT_MESSAGE); SM_PORT_API SmApi [] = { SmInvalid, /* unused */ - SmCompSes, + SmCompSes, /* smapicomp.c */ SmInvalid, /* obsolete */ SmInvalid, /* unknown */ - SmExecPgm + SmExecPgm /* smapiexec.c */ }; - -/********************************************************************** - * NAME - * SmpHandleConnectionRequest/2 - * - * REMARKS - * Quoted in http://support.microsoft.com/kb/258060/EN-US/ - */ +#if !defined(__USE_NT_LPC__) NTSTATUS STDCALL -SmpHandleConnectionRequest (HANDLE Port, PSM_PORT_MESSAGE Request) -{ - NTSTATUS Status = STATUS_SUCCESS; - PSM_CLIENT_DATA ClientData = NULL; - PVOID Context = NULL; - - DPRINT("SM: %s called\n",__FUNCTION__); +SmpHandleConnectionRequest (PSM_PORT_MESSAGE Request); +#endif - Status = SmCreateClient (Request, & ClientData); - if(STATUS_SUCCESS == Status) - { -#ifdef __USE_NT_LPC__ - Status = NtAcceptConnectPort (& ClientData->ApiPort, - Context, - SmApiPort, - TRUE, //accept - NULL, - NULL); -#else - Status = NtAcceptConnectPort (& ClientData->ApiPort, - Context, - (PLPC_MESSAGE) Request, - TRUE, //accept - NULL, - NULL); -#endif - if(NT_SUCCESS(Status)) - { - Status = NtCompleteConnectPort(ClientData->ApiPort); - } - return STATUS_SUCCESS; - } else { - /* Reject the subsystem */ -#ifdef __USE_NT_LPC__ - Status = NtAcceptConnectPort (& ClientData->ApiPort, - Context, - SmApiPort, - FALSE, //reject - NULL, - NULL); -#else - Status = NtAcceptConnectPort (& ClientData->ApiPort, - Context, - (PLPC_MESSAGE) Request, - FALSE, //reject - NULL, - NULL); -#endif - } - return Status; -} /********************************************************************** * NAME - * SmpApiThread/1 + * SmpApiConnectedThread/1 * * DESCRIPTION * Entry point for the listener thread of LPC port "\SmApiPort". */ VOID STDCALL -SmpApiThread(HANDLE Port) +SmpApiConnectedThread(PVOID dummy) { NTSTATUS Status = STATUS_SUCCESS; PVOID Unknown = NULL; @@ -135,7 +64,7 @@ SmpApiThread(HANDLE Port) { DPRINT("SM: %s: waiting for message\n",__FUNCTION__); - Status = NtReplyWaitReceivePort(Port, + Status = NtReplyWaitReceivePort(SmApiPort, (PULONG) & Unknown, Reply, (PLPC_MESSAGE) & Request); @@ -148,7 +77,7 @@ SmpApiThread(HANDLE Port) switch (Request.Header.MessageType) { case LPC_CONNECTION_REQUEST: - SmpHandleConnectionRequest (Port, &Request); + SmpHandleConnectionRequest (&Request); Reply = NULL; break; case LPC_DEBUG_EVENT: @@ -173,6 +102,158 @@ SmpApiThread(HANDLE Port) } } +/********************************************************************** + * NAME + * SmpHandleConnectionRequest/1 + * + * ARGUMENTS + * Request: LPC connection request message + * + * REMARKS + * Quoted in http://support.microsoft.com/kb/258060/EN-US/ + */ +NTSTATUS STDCALL +SmpHandleConnectionRequest (PSM_PORT_MESSAGE Request) +{ +#if defined(__USE_NT_LPC__) + NTSTATUS Status = STATUS_SUCCESS; + PSM_CLIENT_DATA ClientData = NULL; + PVOID Context = NULL; + + DPRINT("SM: %s called\n",__FUNCTION__); + + /* + * SmCreateClient/2 is called here explicitly to *fail*. + * If it succeeds, there is something wrong in the + * connection request. An environment subsystem *never* + * registers twice. (Security issue: maybe we will + * write this event into the security log). + */ + Status = SmCreateClient (Request, & ClientData); + if(STATUS_SUCCESS == Status) + { + /* OK: the client is an environment subsystem + * willing to manage a free image type. + * Accept it. + */ + Status = NtAcceptConnectPort (& ClientData->ApiPort, + Context, + (PLPC_MESSAGE) Request, + TRUE, //accept + NULL, + NULL); + if(NT_SUCCESS(Status)) + { + Status = NtCompleteConnectPort(ClientData->ApiPort); + } + return STATUS_SUCCESS; + } else { + /* Reject the subsystem */ + Status = NtAcceptConnectPort (& ClientData->ApiPort, + Context, + (PLPC_MESSAGE) Request, + FALSE, //reject + NULL, + NULL); + } +#else /* ReactOS LPC */ + NTSTATUS Status = STATUS_SUCCESS; + PSM_CLIENT_DATA ClientData = NULL; + + DPRINT("SM: %s called\n",__FUNCTION__); + + Status = SmCreateClient (Request, & ClientData); + if(STATUS_SUCCESS == Status) + { + Status = NtAcceptConnectPort (& ClientData->ApiPort, + SmApiPort, + NULL, + TRUE, //accept + NULL, + NULL); + if (!NT_SUCCESS(Status)) + { + DPRINT1("SM: %s: NtAcceptConnectPort() failed (Status=0x%08lx)\n", + __FUNCTION__, Status); + return Status; + } else { + Status = NtCompleteConnectPort(ClientData->ApiPort); + if (!NT_SUCCESS(Status)) + { + DPRINT1("SM: %s: NtCompleteConnectPort() failed (Status=0x%08lx)\n", + __FUNCTION__, Status); + return Status; + } + Status = RtlCreateUserThread(NtCurrentProcess(), + NULL, + FALSE, + 0, + NULL, + NULL, + (PTHREAD_START_ROUTINE) SmpApiConnectedThread, + ClientData->ApiPort, + & ClientData->ApiPortThread, + NULL); + if (!NT_SUCCESS(Status)) + { + DPRINT1("SM: %s: Unable to create server thread (Status=0x%08lx)\n", + __FUNCTION__, Status); + return Status; + } + } + return STATUS_SUCCESS; + } else { + /* Reject the subsystem */ + Status = NtAcceptConnectPort (& ClientData->ApiPort, + SmApiPort, + NULL, + FALSE, //reject + NULL, + NULL); + } +#endif /* defined __USE_NT_LPC__ */ + return Status; +} + +/********************************************************************** + * NAME + * SmpApiThread/1 + * + * DECRIPTION + * Due to differences in LPC implementation between NT and ROS, + * we need a thread to listen for connection request that + * creates a new thread for each connected port. This is not + * necessary in NT LPC, because server side connected ports are + * never used to receive requests. + */ +VOID STDCALL +SmpApiThread (HANDLE ListeningPort) +{ + NTSTATUS Status = STATUS_SUCCESS; + LPC_MAX_MESSAGE Request = {{0}}; + + while (TRUE) + { + Status = NtListenPort (ListeningPort, & Request.Header); + if (!NT_SUCCESS(Status)) + { + DPRINT1("SM: %s: NtListenPort() failed! (Status==x%08lx)\n", __FUNCTION__, Status); + break; + } + Status = SmpHandleConnectionRequest ((PSM_PORT_MESSAGE) & Request); + if(!NT_SUCCESS(Status)) + { + DPRINT1("SM: %s: SmpHandleConnectionRequest failed (Status=0x%08lx)\n", + __FUNCTION__, Status); + break; + } + } + /* Cleanup */ + NtClose(ListeningPort); + /* DIE */ + NtTerminateThread(NtCurrentThread(), Status); +} + /* LPC PORT INITIALIZATION **************************************************/ @@ -186,9 +267,9 @@ SmpApiThread(HANDLE Port) NTSTATUS SmCreateApiPort(VOID) { - OBJECT_ATTRIBUTES ObjectAttributes; - UNICODE_STRING UnicodeString; - NTSTATUS Status; + OBJECT_ATTRIBUTES ObjectAttributes = {0}; + UNICODE_STRING UnicodeString = {0}; + NTSTATUS Status = STATUS_SUCCESS; RtlRosInitUnicodeStringFromLiteral(&UnicodeString, L"\\SmApiPort"); @@ -207,19 +288,10 @@ SmCreateApiPort(VOID) { return(Status); } - - /* Create two threads for "\SmApiPort" */ - RtlCreateUserThread(NtCurrentProcess(), - NULL, - FALSE, - 0, - NULL, - NULL, - (PTHREAD_START_ROUTINE)SmpApiThread, - (PVOID)SmApiPort, - NULL, - NULL); - + /* + * Create one thread for the named LPC + * port \SmApiPort + */ RtlCreateUserThread(NtCurrentProcess(), NULL, FALSE, diff --git a/reactos/subsys/smss/smapicomp.c b/reactos/subsys/smss/smapicomp.c new file mode 100644 index 00000000000..a655ef7cf4f --- /dev/null +++ b/reactos/subsys/smss/smapicomp.c @@ -0,0 +1,27 @@ +/* $Id: $ + * + * smapicomp.c - SM_API_COMPLETE_SESSION + * + * Reactos Session Manager + * + */ + +#include "smss.h" +#include + +#define NDEBUG +#include + + +/********************************************************************** + * SmCompSes/1 API + */ +SMAPI(SmCompSes) +{ + DPRINT("SM: %s called\n",__FUNCTION__); + Request->Status = STATUS_NOT_IMPLEMENTED; + return STATUS_SUCCESS; +} + + +/* EOF */ diff --git a/reactos/subsys/smss/smapiexec.c b/reactos/subsys/smss/smapiexec.c new file mode 100644 index 00000000000..d2faac849d0 --- /dev/null +++ b/reactos/subsys/smss/smapiexec.c @@ -0,0 +1,113 @@ +/* $Id: $ + * + * smapiexec.c - SM_API_EXECUTE_PROGRAM + * + * Reactos Session Manager + * + */ + +#include "smss.h" +#include + +#define NDEBUG +#include + +/********************************************************************** + * SmCreateUserProcess/5 + * + */ +NTSTATUS STDCALL +SmCreateUserProcess (LPWSTR ImagePath, + LPWSTR CommandLine, + BOOLEAN WaitForIt, + PLARGE_INTEGER Timeout OPTIONAL, + BOOLEAN TerminateIt, + PRTL_PROCESS_INFO UserProcessInfo OPTIONAL + ) +{ + UNICODE_STRING ImagePathString = {0}; + UNICODE_STRING CommandLineString = {0}; + PRTL_USER_PROCESS_PARAMETERS ProcessParameters = NULL; + RTL_PROCESS_INFO ProcessInfo = {0}; + PRTL_PROCESS_INFO pProcessInfo = & ProcessInfo; + NTSTATUS Status = STATUS_SUCCESS; + + + DPRINT("SM: %s called\n",__FUNCTION__); + + RtlInitUnicodeString (& ImagePathString, ImagePath); + RtlInitUnicodeString (& CommandLineString, CommandLine); + + RtlCreateProcessParameters(& ProcessParameters, + & ImagePathString, + NULL, + NULL, + & CommandLineString, + SmSystemEnvironment, + NULL, + NULL, + NULL, + NULL); + + if(NULL != UserProcessInfo) + { + /* Use caller provided storage */ + pProcessInfo = UserProcessInfo; + } + + Status = RtlCreateUserProcess (& ImagePathString, + OBJ_CASE_INSENSITIVE, + ProcessParameters, + NULL, + NULL, + NULL, + FALSE, + NULL, + NULL, + pProcessInfo); + if (!NT_SUCCESS(Status)) + { + CHAR AnsiBuffer [MAX_PATH]; + INT i = 0; + for(i=0;ImagePathString.Buffer[i];i++) + { + /* raw U -> A */ + AnsiBuffer [i] = (CHAR) (ImagePathString.Buffer[i] & 0xff); + } + + DPRINT1("SM: %s: Running \"%s\" failed (Status=0x%08lx)\n", + AnsiBuffer, __FUNCTION__, Status); + return Status; + } + + RtlDestroyProcessParameters (ProcessParameters); + + /* Wait for process termination */ + if(WaitForIt) + { + NtWaitForSingleObject (pProcessInfo->ProcessHandle, + FALSE, + Timeout); + } + + /* Terminate process */ + if(TerminateIt) + { + NtClose(pProcessInfo->ThreadHandle); + NtClose(pProcessInfo->ProcessHandle); + } + return STATUS_SUCCESS; +} + +/********************************************************************** + * SmExecPgm/1 API + */ +SMAPI(SmExecPgm) +{ + DPRINT("SM: %s called\n",__FUNCTION__); + Request->Status = STATUS_NOT_IMPLEMENTED; + return STATUS_SUCCESS; +} + + +/* EOF */ diff --git a/reactos/subsys/smss/smss.c b/reactos/subsys/smss/smss.c index 72d0656c33c..5d51441b8f6 100644 --- a/reactos/subsys/smss/smss.c +++ b/reactos/subsys/smss/smss.c @@ -25,6 +25,7 @@ */ #include "smss.h" #include +#include #define NDEBUG #include @@ -36,6 +37,11 @@ NtProcessStartup(PPEB Peb) { NTSTATUS Status; + DisplayString(L"SMSS\n"); + PrintString("ReactOS Session Manager %s (Build %s)\n", + KERNEL_RELEASE_STR, + KERNEL_VERSION_BUILD_STR); + Status = InitSessionManager(); if (!NT_SUCCESS(Status)) { diff --git a/reactos/subsys/smss/smss.h b/reactos/subsys/smss/smss.h index 1ed5d26e724..605388282c2 100644 --- a/reactos/subsys/smss/smss.h +++ b/reactos/subsys/smss/smss.h @@ -4,7 +4,6 @@ #define NTOS_MODE_USER #include #include -#include #define CHILD_CSRSS 0 #define CHILD_WINLOGON 1 @@ -50,8 +49,23 @@ NTSTATUS SmRunCsrss(VOID); NTSTATUS SmRunWinlogon(VOID); /* smapi.c */ +#define SMAPI(n) \ +NTSTATUS FASTCALL n (PSM_PORT_MESSAGE Request) + +/* smapiexec.c */ +NTSTATUS STDCALL SmCreateUserProcess(LPWSTR ImagePath, + LPWSTR CommandLine, + BOOLEAN WaitForIt, + PLARGE_INTEGER Timeout OPTIONAL, + BOOLEAN TerminateIt, + PRTL_PROCESS_INFO ProcessInfo OPTIONAL); +NTSTATUS FASTCALL SmExecPgm(PSM_PORT_MESSAGE); + +/* smapicomp.c */ +NTSTATUS FASTCALL SmCompSes(PSM_PORT_MESSAGE); + NTSTATUS SmCreateApiPort(VOID); -VOID STDCALL SmpApiThread(HANDLE Port); +VOID STDCALL SmpApiThread(PVOID); /* client.c */ typedef struct _SM_CLIENT_DATA @@ -60,12 +74,14 @@ typedef struct _SM_CLIENT_DATA BOOL Initialized; HANDLE ServerProcess; HANDLE ApiPort; + HANDLE ApiPortThread; HANDLE SbApiPort; WCHAR SbApiPortName [SM_SB_NAME_MAX_LENGTH]; struct _SM_CLIENT_DATA * Next; } SM_CLIENT_DATA, *PSM_CLIENT_DATA; NTSTATUS SmInitializeClientManagement(VOID); +NTSTATUS SmpRegisterSmss(VOID); NTSTATUS STDCALL SmCreateClient(PSM_PORT_MESSAGE,PSM_CLIENT_DATA*); NTSTATUS STDCALL SmDestroyClient(ULONG); @@ -74,6 +90,10 @@ extern HANDLE DbgSsApiPort; extern HANDLE DbgUiApiPort; NTSTATUS SmInitializeDbgSs(VOID); +/* print.c */ +VOID STDCALL DisplayString(LPCWSTR lpwString); +VOID STDCALL PrintString (char* fmt, ...); + #endif /* _SMSS_H_INCLUDED_ */ /* EOF */