[SERVICES] Remove the "Special service accounts initialization" hack, and enable...
authorHermès Bélusca-Maïto <hermes.belusca-maito@reactos.org>
Fri, 22 Jun 2018 23:36:22 +0000 (01:36 +0200)
committerHermès Bélusca-Maïto <hermes.belusca-maito@reactos.org>
Thu, 28 Jun 2018 21:34:02 +0000 (23:34 +0200)
This effectively removes the temporary hacks introduced in r73486 (a35a785b)
and in r73487 (0ce031f7) for the LocalService and NetworkService accounts.

Now these accounts (and their corresponding user profiles) are created
on the fly, the first time a service that needs these is started.
The code introduced in r73501 (ade0d2cd) is now re-enabled: this has
been made possible thanks to commit f42b4bbe (thanks Eric!).

Dedicated to Joachim Henze ;-)

CORE-12541, CORE-12279

base/system/services/database.c
base/system/services/services.c

index 580dc0f..0a71065 100644 (file)
@@ -184,37 +184,30 @@ ScmLogonService(
     IN PSERVICE pService,
     IN PSERVICE_IMAGE pImage)
 {
-#if 0
+    DWORD dwError = ERROR_SUCCESS;
     PROFILEINFOW ProfileInfo;
     PWSTR pszUserName = NULL;
     PWSTR pszDomainName = NULL;
     PWSTR pszPassword = NULL;
     PWSTR ptr;
-    DWORD dwError = ERROR_SUCCESS;
-#endif
 
     DPRINT("ScmLogonService(%p %p)\n", pService, pImage);
-
     DPRINT("Service %S\n", pService->lpServiceName);
 
     if (ScmIsLocalSystemAccount(pImage->pszAccountName))
         return ERROR_SUCCESS;
 
-    // FIXME: Always assume LocalSystem
-    return ERROR_SUCCESS;
-
-#if 0
     /* Get the user and domain names */
     ptr = wcschr(pImage->pszAccountName, L'\\');
     if (ptr != NULL)
     {
         *ptr = L'\0';
-
         pszUserName = ptr + 1;
         pszDomainName = pImage->pszAccountName;
     }
     else
     {
+        // ERROR_INVALID_SERVICE_ACCOUNT
         pszUserName = pImage->pszAccountName;
         pszDomainName = NULL;
     }
@@ -234,7 +227,7 @@ ScmLogonService(
 
     DPRINT("Domain: %S  User: %S  Password: %S\n", pszDomainName, pszUserName, pszPassword);
 
-    /* Service logon */
+    /* Do the service logon */
     if (!LogonUserW(pszUserName,
                     pszDomainName,
                     pszPassword,
@@ -244,14 +237,13 @@ ScmLogonService(
     {
         dwError = GetLastError();
         DPRINT1("LogonUserW() failed (Error %lu)\n", dwError);
+
+        /* Normalize the returned error */
+        dwError = ERROR_SERVICE_LOGON_FAILED;
         goto done;
     }
 
-    // FIXME: Call LoadUserProfileW to be able to initialize a per-user
-    // environment block, with user-specific environment variables as
-    // %USERNAME%, %USERPROFILE%, and %ALLUSERSPROFILE% correctly initialized!!
-
-    /* Load the user profile, so that the per-user environment variables can be initialized */
+    /* Load the user profile; the per-user environment variables are thus correctly initialized */
     ZeroMemory(&ProfileInfo, sizeof(ProfileInfo));
     ProfileInfo.dwSize = sizeof(ProfileInfo);
     ProfileInfo.dwFlags = PI_NOUI;
@@ -279,7 +271,6 @@ done:
         *ptr = L'\\';
 
     return dwError;
-#endif
 }
 
 
@@ -1682,7 +1673,9 @@ ScmStartUserModeService(PSERVICE Service,
     /* Use the interactive desktop if the service is interactive */
     if ((NoInteractiveServices == 0) &&
         (Service->Status.dwServiceType & SERVICE_INTERACTIVE_PROCESS))
+    {
         StartupInfo.lpDesktop = L"WinSta0\\Default";
+    }
 
     if (Service->lpImage->hToken)
     {
index 58a6256..3b3342f 100644 (file)
@@ -123,178 +123,6 @@ ShutdownHandlerRoutine(DWORD dwCtrlType)
 }
 
 
-/*** HACK CORE-12541: Special service accounts initialization HACK ************/
-
-#include <ndk/setypes.h>
-#include <sddl.h>
-#include <userenv.h>
-#include <strsafe.h>
-
-/* Inspired from userenv.dll's CreateUserProfileExW and LoadUserProfileW APIs */
-static
-BOOL
-ScmLogAccountHack(IN LPCWSTR pszAccountName,
-                  IN LPCWSTR pszSid,
-                  OUT PHKEY phProfile)
-{
-    BOOL Success = FALSE;
-    LONG Error;
-    NTSTATUS Status;
-    BOOLEAN WasPriv1Set = FALSE, WasPriv2Set = FALSE;
-    PSID pSid;
-    DWORD dwLength;
-    WCHAR szUserHivePath[MAX_PATH];
-
-    DPRINT1("ScmLogAccountsHack(%S, %S)\n", pszAccountName, pszSid);
-    if (!pszAccountName || !pszSid || !phProfile)
-        return ERROR_INVALID_PARAMETER;
-
-    /* Convert the SID string into a SID. NOTE: No RTL equivalent. */
-    if (!ConvertStringSidToSidW(pszSid, &pSid))
-    {
-        DPRINT1("ConvertStringSidToSidW() failed (error %lu)\n", GetLastError());
-        return FALSE;
-    }
-
-    /* Determine a suitable profile path */
-    dwLength = ARRAYSIZE(szUserHivePath);
-    if (!GetProfilesDirectoryW(szUserHivePath, &dwLength))
-    {
-        DPRINT1("GetProfilesDirectoryW() failed (error %lu)\n", GetLastError());
-        goto Quit;
-    }
-
-    /* Create user hive name */
-    StringCbCatW(szUserHivePath, sizeof(szUserHivePath), L"\\");
-    StringCbCatW(szUserHivePath, sizeof(szUserHivePath), pszAccountName);
-    StringCbCatW(szUserHivePath, sizeof(szUserHivePath), L"\\ntuser.dat");
-    DPRINT("szUserHivePath: %S\n", szUserHivePath);
-
-    /* Magic #1: Create the special user profile if needed */
-    if (GetFileAttributesW(szUserHivePath) == INVALID_FILE_ATTRIBUTES)
-    {
-        if (!CreateUserProfileW(pSid, pszAccountName))
-        {
-            DPRINT1("CreateUserProfileW() failed (error %lu)\n", GetLastError());
-            goto Quit;
-        }
-    }
-
-    /*
-     * Now Da Magiks #2: Manually mount the user profile registry hive
-     * aka. manually do what LoadUserProfile does!! But we don't require
-     * a security token!
-     */
-
-    /* Acquire restore privilege */
-    Status = RtlAdjustPrivilege(SE_RESTORE_PRIVILEGE, TRUE, FALSE, &WasPriv1Set);
-    if (!NT_SUCCESS(Status))
-    {
-        DPRINT1("RtlAdjustPrivilege(SE_RESTORE_PRIVILEGE) failed (Error 0x%08lx)\n", Status);
-        goto Quit;
-    }
-
-    /* Acquire backup privilege */
-    Status = RtlAdjustPrivilege(SE_BACKUP_PRIVILEGE, TRUE, FALSE, &WasPriv2Set);
-    if (!NT_SUCCESS(Status))
-    {
-        DPRINT1("RtlAdjustPrivilege(SE_BACKUP_PRIVILEGE) failed (Error 0x%08lx)\n", Status);
-        RtlAdjustPrivilege(SE_RESTORE_PRIVILEGE, WasPriv1Set, FALSE, &WasPriv1Set);
-        goto Quit;
-    }
-
-    /* Load user registry hive */
-    Error = RegLoadKeyW(HKEY_USERS, pszSid, szUserHivePath);
-
-    /* Remove restore and backup privileges */
-    RtlAdjustPrivilege(SE_BACKUP_PRIVILEGE, WasPriv2Set, FALSE, &WasPriv2Set);
-    RtlAdjustPrivilege(SE_RESTORE_PRIVILEGE, WasPriv1Set, FALSE, &WasPriv1Set);
-
-    /* HACK: Do not fail if the profile has already been loaded! */
-    if (Error == ERROR_SHARING_VIOLATION)
-        Error = ERROR_SUCCESS;
-
-    if (Error != ERROR_SUCCESS)
-    {
-        DPRINT1("RegLoadKeyW() failed (Error %ld)\n", Error);
-        goto Quit;
-    }
-
-    /* Open future HKEY_CURRENT_USER */
-    Error = RegOpenKeyExW(HKEY_USERS,
-                          pszSid,
-                          0,
-                          MAXIMUM_ALLOWED,
-                          phProfile);
-    if (Error != ERROR_SUCCESS)
-    {
-        DPRINT1("RegOpenKeyExW() failed (Error %ld)\n", Error);
-        goto Quit;
-    }
-
-    Success = TRUE;
-
-Quit:
-    LocalFree(pSid);
-
-    DPRINT1("ScmLogAccountsHack(%S) returned %s\n",
-            pszAccountName, Success ? "success" : "failure");
-
-    return Success;
-}
-
-static struct
-{
-    LPCWSTR pszAccountName;
-    LPCWSTR pszSid;
-    HKEY    hProfile;
-} AccountHandles[] = {
-//  {L"LocalSystem"   , L"S-1-5-18", NULL},
-    {L"LocalService"  , L"S-1-5-19", NULL}, // L"NT AUTHORITY\\LocalService"
-    {L"NetworkService", L"S-1-5-20", NULL}, // L"NT AUTHORITY\\NetworkService"
-};
-
-static VOID
-ScmCleanupServiceAccountsHack(VOID)
-{
-    UINT i;
-
-    DPRINT1("ScmCleanupServiceAccountsHack()\n");
-
-    for (i = 0; i < ARRAYSIZE(AccountHandles); ++i)
-    {
-        if (AccountHandles[i].hProfile)
-        {
-            RegCloseKey(AccountHandles[i].hProfile);
-            AccountHandles[i].hProfile = NULL;
-        }
-    }
-}
-
-static BOOL
-ScmApplyServiceAccountsHack(VOID)
-{
-    UINT i;
-
-    DPRINT1("ScmApplyServiceAccountsHack()\n");
-
-    for (i = 0; i < ARRAYSIZE(AccountHandles); ++i)
-    {
-        if (!ScmLogAccountHack( AccountHandles[i].pszAccountName,
-                                AccountHandles[i].pszSid,
-                               &AccountHandles[i].hProfile))
-        {
-            ScmCleanupServiceAccountsHack();
-            return FALSE;
-        }
-    }
-
-    return TRUE;
-}
-
-/*************************** END OF HACK CORE-12541 ***************************/
-
-
 int WINAPI
 wWinMain(HINSTANCE hInstance,
          HINSTANCE hPrevInstance,
@@ -407,9 +235,6 @@ wWinMain(HINSTANCE hInstance,
      */
     SetProcessShutdownParameters(480, SHUTDOWN_NORETRY);
 
-    /*** HACK CORE-12541: Apply service accounts HACK ***/
-    ScmApplyServiceAccountsHack();
-
     /* Start auto-start services */
     ScmAutoStartServices();
 
@@ -429,9 +254,6 @@ wWinMain(HINSTANCE hInstance,
     /* Wait until the shutdown event gets signaled */
     WaitForSingleObject(hScmShutdownEvent, INFINITE);
 
-    /*** HACK CORE-12541: Cleanup service accounts HACK ***/
-    ScmCleanupServiceAccountsHack();
-
 done:
     ScmShutdownSecurity();