*
*/
-/* NOTE:
- * - Services.exe is NOT a native application, it is a GUI app.
- */
-
/* INCLUDES *****************************************************************/
#include "services.h"
#define PIPE_TIMEOUT 1000
BOOL ScmShutdown = FALSE;
+static HANDLE hScmShutdownEvent = NULL;
/* FUNCTIONS *****************************************************************/
{
HANDLE hEvent;
- hEvent = CreateEvent(NULL,
- TRUE,
- FALSE,
- TEXT("SvcctrlStartEvent_A3752DX"));
+ hEvent = CreateEventW(NULL,
+ TRUE,
+ FALSE,
+ L"SvcctrlStartEvent_A3752DX");
if (hEvent == NULL)
{
if (GetLastError() == ERROR_ALREADY_EXISTS)
{
- hEvent = OpenEvent(EVENT_ALL_ACCESS,
- FALSE,
- TEXT("SvcctrlStartEvent_A3752DX"));
+ hEvent = OpenEventW(EVENT_ALL_ACCESS,
+ FALSE,
+ L"SvcctrlStartEvent_A3752DX");
if (hEvent == NULL)
{
return FALSE;
}
-static VOID
-ScmWaitForLsass(VOID)
+VOID
+ScmWaitForLsa(VOID)
{
HANDLE hEvent;
DWORD dwError;
if (hEvent == NULL)
{
dwError = GetLastError();
- DPRINT("Failed to create the notication event (Error %lu)\n", dwError);
+ DPRINT1("Failed to create the notication event (Error %lu)\n", dwError);
if (dwError == ERROR_ALREADY_EXISTS)
{
DPRINT("LSA server running!\n");
CloseHandle(hEvent);
+
+ DPRINT("ScmWaitForLsa() done\n");
}
DPRINT("ScmCreateNamedPipe() - CreateNamedPipe(\"\\\\.\\pipe\\Ntsvcs\")\n");
- hPipe = CreateNamedPipe(TEXT("\\\\.\\pipe\\Ntsvcs"),
+ hPipe = CreateNamedPipeW(L"\\\\.\\pipe\\Ntsvcs",
PIPE_ACCESS_DUPLEX,
PIPE_TYPE_MESSAGE | PIPE_READMODE_MESSAGE | PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES,
DPRINT("CreateNamedPipe() - returning FALSE\n");
return FALSE;
}
+
+ CloseHandle(hThread);
}
else
{
return FALSE;
}
- return TRUE;
-}
-
-
-VOID FASTCALL
-AcquireLoadDriverPrivilege(VOID)
-{
- HANDLE hToken;
- TOKEN_PRIVILEGES tkp;
-
- /* Get a token for this process */
- if (OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken))
- {
- /* Get the LUID for the debug privilege */
- LookupPrivilegeValue(NULL, SE_LOAD_DRIVER_NAME, &tkp.Privileges[0].Luid);
-
- /* One privilege to set */
- tkp.PrivilegeCount = 1;
- tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
+ CloseHandle(hThread);
- /* Get the debug privilege for this process */
- AdjustTokenPrivileges(hToken, FALSE, &tkp, 0, (PTOKEN_PRIVILEGES)NULL, 0);
- }
+ return TRUE;
}
ScmAutoShutdownServices();
ScmShutdownServiceDatabase();
+
+ /* Set the shutdwon event */
+ SetEvent(hScmShutdownEvent);
}
return TRUE;
LPWSTR lpCmdLine,
int nShowCmd)
{
- HANDLE hScmStartEvent;
- HANDLE hEvent;
+ HANDLE hScmStartEvent = NULL;
+ SC_RPC_LOCK Lock = NULL;
+ BOOL bCanDeleteNamedPipeCriticalSection = FALSE;
DWORD dwError;
DPRINT("SERVICES: Service Control Manager\n");
if (!ScmCreateStartEvent(&hScmStartEvent))
{
DPRINT1("SERVICES: Failed to create start event\n");
- ExitThread(0);
+ goto done;
+ }
+
+ DPRINT("SERVICES: created start event with handle %p.\n", hScmStartEvent);
+
+ /* Create the shutdown event */
+ hScmShutdownEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
+ if (hScmShutdownEvent == NULL)
+ {
+ DPRINT1("SERVICES: Failed to create shutdown event\n");
+ goto done;
}
- DPRINT("SERVICES: created start event with handle %x.\n", hScmStartEvent);
+ /* Initialize our communication named pipe's critical section */
+ ScmInitNamedPipeCriticalSection();
+ bCanDeleteNamedPipeCriticalSection = TRUE;
// ScmInitThreadManager();
/* FIXME: more initialization */
+ /* Read the control set values */
+ if (!ScmGetControlSetValues())
+ {
+ DPRINT1("SERVICES: failed to read the control set values\n");
+ goto done;
+ }
- /* Create the service database */
+ /* Create the services database */
dwError = ScmCreateServiceDatabase();
if (dwError != ERROR_SUCCESS)
{
DPRINT1("SERVICES: failed to create SCM database (Error %lu)\n", dwError);
- ExitThread(0);
+ goto done;
}
- /* Update service database */
+ /* Update the services database */
ScmGetBootAndSystemDriverState();
+ /* Register the Service Control Manager process with CSRSS */
+ if (!RegisterServicesProcess(GetCurrentProcessId()))
+ {
+ DPRINT1("SERVICES: Could not register SCM process\n");
+ goto done;
+ }
+
+ /* Acquire the service start lock until autostart services have been started */
+ dwError = ScmAcquireServiceStartLock(TRUE, &Lock);
+ if (dwError != ERROR_SUCCESS)
+ {
+ DPRINT1("SERVICES: failed to acquire the service start lock (Error %lu)\n", dwError);
+ goto done;
+ }
+
/* Start the RPC server */
ScmStartRpcServer();
- /* Register service process with CSRSS */
- RegisterServicesProcess(GetCurrentProcessId());
-
DPRINT("SERVICES: Initialized.\n");
/* Signal start event */
SetConsoleCtrlHandler(ShutdownHandlerRoutine, TRUE);
/* Wait for the LSA server */
- ScmWaitForLsass();
-
- /* Acquire privileges to load drivers */
- AcquireLoadDriverPrivilege();
-
- ScmInitNamedPipeCriticalSection();
+ ScmWaitForLsa();
/* Start auto-start services */
ScmAutoStartServices();
/* FIXME: more to do ? */
+ /* Release the service start lock */
+ ScmReleaseServiceStartLock(&Lock);
DPRINT("SERVICES: Running.\n");
-#if 1
- hEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
- if (hEvent)
- WaitForSingleObject(hEvent, INFINITE);
-#else
- for (;;)
- {
- NtYieldExecution();
- }
-#endif
+ /* Wait until the shutdown event gets signaled */
+ WaitForSingleObject(hScmShutdownEvent, INFINITE);
+
+done:
+ /* Delete our communication named pipe's critical section */
+ if (bCanDeleteNamedPipeCriticalSection == TRUE)
+ ScmDeleteNamedPipeCriticalSection();
- ScmDeleteNamedPipeCriticalSection();
+ /* Close the shutdown event */
+ if (hScmShutdownEvent != NULL)
+ CloseHandle(hScmShutdownEvent);
- CloseHandle(hScmStartEvent);
+ /* Close the start event */
+ if (hScmStartEvent != NULL)
+ CloseHandle(hScmStartEvent);
DPRINT("SERVICES: Finished.\n");