From fb25b9f54ff7e0c4e18abb1a59c25709dc51a500 Mon Sep 17 00:00:00 2001 From: Eric Kohl Date: Thu, 31 May 2012 11:07:51 +0000 Subject: [PATCH] [SAMLIB] - Implement SamOpenUser and SamSetInformationUser. - Add SamQueryInformationUser stub. [SAMSRV] - Implement SamrOpenUser. - Add a hack to SamrSetInformationUser that enables us to store a users password (as plain-text) in the registry. - SamrCreateUserInDomain: Fix the creation of user account key names and start counting user RIDs at 1000. - Clean-up the SAM registry setup code. - Assingn SIDs to the BUILTIN and Account domains. - Create the Administrator and Guest accounts in the SAM setup. svn path=/trunk/; revision=56679 --- reactos/dll/win32/samlib/samlib.c | 71 +++++ reactos/dll/win32/samlib/samlib.spec | 6 +- reactos/dll/win32/samsrv/samrpc.c | 105 ++++++- reactos/dll/win32/samsrv/samsrv.h | 3 +- reactos/dll/win32/samsrv/setup.c | 454 +++++++++++++-------------- reactos/include/ddk/ntsam.h | 70 +++++ reactos/include/reactos/idl/sam.idl | 24 +- 7 files changed, 482 insertions(+), 251 deletions(-) diff --git a/reactos/dll/win32/samlib/samlib.c b/reactos/dll/win32/samlib/samlib.c index 0f4146b3025..3dc63702773 100644 --- a/reactos/dll/win32/samlib/samlib.c +++ b/reactos/dll/win32/samlib/samlib.c @@ -404,6 +404,7 @@ SamCloseHandle(IN SAM_HANDLE SamHandle) return Status; } + NTSTATUS NTAPI SamConnect(IN OUT PUNICODE_STRING ServerName, @@ -431,6 +432,7 @@ SamConnect(IN OUT PUNICODE_STRING ServerName, return Status; } + NTSTATUS NTAPI SamCreateUserInDomain(IN SAM_HANDLE DomainHandle, @@ -461,6 +463,7 @@ SamCreateUserInDomain(IN SAM_HANDLE DomainHandle, return Status; } + NTSTATUS NTAPI SamOpenDomain(IN SAM_HANDLE ServerHandle, @@ -489,6 +492,74 @@ SamOpenDomain(IN SAM_HANDLE ServerHandle, return Status; } + +NTSTATUS +NTAPI +SamOpenUser(IN SAM_HANDLE DomainHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG UserId, + OUT PSAM_HANDLE UserHandle) +{ + NTSTATUS Status; + + TRACE("SamOpenUser(%p,0x%08x,%lx,%p)\n", + DomainHandle, DesiredAccess, UserId, UserHandle); + + RpcTryExcept + { + Status = SamrOpenUser((SAMPR_HANDLE)DomainHandle, + DesiredAccess, + UserId, + (SAMPR_HANDLE *)UserHandle); + } + RpcExcept(EXCEPTION_EXECUTE_HANDLER) + { + Status = I_RpcMapWin32Status(RpcExceptionCode()); + } + RpcEndExcept; + + return Status; +} + + +NTSTATUS +NTAPI +SamQueryInformationUser(IN SAM_HANDLE UserHandle, + IN USER_INFORMATION_CLASS UserInformationClass, + OUT PVOID *Buffer) +{ + UNIMPLEMENTED; + return STATUS_NOT_IMPLEMENTED; +} + + +NTSTATUS +NTAPI +SamSetInformationUser(IN SAM_HANDLE UserHandle, + IN USER_INFORMATION_CLASS UserInformationClass, + IN PVOID Buffer) +{ + NTSTATUS Status; + + TRACE("SamSetInformationUser(%p %lu %p)\n", + UserHandle, UserInformationClass, Buffer); + + RpcTryExcept + { + Status = SamrSetInformationUser((SAMPR_HANDLE)UserHandle, + UserInformationClass, + Buffer); + } + RpcExcept(EXCEPTION_EXECUTE_HANDLER) + { + Status = I_RpcMapWin32Status(RpcExceptionCode()); + } + RpcEndExcept; + + return Status; +} + + NTSTATUS NTAPI SamShutdownSamServer(IN SAM_HANDLE ServerHandle) diff --git a/reactos/dll/win32/samlib/samlib.spec b/reactos/dll/win32/samlib/samlib.spec index 25cb6e2b498..b2a53077018 100644 --- a/reactos/dll/win32/samlib/samlib.spec +++ b/reactos/dll/win32/samlib/samlib.spec @@ -31,12 +31,12 @@ @ stub SamOpenAlias @ stdcall SamOpenDomain(ptr long ptr ptr) @ stub SamOpenGroup -@ stub SamOpenUser +@ stdcall SamOpenUser(ptr long long ptr) @ stub SamQueryDisplayInformation @ stub SamQueryInformationAlias @ stub SamQueryInformationDomain @ stub SamQueryInformationGroup -@ stub SamQueryInformationUser +@ stdcall SamQueryInformationUser(ptr long ptr) @ stub SamQuerySecurityObject @ stub SamRemoveMemberFromAlias @ stub SamRemoveMemberFromForeignDomain @@ -46,7 +46,7 @@ @ stub SamSetInformationAlias @ stub SamSetInformationDomain @ stub SamSetInformationGroup -@ stub SamSetInformationUser +@ stdcall SamSetInformationUser(ptr long ptr) @ stub SamSetMemberAttributesOfGroup @ stub SamSetSecurityObject @ stdcall SamShutdownSamServer(ptr) diff --git a/reactos/dll/win32/samsrv/samrpc.c b/reactos/dll/win32/samsrv/samrpc.c index 8e19334829f..dd4b6de0959 100644 --- a/reactos/dll/win32/samsrv/samrpc.c +++ b/reactos/dll/win32/samsrv/samrpc.c @@ -337,12 +337,12 @@ SamrCreateUserInDomain(IN SAMPR_HANDLE DomainHandle, (LPVOID)&ulRid, &ulSize); if (!NT_SUCCESS(Status)) - ulRid = DOMAIN_USER_RID_MAX; + ulRid = DOMAIN_USER_RID_MAX + 1; TRACE("RID: %lx\n", ulRid); /* Convert the RID into a string (hex) */ - _ultow(ulRid, szRid, 16); + swprintf(szRid, L"%08lX", ulRid); /* Check whether the user name is already in use */ Status = SampCheckDbObjectNameAlias(DomainObject, @@ -385,9 +385,9 @@ SamrCreateUserInDomain(IN SAMPR_HANDLE DomainHandle, return Status; } - /* Set the account name attribute */ + /* Set the name attribute */ Status = SampSetObjectAttribute(UserObject, - L"AccountName", + L"Name", REG_SZ, (LPVOID)Name->Buffer, Name->MaximumLength); @@ -658,12 +658,48 @@ SamrGetMembersInAlias(IN SAMPR_HANDLE AliasHandle, NTSTATUS NTAPI SamrOpenUser(IN SAMPR_HANDLE DomainHandle, - IN unsigned long DesiredAccess, + IN ACCESS_MASK DesiredAccess, IN unsigned long UserId, OUT SAMPR_HANDLE *UserHandle) { - UNIMPLEMENTED; - return STATUS_NOT_IMPLEMENTED; + PSAM_DB_OBJECT DomainObject; + PSAM_DB_OBJECT UserObject; + WCHAR szRid[9]; + NTSTATUS Status; + + TRACE("SamrOpenUser(%p %lx %lx %p)\n", + DomainHandle, DesiredAccess, UserId, UserHandle); + + /* Validate the domain handle */ + Status = SampValidateDbObject(DomainHandle, + SamDbDomainObject, + DOMAIN_LOOKUP, + &DomainObject); + if (!NT_SUCCESS(Status)) + { + TRACE("failed with status 0x%08lx\n", Status); + return Status; + } + + /* Convert the RID into a string (hex) */ + swprintf(szRid, L"%08lX", UserId); + + /* Create the user object */ + Status = SampOpenDbObject(DomainObject, + L"Users", + szRid, + SamDbUserObject, + DesiredAccess, + &UserObject); + if (!NT_SUCCESS(Status)) + { + TRACE("failed with status 0x%08lx\n", Status); + return Status; + } + + *UserHandle = (SAMPR_HANDLE)UserObject; + + return STATUS_SUCCESS; } /* Function 35 */ @@ -686,6 +722,27 @@ SamrQueryInformationUser(IN SAMPR_HANDLE UserHandle, return STATUS_NOT_IMPLEMENTED; } + +static +NTSTATUS +SampSetPasswordInformation(PSAM_DB_OBJECT UserObject, + PSAMPR_USER_SET_PASSWORD_INFORMATION PasswordInfo) +{ + NTSTATUS Status; + + TRACE("Password: %S\n", PasswordInfo->Password.Buffer); + TRACE("PasswordExpired: %d\n", PasswordInfo->PasswordExpired); + + Status = SampSetObjectAttribute(UserObject, + L"Password", + REG_SZ, + PasswordInfo->Password.Buffer, + PasswordInfo->Password.MaximumLength); + + return Status; +} + + /* Function 37 */ NTSTATUS NTAPI @@ -693,8 +750,36 @@ SamrSetInformationUser(IN SAMPR_HANDLE UserHandle, IN USER_INFORMATION_CLASS UserInformationClass, IN PSAMPR_USER_INFO_BUFFER Buffer) { - UNIMPLEMENTED; - return STATUS_NOT_IMPLEMENTED; + PSAM_DB_OBJECT UserObject; + NTSTATUS Status; + + TRACE("SamrSetInformationUser(%p %lu %p)\n", + UserHandle, UserInformationClass, Buffer); + + /* Validate the domain handle */ + Status = SampValidateDbObject(UserHandle, + SamDbUserObject, + USER_FORCE_PASSWORD_CHANGE, + &UserObject); + if (!NT_SUCCESS(Status)) + { + TRACE("failed with status 0x%08lx\n", Status); + return Status; + } + + switch (UserInformationClass) + { + case UserSetPasswordInformation: + Status = SampSetPasswordInformation(UserObject, + (PSAMPR_USER_SET_PASSWORD_INFORMATION)Buffer); + break; + + default: + Status = STATUS_INVALID_INFO_CLASS; + break; + } + + return Status; } /* Function 38 */ @@ -848,7 +933,7 @@ NTAPI SamrCreateUser2InDomain(IN SAMPR_HANDLE DomainHandle, IN PRPC_UNICODE_STRING Name, IN unsigned long AccountType, - IN unsigned long DesiredAccess, + IN ACCESS_MASK DesiredAccess, OUT SAMPR_HANDLE *UserHandle, OUT unsigned long *GrantedAccess, OUT unsigned long *RelativeId) diff --git a/reactos/dll/win32/samsrv/samsrv.h b/reactos/dll/win32/samsrv/samsrv.h index af33771808e..9c4037f78a6 100644 --- a/reactos/dll/win32/samsrv/samsrv.h +++ b/reactos/dll/win32/samsrv/samsrv.h @@ -7,7 +7,7 @@ * PROGRAMMERS: Eric Kohl */ -#include +#include #define WIN32_NO_STATUS #include #define NTOS_MODE_USER @@ -16,6 +16,7 @@ #include #include #include +#include #include diff --git a/reactos/dll/win32/samsrv/setup.c b/reactos/dll/win32/samsrv/setup.c index 94501607c0c..cc62d1533d1 100644 --- a/reactos/dll/win32/samsrv/setup.c +++ b/reactos/dll/win32/samsrv/setup.c @@ -13,6 +13,9 @@ WINE_DEFAULT_DEBUG_CHANNEL(samsrv); +/* GLOBALS *****************************************************************/ + +SID_IDENTIFIER_AUTHORITY SecurityNtAuthority = {SECURITY_NT_AUTHORITY}; /* FUNCTIONS ***************************************************************/ @@ -56,60 +59,220 @@ SampIsSetupRunning(VOID) static BOOL -CreateNamesKey(HKEY hParentKey) +SampCreateUserAccount(HKEY hDomainKey, + LPCWSTR lpAccountName, + ULONG ulRelativeId) { DWORD dwDisposition; - HKEY hNamesKey; + WCHAR szUserKeyName[32]; + HKEY hUserKey = NULL; + HKEY hNamesKey = NULL; - if (RegCreateKeyExW(hParentKey, - L"Names", + swprintf(szUserKeyName, L"Users\\%08lX", ulRelativeId); + + if (!RegCreateKeyExW(hDomainKey, + szUserKeyName, + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_ALL_ACCESS, + NULL, + &hUserKey, + &dwDisposition)) + { + RegSetValueEx(hUserKey, + L"Name", + 0, + REG_SZ, + (LPVOID)lpAccountName, + (wcslen(lpAccountName) + 1) * sizeof(WCHAR)); + + RegCloseKey(hUserKey); + } + + if (!RegOpenKeyExW(hDomainKey, + L"Users\\Names", + 0, + KEY_ALL_ACCESS, + &hNamesKey)) + { + RegSetValueEx(hNamesKey, + lpAccountName, + 0, + REG_DWORD, + (LPVOID)&ulRelativeId, + sizeof(ULONG)); + + RegCloseKey(hNamesKey); + } + + return TRUE; +} + + +static BOOL +SampCreateDomain(IN HKEY hDomainsKey, + IN LPCWSTR lpDomainName, + IN PSID lpDomainSid, + OUT PHKEY lpDomainKey) +{ + DWORD dwDisposition; + HKEY hDomainKey = NULL; + HKEY hAliasKey = NULL; + HKEY hGroupsKey = NULL; + HKEY hUsersKey = NULL; + HKEY hNamesKey = NULL; + + if (lpDomainKey != NULL) + *lpDomainKey = NULL; + + if (RegCreateKeyExW(hDomainsKey, + lpDomainName, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_ALL_ACCESS, NULL, - &hNamesKey, + &hDomainKey, &dwDisposition)) return FALSE; - RegCloseKey(hNamesKey); + if (lpDomainSid != NULL) + { + RegSetValueEx(hDomainKey, + L"SID", + 0, + REG_BINARY, + (LPVOID)lpDomainSid, + RtlLengthSid(lpDomainSid)); + } + + /* Create the Alias container */ + if (!RegCreateKeyExW(hDomainKey, + L"Alias", + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_ALL_ACCESS, + NULL, + &hAliasKey, + &dwDisposition)) + { + if (!RegCreateKeyExW(hAliasKey, + L"Names", + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_ALL_ACCESS, + NULL, + &hNamesKey, + &dwDisposition)) + RegCloseKey(hNamesKey); + + RegCloseKey(hAliasKey); + } + + /* Create the Groups container */ + if (!RegCreateKeyExW(hDomainKey, + L"Groups", + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_ALL_ACCESS, + NULL, + &hGroupsKey, + &dwDisposition)) + { + if (!RegCreateKeyExW(hGroupsKey, + L"Names", + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_ALL_ACCESS, + NULL, + &hNamesKey, + &dwDisposition)) + RegCloseKey(hNamesKey); + + RegCloseKey(hGroupsKey); + } + + + /* Create the Users container */ + if (!RegCreateKeyExW(hDomainKey, + L"Users", + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_ALL_ACCESS, + NULL, + &hUsersKey, + &dwDisposition)) + { + if (!RegCreateKeyExW(hUsersKey, + L"Names", + 0, + NULL, + REG_OPTION_NON_VOLATILE, + KEY_ALL_ACCESS, + NULL, + &hNamesKey, + &dwDisposition)) + RegCloseKey(hNamesKey); + + RegCloseKey(hUsersKey); + } + + if (lpDomainKey != NULL) + *lpDomainKey = hDomainKey; + return TRUE; } -static BOOL -CreateBuiltinAliases(HKEY hAliasesKey) +NTSTATUS +SampGetAccountDomainInfo(PPOLICY_ACCOUNT_DOMAIN_INFO *AccountDomainInfo) { - return TRUE; -} + LSA_OBJECT_ATTRIBUTES ObjectAttributes; + LSA_HANDLE PolicyHandle; + NTSTATUS Status; + TRACE("SampGetAccountDomainInfo\n"); -static BOOL -CreateBuiltinGroups(HKEY hGroupsKey) -{ - return TRUE; -} + memset(&ObjectAttributes, 0, sizeof(LSA_OBJECT_ATTRIBUTES)); + ObjectAttributes.Length = sizeof(LSA_OBJECT_ATTRIBUTES); + Status = LsaOpenPolicy(NULL, + &ObjectAttributes, + POLICY_TRUST_ADMIN, + &PolicyHandle); + if (Status != STATUS_SUCCESS) + { + ERR("LsaOpenPolicy failed (Status: 0x%08lx)\n", Status); + return Status; + } -static BOOL -CreateBuiltinUsers(HKEY hUsersKey) -{ - return TRUE; + Status = LsaQueryInformationPolicy(PolicyHandle, + PolicyAccountDomainInformation, + (PVOID *)AccountDomainInfo); + + LsaClose(PolicyHandle); + + return Status; } BOOL SampInitializeSAM(VOID) { + PPOLICY_ACCOUNT_DOMAIN_INFO AccountDomainInfo = NULL; DWORD dwDisposition; HKEY hSamKey = NULL; HKEY hDomainsKey = NULL; - HKEY hAccountKey = NULL; - HKEY hBuiltinKey = NULL; - HKEY hAliasesKey = NULL; - HKEY hGroupsKey = NULL; - HKEY hUsersKey = NULL; + HKEY hDomainKey = NULL; + PSID pBuiltinSid = NULL; BOOL bResult = TRUE; + NTSTATUS Status; TRACE("SampInitializeSAM() called\n"); @@ -145,237 +308,60 @@ SampInitializeSAM(VOID) RegCloseKey(hSamKey); hSamKey = NULL; - /* Create the 'Domains\\Account' key */ - if (RegCreateKeyExW(hDomainsKey, - L"Account", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hAccountKey, - &dwDisposition)) + /* Create and initialize the Builtin Domain SID */ + pBuiltinSid = RtlAllocateHeap(RtlGetProcessHeap(), 0, RtlLengthRequiredSid(1)); + if (pBuiltinSid == NULL) { - ERR("Failed to create 'Domains\\Account' key! (Error %lu)\n", GetLastError()); + ERR("Failed to alloacte the Builtin Domain SID\n"); bResult = FALSE; goto done; } + RtlInitializeSid(pBuiltinSid, &SecurityNtAuthority, 1); + *(RtlSubAuthoritySid(pBuiltinSid, 0)) = SECURITY_BUILTIN_DOMAIN_RID; - /* Create the 'Account\Aliases' key */ - if (RegCreateKeyExW(hAccountKey, - L"Aliases", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hAliasesKey, - &dwDisposition)) + /* Get account domain information */ + Status = SampGetAccountDomainInfo(&AccountDomainInfo); + if (!NT_SUCCESS(Status)) { - ERR("Failed to create 'Account\\Aliases' key! (Error %lu)\n", GetLastError()); + ERR("SampGetAccountDomainInfo failed (Status %08lx)\n", Status); bResult = FALSE; goto done; } - if (!CreateNamesKey(hAliasesKey)) + /* Create the Builtin domain */ + if (SampCreateDomain(hDomainsKey, + L"Builtin", + pBuiltinSid, + &hDomainKey)) { - ERR("Failed to create 'Account\\Aliases\\Names' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; + + RegCloseKey(hDomainKey); } - RegCloseKey(hAliasesKey); - hAliasesKey = NULL; - - /* Create the 'Account\Groups' key */ - if (RegCreateKeyExW(hAccountKey, - L"Groups", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hGroupsKey, - &dwDisposition)) + /* Create the Account domain */ + if (SampCreateDomain(hDomainsKey, + L"Account", + AccountDomainInfo->DomainSid, //NULL, + &hDomainKey)) { - ERR("Failed to create 'Account\\Groups' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } + SampCreateUserAccount(hDomainKey, + L"Administrator", + DOMAIN_USER_RID_ADMIN); - if (!CreateNamesKey(hGroupsKey)) - { - ERR("Failed to create 'Account\\Groups\\Names' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } + SampCreateUserAccount(hDomainKey, + L"Guest", + DOMAIN_USER_RID_GUEST); - RegCloseKey(hGroupsKey); - hGroupsKey = NULL; - - - /* Create the 'Account\Users' key */ - if (RegCreateKeyExW(hAccountKey, - L"Users", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hUsersKey, - &dwDisposition)) - { - ERR("Failed to create 'Account\\Users' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - if (!CreateNamesKey(hUsersKey)) - { - ERR("Failed to create 'Account\\Aliases\\Users' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - RegCloseKey(hUsersKey); - hUsersKey = NULL; - - RegCloseKey(hAccountKey); - hAccountKey = NULL; - - /* Create the 'Domains\\Builtin' */ - if (RegCreateKeyExW(hDomainsKey, - L"Builtin", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hBuiltinKey, - &dwDisposition)) - { - ERR("Failed to create Builtin key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - - /* Create the 'Builtin\Aliases' key */ - if (RegCreateKeyExW(hBuiltinKey, - L"Aliases", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hAliasesKey, - &dwDisposition)) - { - ERR("Failed to create 'Builtin\\Aliases' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - if (!CreateNamesKey(hAliasesKey)) - { - ERR("Failed to create 'Builtin\\Aliases\\Names' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - /* Create builtin aliases */ - if (!CreateBuiltinAliases(hAliasesKey)) - { - ERR("Failed to create builtin aliases!\n"); - bResult = FALSE; - goto done; - } - - RegCloseKey(hAliasesKey); - hAliasesKey = NULL; - - /* Create the 'Builtin\Groups' key */ - if (RegCreateKeyExW(hBuiltinKey, - L"Groups", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hGroupsKey, - &dwDisposition)) - { - ERR("Failed to create 'Builtin\\Groups' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - if (!CreateNamesKey(hGroupsKey)) - { - ERR("Failed to create 'Builtin\\Groups\\Names' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - /* Create builtin groups */ - if (!CreateBuiltinGroups(hGroupsKey)) - { - ERR("Failed to create builtin groups!\n"); - bResult = FALSE; - goto done; - } - - RegCloseKey(hGroupsKey); - hGroupsKey = NULL; - - - /* Create the 'Builtin\Users' key */ - if (RegCreateKeyExW(hBuiltinKey, - L"Users", - 0, - NULL, - REG_OPTION_NON_VOLATILE, - KEY_ALL_ACCESS, - NULL, - &hUsersKey, - &dwDisposition)) - { - ERR("Failed to create 'Builtin\\Users' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - if (!CreateNamesKey(hUsersKey)) - { - ERR("Failed to create 'Builtin\\Users\\Names' key! (Error %lu)\n", GetLastError()); - bResult = FALSE; - goto done; - } - - /* Create builtin users */ - if (!CreateBuiltinUsers(hUsersKey)) - { - ERR("Failed to create builtin users!\n"); - bResult = FALSE; - goto done; + RegCloseKey(hDomainKey); } done: - if (hAliasesKey) - RegCloseKey(hAliasesKey); + if (AccountDomainInfo) + LsaFreeMemory(AccountDomainInfo); - if (hGroupsKey) - RegCloseKey(hGroupsKey); - - if (hUsersKey) - RegCloseKey(hUsersKey); - - if (hAccountKey) - RegCloseKey(hAccountKey); - - if (hBuiltinKey) - RegCloseKey(hBuiltinKey); + if (pBuiltinSid) + RtlFreeHeap(RtlGetProcessHeap(), 0, pBuiltinSid); if (hDomainsKey) RegCloseKey(hDomainsKey); diff --git a/reactos/include/ddk/ntsam.h b/reactos/include/ddk/ntsam.h index fec2f53c01e..b1e7dc4818d 100644 --- a/reactos/include/ddk/ntsam.h +++ b/reactos/include/ddk/ntsam.h @@ -25,9 +25,60 @@ extern "C" { #define SAM_SERVER_ENUMERATE_DOMAINS 16 #define SAM_SERVER_LOOKUP_DOMAIN 32 +#define USER_READ_GENERAL 1 +#define USER_READ_PREFERENCES 2 +#define USER_WRITE_PREFERENCES 4 +#define USER_READ_LOGON 8 +#define USER_READ_ACCOUNT 16 +#define USER_WRITE_ACCOUNT 32 +#define USER_CHANGE_PASSWORD 64 +#define USER_FORCE_PASSWORD_CHANGE 128 +#define USER_LIST_GROUPS 256 +#define USER_READ_GROUP_INFORMATION 512 +#define USER_WRITE_GROUP_INFORMATION 1024 typedef PVOID SAM_HANDLE, *PSAM_HANDLE; +typedef enum _USER_INFORMATION_CLASS +{ + UserGeneralInformation = 1, + UserPreferencesInformation, + UserLogonInformation, + UserLogonHoursInformation, + UserAccountInformation, + UserNameInformation, + UserAccountNameInformation, + UserFullNameInformation, + UserPrimaryGroupInformation, + UserHomeInformation, + UserScriptInformation, + UserProfileInformation, + UserAdminCommentInformation, + UserWorkStationsInformation, + UserSetPasswordInformation, + UserControlInformation, + UserExpiresInformation, + UserInternal1Information, + UserInternal2Information, + UserParametersInformation, + UserAllInformation, + UserInternal3Information, + UserInternal4Information, + UserInternal5Information, + UserInternal4InformationNew, + UserInternal5InformationNew, + UserInternal6Information, + UserExtendedInformation, + UserLogonUIInformation, +} USER_INFORMATION_CLASS, *PUSER_INFORMATION_CLASS; + +typedef struct _USER_SET_PASSWORD_INFORMATION +{ + UNICODE_STRING Password; + BOOLEAN PasswordExpired; +} USER_SET_PASSWORD_INFORMATION, *PUSER_SET_PASSWORD_INFORMATION; + + NTSTATUS NTAPI SamCloseHandle(IN SAM_HANDLE SamHandle); @@ -54,6 +105,25 @@ SamOpenDomain(IN SAM_HANDLE ServerHandle, IN PSID DomainId, OUT PSAM_HANDLE DomainHandle); +NTSTATUS +NTAPI +SamOpenUser(IN SAM_HANDLE DomainHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG UserId, + OUT PSAM_HANDLE UserHandle); + +NTSTATUS +NTAPI +SamQueryInformationUser(IN SAM_HANDLE UserHandle, + IN USER_INFORMATION_CLASS UserInformationClass, + OUT PVOID *Buffer); + +NTSTATUS +NTAPI +SamSetInformationUser(IN SAM_HANDLE UserHandle, + IN USER_INFORMATION_CLASS UserInformationClass, + IN PVOID Buffer); + NTSTATUS NTAPI SamShutdownSamServer(IN SAM_HANDLE ServerHandle); diff --git a/reactos/include/reactos/idl/sam.idl b/reactos/include/reactos/idl/sam.idl index 141629ac0e9..cff102494dc 100644 --- a/reactos/include/reactos/idl/sam.idl +++ b/reactos/include/reactos/idl/sam.idl @@ -152,6 +152,7 @@ typedef enum _DOMAIN_SERVER_ROLE DomainServerRolePrimary = 3 } DOMAIN_SERVER_ROLE, *PDOMAIN_SERVER_ROLE; +cpp_quote("#ifndef _NTSECAPI_H") typedef struct _DOMAIN_PASSWORD_INFORMATION { unsigned short MinPasswordLength; @@ -160,6 +161,7 @@ typedef struct _DOMAIN_PASSWORD_INFORMATION OLD_LARGE_INTEGER MaxPasswordAge; OLD_LARGE_INTEGER MinPasswordAge; } DOMAIN_PASSWORD_INFORMATION, *PDOMAIN_PASSWORD_INFORMATION; +cpp_quote("#endif") typedef struct _DOMAIN_LOGOFF_INFORMATION { @@ -600,6 +602,13 @@ typedef struct _SAMPR_USER_WORKSTATIONS_INFORMATION RPC_UNICODE_STRING WorkStations; } SAMPR_USER_WORKSTATIONS_INFORMATION, *PSAMPR_USER_WORKSTATIONS_INFORMATION; +typedef struct _SAMPR_USER_SET_PASSWORD_INFORMATION +{ +// SAMPR_ENCRYPTED_USER_PASSWORD Password; + RPC_UNICODE_STRING Password; + BOOLEAN PasswordExpired; +} SAMPR_USER_SET_PASSWORD_INFORMATION, *PSAMPR_USER_SET_PASSWORD_INFORMATION; + typedef struct _SAMPR_USER_LOGON_HOURS_INFORMATION { SAMPR_LOGON_HOURS LogonHours; @@ -638,6 +647,7 @@ typedef struct _SAMPR_USER_INTERNAL5_INFORMATION_NEW unsigned char PasswordExpired; } SAMPR_USER_INTERNAL5_INFORMATION_NEW, *PSAMPR_USER_INTERNAL5_INFORMATION_NEW; +cpp_quote("#ifndef _NTSAM_") typedef enum _USER_INFORMATION_CLASS { UserGeneralInformation = 1, @@ -654,16 +664,23 @@ typedef enum _USER_INFORMATION_CLASS UserProfileInformation = 12, UserAdminCommentInformation = 13, UserWorkStationsInformation = 14, + UserSetPasswordInformation = 15, /* This is missing from the SAM RPC documentation */ UserControlInformation = 16, UserExpiresInformation = 17, UserInternal1Information = 18, + UserInternal2Information = 19, /* This is missing from the SAM RPC documentation */ UserParametersInformation = 20, UserAllInformation = 21, + UserInternal3Information = 22, /* This is missing from the SAM RPC documentation */ UserInternal4Information = 23, UserInternal5Information = 24, UserInternal4InformationNew = 25, UserInternal5InformationNew = 26, + UserInternal6Information, /* This is missing from the SAM RPC documentation */ + UserExtendedInformation, /* This is missing from the SAM RPC documentation */ + UserLogonUIInformation, /* This is missing from the SAM RPC documentation */ } USER_INFORMATION_CLASS, *PUSER_INFORMATION_CLASS; +cpp_quote("#endif") typedef [switch_type(USER_INFORMATION_CLASS)] union _SAMPR_USER_INFO_BUFFER { @@ -681,6 +698,7 @@ typedef [switch_type(USER_INFORMATION_CLASS)] union _SAMPR_USER_INFO_BUFFER [case(UserProfileInformation)] SAMPR_USER_PROFILE_INFORMATION Profile; [case(UserAdminCommentInformation)] SAMPR_USER_ADMIN_COMMENT_INFORMATION AdminComment; [case(UserWorkStationsInformation)] SAMPR_USER_WORKSTATIONS_INFORMATION WorkStations; + [case(UserSetPasswordInformation)] SAMPR_USER_SET_PASSWORD_INFORMATION SetPassword; [case(UserControlInformation)] USER_CONTROL_INFORMATION Control; [case(UserExpiresInformation)] USER_EXPIRES_INFORMATION Expires; [case(UserInternal1Information)] SAMPR_USER_INTERNAL1_INFORMATION Internal1; @@ -1015,7 +1033,7 @@ interface samr __stdcall SamrOpenAlias( [in] SAMPR_HANDLE DomainHandle, - [in] unsigned long DesiredAccess, + [in] ACCESS_MASK DesiredAccess, [in] unsigned long AliasId, [out] SAMPR_HANDLE *AliasHandle); @@ -1067,7 +1085,7 @@ interface samr __stdcall SamrOpenUser( [in] SAMPR_HANDLE DomainHandle, - [in] unsigned long DesiredAccess, + [in] ACCESS_MASK DesiredAccess, [in] unsigned long UserId, [out] SAMPR_HANDLE *UserHandle); @@ -1209,7 +1227,7 @@ interface samr [in] SAMPR_HANDLE DomainHandle, [in] PRPC_UNICODE_STRING Name, [in] unsigned long AccountType, - [in] unsigned long DesiredAccess, + [in] ACCESS_MASK DesiredAccess, [out] SAMPR_HANDLE *UserHandle, [out] unsigned long *GrantedAccess, [out] unsigned long *RelativeId);