xref: /reactos/ntoskrnl/se/semgr.c (revision 8b75dce4)
1c2c66affSColin Finck /*
26413009cSGeorge Bișoc  * PROJECT:     ReactOS Kernel
36413009cSGeorge Bișoc  * LICENSE:     GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later)
46413009cSGeorge Bișoc  * PURPOSE:     Security manager infrastructure
56413009cSGeorge Bișoc  * COPYRIGHT:   Copyright Timo Kreuzer <timo.kreuzer@reactos.org>
66413009cSGeorge Bișoc  *              Copyright Eric Kohl
76413009cSGeorge Bișoc  *              Copyright Aleksey Bragin
86413009cSGeorge Bișoc  *              Copyright Alex Ionescu <alex@relsoft.net>
9c2c66affSColin Finck  */
10c2c66affSColin Finck 
11c2c66affSColin Finck /* INCLUDES *******************************************************************/
12c2c66affSColin Finck 
13c2c66affSColin Finck #include <ntoskrnl.h>
14c2c66affSColin Finck #define NDEBUG
15c2c66affSColin Finck #include <debug.h>
16c2c66affSColin Finck 
17c2c66affSColin Finck /* GLOBALS ********************************************************************/
18c2c66affSColin Finck 
195b5b814aSGeorge Bișoc PTOKEN SeAnonymousLogonToken = NULL;
205b5b814aSGeorge Bișoc PTOKEN SeAnonymousLogonTokenNoEveryone = NULL;
21c2c66affSColin Finck PSE_EXPORTS SeExports = NULL;
22c2c66affSColin Finck SE_EXPORTS SepExports;
23c2c66affSColin Finck ULONG SidInTokenCalls = 0;
24c2c66affSColin Finck 
25c2c66affSColin Finck extern ULONG ExpInitializationPhase;
26c2c66affSColin Finck extern ERESOURCE SepSubjectContextLock;
27c2c66affSColin Finck 
28c2c66affSColin Finck /* PRIVATE FUNCTIONS **********************************************************/
29c2c66affSColin Finck 
306413009cSGeorge Bișoc /**
316413009cSGeorge Bișoc  * @brief
326413009cSGeorge Bișoc  * Initializes all the security exports upon initialization phase of
336413009cSGeorge Bișoc  * the module.
346413009cSGeorge Bișoc  *
356413009cSGeorge Bișoc  * @return
366413009cSGeorge Bișoc  * Returns TRUE.
376413009cSGeorge Bișoc  */
3871fefa32STimo Kreuzer static
395c7ce447SVictor Perevertkin CODE_SEG("INIT")
4071fefa32STimo Kreuzer BOOLEAN
SepInitExports(VOID)41c2c66affSColin Finck SepInitExports(VOID)
42c2c66affSColin Finck {
43c2c66affSColin Finck     SepExports.SeCreateTokenPrivilege = SeCreateTokenPrivilege;
44c2c66affSColin Finck     SepExports.SeAssignPrimaryTokenPrivilege = SeAssignPrimaryTokenPrivilege;
45c2c66affSColin Finck     SepExports.SeLockMemoryPrivilege = SeLockMemoryPrivilege;
46c2c66affSColin Finck     SepExports.SeIncreaseQuotaPrivilege = SeIncreaseQuotaPrivilege;
47c2c66affSColin Finck     SepExports.SeUnsolicitedInputPrivilege = SeUnsolicitedInputPrivilege;
48c2c66affSColin Finck     SepExports.SeTcbPrivilege = SeTcbPrivilege;
49c2c66affSColin Finck     SepExports.SeSecurityPrivilege = SeSecurityPrivilege;
50c2c66affSColin Finck     SepExports.SeTakeOwnershipPrivilege = SeTakeOwnershipPrivilege;
51c2c66affSColin Finck     SepExports.SeLoadDriverPrivilege = SeLoadDriverPrivilege;
52c2c66affSColin Finck     SepExports.SeCreatePagefilePrivilege = SeCreatePagefilePrivilege;
53c2c66affSColin Finck     SepExports.SeIncreaseBasePriorityPrivilege = SeIncreaseBasePriorityPrivilege;
54c2c66affSColin Finck     SepExports.SeSystemProfilePrivilege = SeSystemProfilePrivilege;
55c2c66affSColin Finck     SepExports.SeSystemtimePrivilege = SeSystemtimePrivilege;
56c2c66affSColin Finck     SepExports.SeProfileSingleProcessPrivilege = SeProfileSingleProcessPrivilege;
57c2c66affSColin Finck     SepExports.SeCreatePermanentPrivilege = SeCreatePermanentPrivilege;
58c2c66affSColin Finck     SepExports.SeBackupPrivilege = SeBackupPrivilege;
59c2c66affSColin Finck     SepExports.SeRestorePrivilege = SeRestorePrivilege;
60c2c66affSColin Finck     SepExports.SeShutdownPrivilege = SeShutdownPrivilege;
61c2c66affSColin Finck     SepExports.SeDebugPrivilege = SeDebugPrivilege;
62c2c66affSColin Finck     SepExports.SeAuditPrivilege = SeAuditPrivilege;
63c2c66affSColin Finck     SepExports.SeSystemEnvironmentPrivilege = SeSystemEnvironmentPrivilege;
64c2c66affSColin Finck     SepExports.SeChangeNotifyPrivilege = SeChangeNotifyPrivilege;
65c2c66affSColin Finck     SepExports.SeRemoteShutdownPrivilege = SeRemoteShutdownPrivilege;
66c2c66affSColin Finck 
67c2c66affSColin Finck     SepExports.SeNullSid = SeNullSid;
68c2c66affSColin Finck     SepExports.SeWorldSid = SeWorldSid;
69c2c66affSColin Finck     SepExports.SeLocalSid = SeLocalSid;
70c2c66affSColin Finck     SepExports.SeCreatorOwnerSid = SeCreatorOwnerSid;
71c2c66affSColin Finck     SepExports.SeCreatorGroupSid = SeCreatorGroupSid;
72c2c66affSColin Finck     SepExports.SeNtAuthoritySid = SeNtAuthoritySid;
73c2c66affSColin Finck     SepExports.SeDialupSid = SeDialupSid;
74c2c66affSColin Finck     SepExports.SeNetworkSid = SeNetworkSid;
75c2c66affSColin Finck     SepExports.SeBatchSid = SeBatchSid;
76c2c66affSColin Finck     SepExports.SeInteractiveSid = SeInteractiveSid;
77c2c66affSColin Finck     SepExports.SeLocalSystemSid = SeLocalSystemSid;
78c2c66affSColin Finck     SepExports.SeAliasAdminsSid = SeAliasAdminsSid;
79c2c66affSColin Finck     SepExports.SeAliasUsersSid = SeAliasUsersSid;
80c2c66affSColin Finck     SepExports.SeAliasGuestsSid = SeAliasGuestsSid;
81c2c66affSColin Finck     SepExports.SeAliasPowerUsersSid = SeAliasPowerUsersSid;
82c2c66affSColin Finck     SepExports.SeAliasAccountOpsSid = SeAliasAccountOpsSid;
83c2c66affSColin Finck     SepExports.SeAliasSystemOpsSid = SeAliasSystemOpsSid;
84c2c66affSColin Finck     SepExports.SeAliasPrintOpsSid = SeAliasPrintOpsSid;
85c2c66affSColin Finck     SepExports.SeAliasBackupOpsSid = SeAliasBackupOpsSid;
86c2c66affSColin Finck     SepExports.SeAuthenticatedUsersSid = SeAuthenticatedUsersSid;
87c2c66affSColin Finck     SepExports.SeRestrictedSid = SeRestrictedSid;
88c2c66affSColin Finck     SepExports.SeAnonymousLogonSid = SeAnonymousLogonSid;
89c2c66affSColin Finck     SepExports.SeLocalServiceSid = SeLocalServiceSid;
90c2c66affSColin Finck     SepExports.SeNetworkServiceSid = SeNetworkServiceSid;
91c2c66affSColin Finck 
92c2c66affSColin Finck     SepExports.SeUndockPrivilege = SeUndockPrivilege;
93c2c66affSColin Finck     SepExports.SeSyncAgentPrivilege = SeSyncAgentPrivilege;
94c2c66affSColin Finck     SepExports.SeEnableDelegationPrivilege = SeEnableDelegationPrivilege;
95c2c66affSColin Finck     SepExports.SeManageVolumePrivilege = SeManageVolumePrivilege;
96c2c66affSColin Finck     SepExports.SeImpersonatePrivilege = SeImpersonatePrivilege;
97c2c66affSColin Finck     SepExports.SeCreateGlobalPrivilege = SeCreateGlobalPrivilege;
98c2c66affSColin Finck 
99c2c66affSColin Finck     SeExports = &SepExports;
100c2c66affSColin Finck     return TRUE;
101c2c66affSColin Finck }
102c2c66affSColin Finck 
1036413009cSGeorge Bișoc /**
1046413009cSGeorge Bișoc  * @brief
1056413009cSGeorge Bișoc  * Handles the phase 0 procedure of the SRM initialization.
1066413009cSGeorge Bișoc  *
1076413009cSGeorge Bișoc  * @return
1086413009cSGeorge Bișoc  * Returns TRUE if the phase 0 initialization has succeeded and that
1096413009cSGeorge Bișoc  * we can proceed further with next initialization phase, FALSE
1106413009cSGeorge Bișoc  * otherwise.
1116413009cSGeorge Bișoc  */
1125c7ce447SVictor Perevertkin CODE_SEG("INIT")
113c2c66affSColin Finck BOOLEAN
114c2c66affSColin Finck NTAPI
SepInitializationPhase0(VOID)115c2c66affSColin Finck SepInitializationPhase0(VOID)
116c2c66affSColin Finck {
117c2c66affSColin Finck     PAGED_CODE();
118c2c66affSColin Finck 
119eb8b481cSPierre Schweitzer     if (!ExLuidInitialization()) return FALSE;
120c2c66affSColin Finck     if (!SepInitSecurityIDs()) return FALSE;
121c2c66affSColin Finck     if (!SepInitDACLs()) return FALSE;
122c2c66affSColin Finck     if (!SepInitSDs()) return FALSE;
123c2c66affSColin Finck     SepInitPrivileges();
124c2c66affSColin Finck     if (!SepInitExports()) return FALSE;
125c2c66affSColin Finck 
126c2c66affSColin Finck     /* Initialize the subject context lock */
127c2c66affSColin Finck     ExInitializeResource(&SepSubjectContextLock);
128c2c66affSColin Finck 
129c2c66affSColin Finck     /* Initialize token objects */
130c2c66affSColin Finck     SepInitializeTokenImplementation();
131c2c66affSColin Finck 
132c2c66affSColin Finck     /* Initialize logon sessions */
133c2c66affSColin Finck     if (!SeRmInitPhase0()) return FALSE;
134c2c66affSColin Finck 
135c2c66affSColin Finck     /* Clear impersonation info for the idle thread */
136c2c66affSColin Finck     PsGetCurrentThread()->ImpersonationInfo = NULL;
137c2c66affSColin Finck     PspClearCrossThreadFlag(PsGetCurrentThread(),
138c2c66affSColin Finck                             CT_ACTIVE_IMPERSONATION_INFO_BIT);
139c2c66affSColin Finck 
140c2c66affSColin Finck     /* Initialize the boot token */
141c2c66affSColin Finck     ObInitializeFastReference(&PsGetCurrentProcess()->Token, NULL);
142c2c66affSColin Finck     ObInitializeFastReference(&PsGetCurrentProcess()->Token,
143c2c66affSColin Finck                               SepCreateSystemProcessToken());
1445b5b814aSGeorge Bișoc 
1455b5b814aSGeorge Bișoc     /* Initialise the anonymous logon tokens */
1465b5b814aSGeorge Bișoc     SeAnonymousLogonToken = SepCreateSystemAnonymousLogonToken();
1475b5b814aSGeorge Bișoc     if (!SeAnonymousLogonToken)
1485b5b814aSGeorge Bișoc         return FALSE;
1495b5b814aSGeorge Bișoc 
1505b5b814aSGeorge Bișoc     SeAnonymousLogonTokenNoEveryone = SepCreateSystemAnonymousLogonTokenNoEveryone();
1515b5b814aSGeorge Bișoc     if (!SeAnonymousLogonTokenNoEveryone)
1525b5b814aSGeorge Bișoc         return FALSE;
1535b5b814aSGeorge Bișoc 
154c2c66affSColin Finck     return TRUE;
155c2c66affSColin Finck }
156c2c66affSColin Finck 
1576413009cSGeorge Bișoc /**
1586413009cSGeorge Bișoc  * @brief
1596413009cSGeorge Bișoc  * Handles the phase 1 procedure of the SRM initialization.
1606413009cSGeorge Bișoc  *
1616413009cSGeorge Bișoc  * @return
1626413009cSGeorge Bișoc  * Returns TRUE if the phase 1 initialization has succeeded, FALSE
1636413009cSGeorge Bișoc  * otherwise.
1646413009cSGeorge Bișoc  */
1655c7ce447SVictor Perevertkin CODE_SEG("INIT")
166c2c66affSColin Finck BOOLEAN
167c2c66affSColin Finck NTAPI
SepInitializationPhase1(VOID)168c2c66affSColin Finck SepInitializationPhase1(VOID)
169c2c66affSColin Finck {
170c2c66affSColin Finck     OBJECT_ATTRIBUTES ObjectAttributes;
171c2c66affSColin Finck     UNICODE_STRING Name;
172c2c66affSColin Finck     HANDLE SecurityHandle;
173c2c66affSColin Finck     HANDLE EventHandle;
174c2c66affSColin Finck     NTSTATUS Status;
1756747dacfSPierre Schweitzer     SECURITY_DESCRIPTOR SecurityDescriptor;
1766747dacfSPierre Schweitzer     PACL Dacl;
1776747dacfSPierre Schweitzer     ULONG DaclLength;
178c2c66affSColin Finck 
179c2c66affSColin Finck     PAGED_CODE();
180c2c66affSColin Finck 
181c2c66affSColin Finck     /* Insert the system token into the tree */
182c2c66affSColin Finck     Status = ObInsertObject((PVOID)(PsGetCurrentProcess()->Token.Value &
183c2c66affSColin Finck                                     ~MAX_FAST_REFS),
184c2c66affSColin Finck                             NULL,
185c2c66affSColin Finck                             0,
186c2c66affSColin Finck                             0,
187c2c66affSColin Finck                             NULL,
188c2c66affSColin Finck                             NULL);
189c2c66affSColin Finck     ASSERT(NT_SUCCESS(Status));
190c2c66affSColin Finck 
1916747dacfSPierre Schweitzer     /* Create a security descriptor for the directory */
1926747dacfSPierre Schweitzer     RtlCreateSecurityDescriptor(&SecurityDescriptor, SECURITY_DESCRIPTOR_REVISION);
1936747dacfSPierre Schweitzer 
1946747dacfSPierre Schweitzer     /* Setup the ACL */
1956747dacfSPierre Schweitzer     DaclLength = sizeof(ACL) + 3 * sizeof(ACCESS_ALLOWED_ACE) +
1966747dacfSPierre Schweitzer                  RtlLengthSid(SeLocalSystemSid) +
1976747dacfSPierre Schweitzer                  RtlLengthSid(SeAliasAdminsSid) +
1986747dacfSPierre Schweitzer                  RtlLengthSid(SeWorldSid);
1996747dacfSPierre Schweitzer     Dacl = ExAllocatePoolWithTag(NonPagedPool, DaclLength, TAG_SE);
2006747dacfSPierre Schweitzer     if (Dacl == NULL)
2016747dacfSPierre Schweitzer     {
2026747dacfSPierre Schweitzer         return FALSE;
2036747dacfSPierre Schweitzer     }
2046747dacfSPierre Schweitzer 
2056747dacfSPierre Schweitzer     Status = RtlCreateAcl(Dacl, DaclLength, ACL_REVISION);
2066747dacfSPierre Schweitzer     ASSERT(NT_SUCCESS(Status));
2076747dacfSPierre Schweitzer 
2086747dacfSPierre Schweitzer     /* Grant full access to SYSTEM */
2096747dacfSPierre Schweitzer     Status = RtlAddAccessAllowedAce(Dacl,
2106747dacfSPierre Schweitzer                                     ACL_REVISION,
2116747dacfSPierre Schweitzer                                     DIRECTORY_ALL_ACCESS,
2126747dacfSPierre Schweitzer                                     SeLocalSystemSid);
2136747dacfSPierre Schweitzer     ASSERT(NT_SUCCESS(Status));
2146747dacfSPierre Schweitzer 
2156747dacfSPierre Schweitzer     /* Allow admins to traverse and query */
2166747dacfSPierre Schweitzer     Status = RtlAddAccessAllowedAce(Dacl,
2176747dacfSPierre Schweitzer                                     ACL_REVISION,
2186747dacfSPierre Schweitzer                                     READ_CONTROL | DIRECTORY_TRAVERSE | DIRECTORY_QUERY,
2196747dacfSPierre Schweitzer                                     SeAliasAdminsSid);
2206747dacfSPierre Schweitzer     ASSERT(NT_SUCCESS(Status));
2216747dacfSPierre Schweitzer 
2226747dacfSPierre Schweitzer     /* Allow anyone to traverse */
2236747dacfSPierre Schweitzer     Status = RtlAddAccessAllowedAce(Dacl,
2246747dacfSPierre Schweitzer                                     ACL_REVISION,
2256747dacfSPierre Schweitzer                                     DIRECTORY_TRAVERSE,
2266747dacfSPierre Schweitzer                                     SeWorldSid);
2276747dacfSPierre Schweitzer     ASSERT(NT_SUCCESS(Status));
2286747dacfSPierre Schweitzer 
2296747dacfSPierre Schweitzer     /* And link ACL and SD */
2306747dacfSPierre Schweitzer     Status = RtlSetDaclSecurityDescriptor(&SecurityDescriptor, TRUE, Dacl, FALSE);
2316747dacfSPierre Schweitzer     ASSERT(NT_SUCCESS(Status));
232c2c66affSColin Finck 
233c2c66affSColin Finck     /* Create '\Security' directory */
234c2c66affSColin Finck     RtlInitUnicodeString(&Name, L"\\Security");
235c2c66affSColin Finck     InitializeObjectAttributes(&ObjectAttributes,
236c2c66affSColin Finck                                &Name,
237c2c66affSColin Finck                                OBJ_PERMANENT | OBJ_CASE_INSENSITIVE,
238c2c66affSColin Finck                                0,
2396747dacfSPierre Schweitzer                                &SecurityDescriptor);
240c2c66affSColin Finck 
241c2c66affSColin Finck     Status = ZwCreateDirectoryObject(&SecurityHandle,
242c2c66affSColin Finck                                      DIRECTORY_ALL_ACCESS,
243c2c66affSColin Finck                                      &ObjectAttributes);
244c2c66affSColin Finck     ASSERT(NT_SUCCESS(Status));
245c2c66affSColin Finck 
24695bc44e2SPierre Schweitzer     /* Free the DACL */
24795bc44e2SPierre Schweitzer     ExFreePoolWithTag(Dacl, TAG_SE);
24895bc44e2SPierre Schweitzer 
249c2c66affSColin Finck     /* Create 'LSA_AUTHENTICATION_INITIALIZED' event */
250c2c66affSColin Finck     RtlInitUnicodeString(&Name, L"LSA_AUTHENTICATION_INITIALIZED");
251c2c66affSColin Finck     InitializeObjectAttributes(&ObjectAttributes,
252c2c66affSColin Finck                                &Name,
253c2c66affSColin Finck                                OBJ_PERMANENT | OBJ_CASE_INSENSITIVE,
254c2c66affSColin Finck                                SecurityHandle,
255c2c66affSColin Finck                                SePublicDefaultSd);
256c2c66affSColin Finck 
257c2c66affSColin Finck     Status = ZwCreateEvent(&EventHandle,
258c2c66affSColin Finck                            GENERIC_WRITE,
259c2c66affSColin Finck                            &ObjectAttributes,
260c2c66affSColin Finck                            NotificationEvent,
261c2c66affSColin Finck                            FALSE);
262c2c66affSColin Finck     ASSERT(NT_SUCCESS(Status));
263c2c66affSColin Finck 
264c2c66affSColin Finck     Status = ZwClose(EventHandle);
265c2c66affSColin Finck     ASSERT(NT_SUCCESS(Status));
266c2c66affSColin Finck 
267c2c66affSColin Finck     Status = ZwClose(SecurityHandle);
268c2c66affSColin Finck     ASSERT(NT_SUCCESS(Status));
269c2c66affSColin Finck 
270c2c66affSColin Finck     return TRUE;
271c2c66affSColin Finck }
272c2c66affSColin Finck 
2736413009cSGeorge Bișoc /**
2746413009cSGeorge Bișoc  * @brief
2756413009cSGeorge Bișoc  * Main security manager initialization function.
2766413009cSGeorge Bișoc  *
2776413009cSGeorge Bișoc  * @return
2786413009cSGeorge Bișoc  * Returns a boolean value according to the phase initialization
2796413009cSGeorge Bișoc  * routine that handles it. If TRUE, the routine deems the initialization
2806413009cSGeorge Bișoc  * phase as complete, FALSE otherwise.
2816413009cSGeorge Bișoc  */
2825c7ce447SVictor Perevertkin CODE_SEG("INIT")
283c2c66affSColin Finck BOOLEAN
284c2c66affSColin Finck NTAPI
SeInitSystem(VOID)285c2c66affSColin Finck SeInitSystem(VOID)
286c2c66affSColin Finck {
287c2c66affSColin Finck     /* Check the initialization phase */
288c2c66affSColin Finck     switch (ExpInitializationPhase)
289c2c66affSColin Finck     {
290c2c66affSColin Finck         case 0:
291c2c66affSColin Finck 
292c2c66affSColin Finck             /* Do Phase 0 */
293c2c66affSColin Finck             return SepInitializationPhase0();
294c2c66affSColin Finck 
295c2c66affSColin Finck         case 1:
296c2c66affSColin Finck 
297c2c66affSColin Finck             /* Do Phase 1 */
298c2c66affSColin Finck             return SepInitializationPhase1();
299c2c66affSColin Finck 
300c2c66affSColin Finck         default:
301c2c66affSColin Finck 
302c2c66affSColin Finck             /* Don't know any other phase! Bugcheck! */
303c2c66affSColin Finck             KeBugCheckEx(UNEXPECTED_INITIALIZATION_CALL,
304c2c66affSColin Finck                          0,
305c2c66affSColin Finck                          ExpInitializationPhase,
306c2c66affSColin Finck                          0,
307c2c66affSColin Finck                          0);
308c2c66affSColin Finck             return FALSE;
309c2c66affSColin Finck     }
310c2c66affSColin Finck }
311c2c66affSColin Finck 
3126413009cSGeorge Bișoc /**
3136413009cSGeorge Bișoc  * @brief
3146413009cSGeorge Bișoc  * Internal function that is responsible for querying, deleting, assigning and
3156413009cSGeorge Bișoc  * setting a security descriptor for an object in the NT kernel. It is the default
3166413009cSGeorge Bișoc  * security method for objects regarding the security context of objects.
3176413009cSGeorge Bișoc  *
3186413009cSGeorge Bișoc  * @param[in] Object
3196413009cSGeorge Bișoc  * The object that has the default security method, which the function has been
3206413009cSGeorge Bișoc  * called upon.
3216413009cSGeorge Bișoc  *
3226413009cSGeorge Bișoc  * @param[in] OperationType
3236413009cSGeorge Bișoc  * Operation type to perform to that object.
3246413009cSGeorge Bișoc  *
3256413009cSGeorge Bișoc  * @param[in] SecurityInformation
3266413009cSGeorge Bișoc  * Auxiliary security information of the object.
3276413009cSGeorge Bișoc  *
328*8567d814SGeorge Bișoc  * @param[in,out] SecurityDescriptor
3296413009cSGeorge Bișoc  * A security descriptor. This SD is used accordingly to the operation type
3306413009cSGeorge Bișoc  * requested by the caller.
3316413009cSGeorge Bișoc  *
332*8567d814SGeorge Bișoc  * @param[in,out] ReturnLength
3336413009cSGeorge Bișoc  * The length size of the queried security descriptor, in bytes.
3346413009cSGeorge Bișoc  *
335*8567d814SGeorge Bișoc  * @param[in,out] OldSecurityDescriptor
3366413009cSGeorge Bișoc  * The old SD that belonged to the object, in case we're either deleting
3376413009cSGeorge Bișoc  * or replacing it.
3386413009cSGeorge Bișoc  *
3396413009cSGeorge Bișoc  * @param[in] PoolType
3406413009cSGeorge Bișoc  * Pool type allocation for the security descriptor.
3416413009cSGeorge Bișoc  *
3426413009cSGeorge Bișoc  * @param[in] GenericMapping
3436413009cSGeorge Bișoc  * The generic mapping of access rights masks for the object.
3446413009cSGeorge Bișoc  *
3456413009cSGeorge Bișoc  * @return
3466413009cSGeorge Bișoc  * Returns STATUS_SUCCESS if the specific operation tasked has been
3476413009cSGeorge Bișoc  * completed. Otherwise a failure NTSTATUS code is returned.
3486413009cSGeorge Bișoc  */
349c2c66affSColin Finck NTSTATUS
350c2c66affSColin Finck NTAPI
SeDefaultObjectMethod(_In_ PVOID Object,_In_ SECURITY_OPERATION_CODE OperationType,_In_ PSECURITY_INFORMATION SecurityInformation,_Inout_ PSECURITY_DESCRIPTOR SecurityDescriptor,_Inout_opt_ PULONG ReturnLength,_Inout_ PSECURITY_DESCRIPTOR * OldSecurityDescriptor,_In_ POOL_TYPE PoolType,_In_ PGENERIC_MAPPING GenericMapping)351*8567d814SGeorge Bișoc SeDefaultObjectMethod(
352*8567d814SGeorge Bișoc     _In_ PVOID Object,
353*8567d814SGeorge Bișoc     _In_ SECURITY_OPERATION_CODE OperationType,
354*8567d814SGeorge Bișoc     _In_ PSECURITY_INFORMATION SecurityInformation,
355*8567d814SGeorge Bișoc     _Inout_ PSECURITY_DESCRIPTOR SecurityDescriptor,
356*8567d814SGeorge Bișoc     _Inout_opt_ PULONG ReturnLength,
357*8567d814SGeorge Bișoc     _Inout_ PSECURITY_DESCRIPTOR *OldSecurityDescriptor,
358*8567d814SGeorge Bișoc     _In_ POOL_TYPE PoolType,
359*8567d814SGeorge Bișoc     _In_ PGENERIC_MAPPING GenericMapping)
360c2c66affSColin Finck {
361c2c66affSColin Finck     PAGED_CODE();
362c2c66affSColin Finck 
363c2c66affSColin Finck     /* Select the operation type */
364c2c66affSColin Finck     switch (OperationType)
365c2c66affSColin Finck     {
366c2c66affSColin Finck             /* Setting a new descriptor */
367c2c66affSColin Finck         case SetSecurityDescriptor:
368c2c66affSColin Finck 
369c2c66affSColin Finck             /* Sanity check */
370c2c66affSColin Finck             ASSERT((PoolType == PagedPool) || (PoolType == NonPagedPool));
371c2c66affSColin Finck 
372c2c66affSColin Finck             /* Set the information */
373c2c66affSColin Finck             return ObSetSecurityDescriptorInfo(Object,
374c2c66affSColin Finck                                                SecurityInformation,
375c2c66affSColin Finck                                                SecurityDescriptor,
376c2c66affSColin Finck                                                OldSecurityDescriptor,
377c2c66affSColin Finck                                                PoolType,
378c2c66affSColin Finck                                                GenericMapping);
379c2c66affSColin Finck 
380c2c66affSColin Finck         case QuerySecurityDescriptor:
381c2c66affSColin Finck 
382c2c66affSColin Finck             /* Query the information */
383c2c66affSColin Finck             return ObQuerySecurityDescriptorInfo(Object,
384c2c66affSColin Finck                                                  SecurityInformation,
385c2c66affSColin Finck                                                  SecurityDescriptor,
386c2c66affSColin Finck                                                  ReturnLength,
387c2c66affSColin Finck                                                  OldSecurityDescriptor);
388c2c66affSColin Finck 
389c2c66affSColin Finck         case DeleteSecurityDescriptor:
390c2c66affSColin Finck 
391c2c66affSColin Finck             /* De-assign it */
392c2c66affSColin Finck             return ObDeassignSecurity(OldSecurityDescriptor);
393c2c66affSColin Finck 
394c2c66affSColin Finck         case AssignSecurityDescriptor:
395c2c66affSColin Finck 
396c2c66affSColin Finck             /* Assign it */
397c2c66affSColin Finck             ObAssignObjectSecurityDescriptor(Object, SecurityDescriptor, PoolType);
398c2c66affSColin Finck             return STATUS_SUCCESS;
399c2c66affSColin Finck 
400c2c66affSColin Finck         default:
401c2c66affSColin Finck 
402c2c66affSColin Finck             /* Bug check */
403c2c66affSColin Finck             KeBugCheckEx(SECURITY_SYSTEM, 0, STATUS_INVALID_PARAMETER, 0, 0);
404c2c66affSColin Finck     }
405c2c66affSColin Finck 
406c2c66affSColin Finck     /* Should never reach here */
407c2c66affSColin Finck     ASSERT(FALSE);
408c2c66affSColin Finck     return STATUS_SUCCESS;
409c2c66affSColin Finck }
410c2c66affSColin Finck 
4116413009cSGeorge Bișoc /**
4126413009cSGeorge Bișoc  * @brief
4136413009cSGeorge Bișoc  * Queries the access mask from a security information context.
4146413009cSGeorge Bișoc  *
4156413009cSGeorge Bișoc  * @param[in] SecurityInformation
4166413009cSGeorge Bișoc  * The security information context where the access mask is to be
4176413009cSGeorge Bișoc  * gathered.
4186413009cSGeorge Bișoc  *
4196413009cSGeorge Bișoc  * @param[out] DesiredAccess
4206413009cSGeorge Bișoc  * The queried access mask right.
4216413009cSGeorge Bișoc  *
4226413009cSGeorge Bișoc  * @return
4236413009cSGeorge Bișoc  * Nothing.
4246413009cSGeorge Bișoc  */
425c2c66affSColin Finck VOID
426c2c66affSColin Finck NTAPI
SeQuerySecurityAccessMask(_In_ SECURITY_INFORMATION SecurityInformation,_Out_ PACCESS_MASK DesiredAccess)427*8567d814SGeorge Bișoc SeQuerySecurityAccessMask(
428*8567d814SGeorge Bișoc     _In_ SECURITY_INFORMATION SecurityInformation,
429*8567d814SGeorge Bișoc     _Out_ PACCESS_MASK DesiredAccess)
430c2c66affSColin Finck {
431c2c66affSColin Finck     *DesiredAccess = 0;
432c2c66affSColin Finck 
433c2c66affSColin Finck     if (SecurityInformation & (OWNER_SECURITY_INFORMATION |
434c2c66affSColin Finck                                GROUP_SECURITY_INFORMATION | DACL_SECURITY_INFORMATION))
435c2c66affSColin Finck     {
436c2c66affSColin Finck         *DesiredAccess |= READ_CONTROL;
437c2c66affSColin Finck     }
438c2c66affSColin Finck 
439c2c66affSColin Finck     if (SecurityInformation & SACL_SECURITY_INFORMATION)
440c2c66affSColin Finck     {
441c2c66affSColin Finck         *DesiredAccess |= ACCESS_SYSTEM_SECURITY;
442c2c66affSColin Finck     }
443c2c66affSColin Finck }
444c2c66affSColin Finck 
4456413009cSGeorge Bișoc /**
4466413009cSGeorge Bișoc  * @brief
4476413009cSGeorge Bișoc  * Sets the access mask for a security information context.
4486413009cSGeorge Bișoc  *
4496413009cSGeorge Bișoc  * @param[in] SecurityInformation
4506413009cSGeorge Bișoc  * The security information context to apply a new access right.
4516413009cSGeorge Bișoc  *
4526413009cSGeorge Bișoc  * @param[out] DesiredAccess
4536413009cSGeorge Bișoc  * The returned access mask right.
4546413009cSGeorge Bișoc  *
4556413009cSGeorge Bișoc  * @return
4566413009cSGeorge Bișoc  * Nothing.
4576413009cSGeorge Bișoc  */
458c2c66affSColin Finck VOID
459c2c66affSColin Finck NTAPI
SeSetSecurityAccessMask(_In_ SECURITY_INFORMATION SecurityInformation,_Out_ PACCESS_MASK DesiredAccess)460*8567d814SGeorge Bișoc SeSetSecurityAccessMask(
461*8567d814SGeorge Bișoc     _In_ SECURITY_INFORMATION SecurityInformation,
462*8567d814SGeorge Bișoc     _Out_ PACCESS_MASK DesiredAccess)
463c2c66affSColin Finck {
464c2c66affSColin Finck     *DesiredAccess = 0;
465c2c66affSColin Finck 
466c2c66affSColin Finck     if (SecurityInformation & (OWNER_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION))
467c2c66affSColin Finck     {
468c2c66affSColin Finck         *DesiredAccess |= WRITE_OWNER;
469c2c66affSColin Finck     }
470c2c66affSColin Finck 
471c2c66affSColin Finck     if (SecurityInformation & DACL_SECURITY_INFORMATION)
472c2c66affSColin Finck     {
473c2c66affSColin Finck         *DesiredAccess |= WRITE_DAC;
474c2c66affSColin Finck     }
475c2c66affSColin Finck 
476c2c66affSColin Finck     if (SecurityInformation & SACL_SECURITY_INFORMATION)
477c2c66affSColin Finck     {
478c2c66affSColin Finck         *DesiredAccess |= ACCESS_SYSTEM_SECURITY;
479c2c66affSColin Finck     }
480c2c66affSColin Finck }
481c2c66affSColin Finck 
4826413009cSGeorge Bișoc /**
4836413009cSGeorge Bișoc  * @unimplemented
4846413009cSGeorge Bișoc  * @brief
4856413009cSGeorge Bișoc  * Report a security event to the security manager.
4866413009cSGeorge Bișoc  *
4876413009cSGeorge Bișoc  * @param[in] Flags
4886413009cSGeorge Bișoc  * Flags that influence how the event should be reported.
4896413009cSGeorge Bișoc  *
4906413009cSGeorge Bișoc  * @param[in] SourceName
4916413009cSGeorge Bișoc  * A Unicode string that represents the source name of the event.
4926413009cSGeorge Bișoc  *
4936413009cSGeorge Bișoc  * @param[in] UserSid
4946413009cSGeorge Bișoc  * The SID that represents a user that initiated the reporting.
4956413009cSGeorge Bișoc  *
4966413009cSGeorge Bișoc  * @param[in] AuditParameters
4976413009cSGeorge Bișoc  * An array of parameters for auditing purposes. This is used
4986413009cSGeorge Bișoc  * for reporting the event which the security manager will take
4996413009cSGeorge Bișoc  * care subsequently of doing eventual security auditing.
5006413009cSGeorge Bișoc  *
5016413009cSGeorge Bișoc  * @return
5026413009cSGeorge Bișoc  * Returns STATUS_SUCCESS if the security event has been reported.
5036413009cSGeorge Bișoc  * STATUS_INVALID_PARAMETER is returned if one of the parameters
5046413009cSGeorge Bișoc  * do not satisfy the requirements expected by the function.
5056413009cSGeorge Bișoc  */
506c2c66affSColin Finck NTSTATUS
507c2c66affSColin Finck NTAPI
SeReportSecurityEvent(_In_ ULONG Flags,_In_ PUNICODE_STRING SourceName,_In_opt_ PSID UserSid,_In_ PSE_ADT_PARAMETER_ARRAY AuditParameters)508c2c66affSColin Finck SeReportSecurityEvent(
509c2c66affSColin Finck     _In_ ULONG Flags,
510c2c66affSColin Finck     _In_ PUNICODE_STRING SourceName,
511c2c66affSColin Finck     _In_opt_ PSID UserSid,
512c2c66affSColin Finck     _In_ PSE_ADT_PARAMETER_ARRAY AuditParameters)
513c2c66affSColin Finck {
514c2c66affSColin Finck     SECURITY_SUBJECT_CONTEXT SubjectContext;
515c2c66affSColin Finck     PTOKEN EffectiveToken;
516c2c66affSColin Finck     PISID Sid;
517c2c66affSColin Finck     NTSTATUS Status;
518c2c66affSColin Finck 
519c2c66affSColin Finck     /* Validate parameters */
520c2c66affSColin Finck     if ((Flags != 0) ||
521c2c66affSColin Finck         (SourceName == NULL) ||
522c2c66affSColin Finck         (SourceName->Buffer == NULL) ||
523c2c66affSColin Finck         (SourceName->Length == 0) ||
524c2c66affSColin Finck         (AuditParameters == NULL) ||
525c2c66affSColin Finck         (AuditParameters->ParameterCount > SE_MAX_AUDIT_PARAMETERS - 4))
526c2c66affSColin Finck     {
527c2c66affSColin Finck         return STATUS_INVALID_PARAMETER;
528c2c66affSColin Finck     }
529c2c66affSColin Finck 
530c2c66affSColin Finck     /* Validate the source name */
531c2c66affSColin Finck     Status = RtlValidateUnicodeString(0, SourceName);
532c2c66affSColin Finck     if (!NT_SUCCESS(Status))
533c2c66affSColin Finck     {
534c2c66affSColin Finck         return Status;
535c2c66affSColin Finck     }
536c2c66affSColin Finck 
537c2c66affSColin Finck     /* Check if we have a user SID */
538c2c66affSColin Finck     if (UserSid != NULL)
539c2c66affSColin Finck     {
540c2c66affSColin Finck         /* Validate it */
541c2c66affSColin Finck         if (!RtlValidSid(UserSid))
542c2c66affSColin Finck         {
543c2c66affSColin Finck             return STATUS_INVALID_PARAMETER;
544c2c66affSColin Finck         }
545c2c66affSColin Finck 
546c2c66affSColin Finck         /* Use the user SID */
547c2c66affSColin Finck         Sid = UserSid;
548c2c66affSColin Finck     }
549c2c66affSColin Finck     else
550c2c66affSColin Finck     {
551c2c66affSColin Finck         /* No user SID, capture the security subject context */
552c2c66affSColin Finck         SeCaptureSubjectContext(&SubjectContext);
553c2c66affSColin Finck 
554c2c66affSColin Finck         /* Extract the effective token */
555c2c66affSColin Finck         EffectiveToken = SubjectContext.ClientToken ?
556c2c66affSColin Finck             SubjectContext.ClientToken : SubjectContext.PrimaryToken;
557c2c66affSColin Finck 
558c2c66affSColin Finck         /* Use the user-and-groups SID */
559c2c66affSColin Finck         Sid = EffectiveToken->UserAndGroups->Sid;
560c2c66affSColin Finck     }
561c2c66affSColin Finck 
562c2c66affSColin Finck     UNIMPLEMENTED;
563c2c66affSColin Finck 
564c2c66affSColin Finck     /* Check if we captured the subject context */
565c2c66affSColin Finck     if (Sid != UserSid)
566c2c66affSColin Finck     {
567c2c66affSColin Finck         /* Release it */
568c2c66affSColin Finck         SeReleaseSubjectContext(&SubjectContext);
569c2c66affSColin Finck     }
570c2c66affSColin Finck 
571c2c66affSColin Finck     /* Return success */
572c2c66affSColin Finck     return STATUS_SUCCESS;
573c2c66affSColin Finck }
574c2c66affSColin Finck 
5756413009cSGeorge Bișoc /**
5766413009cSGeorge Bișoc  * @unimplemented
5776413009cSGeorge Bișoc  * @brief
5786413009cSGeorge Bișoc  * Sets an array of audit parameters for later security auditing use.
5796413009cSGeorge Bișoc  *
5806413009cSGeorge Bișoc  * @param[in,out] AuditParameters
5816413009cSGeorge Bișoc  * An array of audit parameters to be set.
5826413009cSGeorge Bișoc  *
5836413009cSGeorge Bișoc  * @param[in] Type
5846413009cSGeorge Bișoc  * The type of audit parameters to be set.
5856413009cSGeorge Bișoc  *
5866413009cSGeorge Bișoc  * @param[in] Index
5876413009cSGeorge Bișoc  * Index number that represents an instance of an audit parameters.
5886413009cSGeorge Bișoc  * Such index must be within the maximum range of audit parameters.
5896413009cSGeorge Bișoc  *
5906413009cSGeorge Bișoc  * @param[in] Data
5916413009cSGeorge Bișoc  * An arbitrary buffer data that is bounds to what kind of audit parameter
5926413009cSGeorge Bișoc  * type must be set.
5936413009cSGeorge Bișoc  *
5946413009cSGeorge Bișoc  * @return
5956413009cSGeorge Bișoc  * To be added...
5966413009cSGeorge Bișoc  */
597c2c66affSColin Finck _Const_
598c2c66affSColin Finck NTSTATUS
599c2c66affSColin Finck NTAPI
600c2c66affSColin Finck SeSetAuditParameter(
601c2c66affSColin Finck     _Inout_ PSE_ADT_PARAMETER_ARRAY AuditParameters,
602c2c66affSColin Finck     _In_ SE_ADT_PARAMETER_TYPE Type,
603c2c66affSColin Finck     _In_range_(<, SE_MAX_AUDIT_PARAMETERS) ULONG Index,
604c2c66affSColin Finck     _In_reads_(_Inexpressible_("depends on SE_ADT_PARAMETER_TYPE")) PVOID Data)
605c2c66affSColin Finck {
606c2c66affSColin Finck     UNIMPLEMENTED;
607c2c66affSColin Finck     return STATUS_SUCCESS;
608c2c66affSColin Finck }
609c2c66affSColin Finck 
610c2c66affSColin Finck /* EOF */
611