2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS system libraries
4 * FILE: lib/advapi32/sec/misc.c
5 * PURPOSE: Miscellaneous security functions (some ported from Wine)
9 #include "wine/debug.h"
11 WINE_DEFAULT_DEBUG_CHANNEL(advapi
);
13 /* Needed for LookupAccountNameW implementation from Wine */
15 typedef struct _AccountSid
{
16 WELL_KNOWN_SID_TYPE type
;
19 SID_NAME_USE name_use
;
22 static const WCHAR Account_Operators
[] = { 'A','c','c','o','u','n','t',' ','O','p','e','r','a','t','o','r','s',0 };
23 static const WCHAR Administrator
[] = {'A','d','m','i','n','i','s','t','r','a','t','o','r',0 };
24 static const WCHAR Administrators
[] = { 'A','d','m','i','n','i','s','t','r','a','t','o','r','s',0 };
25 static const WCHAR ANONYMOUS_LOGON
[] = { 'A','N','O','N','Y','M','O','U','S',' ','L','O','G','O','N',0 };
26 static const WCHAR Authenticated_Users
[] = { 'A','u','t','h','e','n','t','i','c','a','t','e','d',' ','U','s','e','r','s',0 };
27 static const WCHAR Backup_Operators
[] = { 'B','a','c','k','u','p',' ','O','p','e','r','a','t','o','r','s',0 };
28 static const WCHAR BATCH
[] = { 'B','A','T','C','H',0 };
29 static const WCHAR Blank
[] = { 0 };
30 static const WCHAR BUILTIN
[] = { 'B','U','I','L','T','I','N',0 };
31 static const WCHAR Cert_Publishers
[] = { 'C','e','r','t',' ','P','u','b','l','i','s','h','e','r','s',0 };
32 static const WCHAR CREATOR_GROUP
[] = { 'C','R','E','A','T','O','R',' ','G','R','O','U','P',0 };
33 static const WCHAR CREATOR_GROUP_SERVER
[] = { 'C','R','E','A','T','O','R',' ','G','R','O','U','P',' ','S','E','R','V','E','R',0 };
34 static const WCHAR CREATOR_OWNER
[] = { 'C','R','E','A','T','O','R',' ','O','W','N','E','R',0 };
35 static const WCHAR CREATOR_OWNER_SERVER
[] = { 'C','R','E','A','T','O','R',' ','O','W','N','E','R',' ','S','E','R','V','E','R',0 };
36 static const WCHAR DIALUP
[] = { 'D','I','A','L','U','P',0 };
37 static const WCHAR Digest_Authentication
[] = { 'D','i','g','e','s','t',' ','A','u','t','h','e','n','t','i','c','a','t','i','o','n',0 };
38 static const WCHAR DOMAIN
[] = {'D','O','M','A','I','N',0};
39 static const WCHAR Domain_Admins
[] = { 'D','o','m','a','i','n',' ','A','d','m','i','n','s',0 };
40 static const WCHAR Domain_Computers
[] = { 'D','o','m','a','i','n',' ','C','o','m','p','u','t','e','r','s',0 };
41 static const WCHAR Domain_Controllers
[] = { 'D','o','m','a','i','n',' ','C','o','n','t','r','o','l','l','e','r','s',0 };
42 static const WCHAR Domain_Guests
[] = { 'D','o','m','a','i','n',' ','G','u','e','s','t','s',0 };
43 static const WCHAR Domain_Users
[] = { 'D','o','m','a','i','n',' ','U','s','e','r','s',0 };
44 static const WCHAR Enterprise_Admins
[] = { 'E','n','t','e','r','p','r','i','s','e',' ','A','d','m','i','n','s',0 };
45 static const WCHAR ENTERPRISE_DOMAIN_CONTROLLERS
[] = { 'E','N','T','E','R','P','R','I','S','E',' ','D','O','M','A','I','N',' ','C','O','N','T','R','O','L','L','E','R','S',0 };
46 static const WCHAR Everyone
[] = { 'E','v','e','r','y','o','n','e',0 };
47 static const WCHAR Group_Policy_Creator_Owners
[] = { 'G','r','o','u','p',' ','P','o','l','i','c','y',' ','C','r','e','a','t','o','r',' ','O','w','n','e','r','s',0 };
48 static const WCHAR Guest
[] = { 'G','u','e','s','t',0 };
49 static const WCHAR Guests
[] = { 'G','u','e','s','t','s',0 };
50 static const WCHAR INTERACTIVE
[] = { 'I','N','T','E','R','A','C','T','I','V','E',0 };
51 static const WCHAR LOCAL
[] = { 'L','O','C','A','L',0 };
52 static const WCHAR LOCAL_SERVICE
[] = { 'L','O','C','A','L',' ','S','E','R','V','I','C','E',0 };
53 static const WCHAR NETWORK
[] = { 'N','E','T','W','O','R','K',0 };
54 static const WCHAR Network_Configuration_Operators
[] = { 'N','e','t','w','o','r','k',' ','C','o','n','f','i','g','u','r','a','t','i','o','n',' ','O','p','e','r','a','t','o','r','s',0 };
55 static const WCHAR NETWORK_SERVICE
[] = { 'N','E','T','W','O','R','K',' ','S','E','R','V','I','C','E',0 };
56 static const WCHAR NT_AUTHORITY
[] = { 'N','T',' ','A','U','T','H','O','R','I','T','Y',0 };
57 static const WCHAR NT_Pseudo_Domain
[] = { 'N','T',' ','P','s','e','u','d','o',' ','D','o','m','a','i','n',0 };
58 static const WCHAR NTML_Authentication
[] = { 'N','T','M','L',' ','A','u','t','h','e','n','t','i','c','a','t','i','o','n',0 };
59 static const WCHAR NULL_SID
[] = { 'N','U','L','L',' ','S','I','D',0 };
60 static const WCHAR Other_Organization
[] = { 'O','t','h','e','r',' ','O','r','g','a','n','i','z','a','t','i','o','n',0 };
61 static const WCHAR Performance_Log_Users
[] = { 'P','e','r','f','o','r','m','a','n','c','e',' ','L','o','g',' ','U','s','e','r','s',0 };
62 static const WCHAR Performance_Monitor_Users
[] = { 'P','e','r','f','o','r','m','a','n','c','e',' ','M','o','n','i','t','o','r',' ','U','s','e','r','s',0 };
63 static const WCHAR Power_Users
[] = { 'P','o','w','e','r',' ','U','s','e','r','s',0 };
64 static const WCHAR Pre_Windows_2000_Compatible_Access
[] = { 'P','r','e','-','W','i','n','d','o','w','s',' ','2','0','0','0',' ','C','o','m','p','a','t','i','b','l','e',' ','A','c','c','e','s','s',0 };
65 static const WCHAR Print_Operators
[] = { 'P','r','i','n','t',' ','O','p','e','r','a','t','o','r','s',0 };
66 static const WCHAR PROXY
[] = { 'P','R','O','X','Y',0 };
67 static const WCHAR RAS_and_IAS_Servers
[] = { 'R','A','S',' ','a','n','d',' ','I','A','S',' ','S','e','r','v','e','r','s',0 };
68 static const WCHAR Remote_Desktop_Users
[] = { 'R','e','m','o','t','e',' ','D','e','s','k','t','o','p',' ','U','s','e','r','s',0 };
69 static const WCHAR REMOTE_INTERACTIVE_LOGON
[] = { 'R','E','M','O','T','E',' ','I','N','T','E','R','A','C','T','I','V','E',' ','L','O','G','O','N',0 };
70 static const WCHAR Replicators
[] = { 'R','e','p','l','i','c','a','t','o','r','s',0 };
71 static const WCHAR RESTRICTED
[] = { 'R','E','S','T','R','I','C','T','E','D',0 };
72 static const WCHAR SChannel_Authentication
[] = { 'S','C','h','a','n','n','e','l',' ','A','u','t','h','e','n','t','i','c','a','t','i','o','n',0 };
73 static const WCHAR Schema_Admins
[] = { 'S','c','h','e','m','a',' ','A','d','m','i','n','s',0 };
74 static const WCHAR SELF
[] = { 'S','E','L','F',0 };
75 static const WCHAR Server_Operators
[] = { 'S','e','r','v','e','r',' ','O','p','e','r','a','t','o','r','s',0 };
76 static const WCHAR SERVICE
[] = { 'S','E','R','V','I','C','E',0 };
77 static const WCHAR SYSTEM
[] = { 'S','Y','S','T','E','M',0 };
78 static const WCHAR TERMINAL_SERVER_USER
[] = { 'T','E','R','M','I','N','A','L',' ','S','E','R','V','E','R',' ','U','S','E','R',0 };
79 static const WCHAR This_Organization
[] = { 'T','h','i','s',' ','O','r','g','a','n','i','z','a','t','i','o','n',0 };
80 static const WCHAR Users
[] = { 'U','s','e','r','s',0 };
82 static const AccountSid ACCOUNT_SIDS
[] = {
83 { WinNullSid
, NULL_SID
, Blank
, SidTypeWellKnownGroup
},
84 { WinWorldSid
, Everyone
, Blank
, SidTypeWellKnownGroup
},
85 { WinLocalSid
, LOCAL
, Blank
, SidTypeWellKnownGroup
},
86 { WinCreatorOwnerSid
, CREATOR_OWNER
, Blank
, SidTypeWellKnownGroup
},
87 { WinCreatorGroupSid
, CREATOR_GROUP
, Blank
, SidTypeWellKnownGroup
},
88 { WinCreatorOwnerServerSid
, CREATOR_OWNER_SERVER
, Blank
, SidTypeWellKnownGroup
},
89 { WinCreatorGroupServerSid
, CREATOR_GROUP_SERVER
, Blank
, SidTypeWellKnownGroup
},
90 { WinNtAuthoritySid
, NT_Pseudo_Domain
, NT_Pseudo_Domain
, SidTypeDomain
},
91 { WinDialupSid
, DIALUP
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
92 { WinNetworkSid
, NETWORK
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
93 { WinBatchSid
, BATCH
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
94 { WinInteractiveSid
, INTERACTIVE
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
95 { WinServiceSid
, SERVICE
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
96 { WinAnonymousSid
, ANONYMOUS_LOGON
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
97 { WinProxySid
, PROXY
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
98 { WinEnterpriseControllersSid
, ENTERPRISE_DOMAIN_CONTROLLERS
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
99 { WinSelfSid
, SELF
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
100 { WinAuthenticatedUserSid
, Authenticated_Users
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
101 { WinRestrictedCodeSid
, RESTRICTED
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
102 { WinTerminalServerSid
, TERMINAL_SERVER_USER
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
103 { WinRemoteLogonIdSid
, REMOTE_INTERACTIVE_LOGON
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
104 { WinLocalSystemSid
, SYSTEM
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
105 { WinLocalServiceSid
, LOCAL_SERVICE
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
106 { WinNetworkServiceSid
, NETWORK_SERVICE
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
107 { WinBuiltinDomainSid
, BUILTIN
, BUILTIN
, SidTypeDomain
},
108 { WinBuiltinAdministratorsSid
, Administrators
, BUILTIN
, SidTypeAlias
},
109 { WinBuiltinUsersSid
, Users
, BUILTIN
, SidTypeAlias
},
110 { WinBuiltinGuestsSid
, Guests
, BUILTIN
, SidTypeAlias
},
111 { WinBuiltinPowerUsersSid
, Power_Users
, BUILTIN
, SidTypeAlias
},
112 { WinBuiltinAccountOperatorsSid
, Account_Operators
, BUILTIN
, SidTypeAlias
},
113 { WinBuiltinSystemOperatorsSid
, Server_Operators
, BUILTIN
, SidTypeAlias
},
114 { WinBuiltinPrintOperatorsSid
, Print_Operators
, BUILTIN
, SidTypeAlias
},
115 { WinBuiltinBackupOperatorsSid
, Backup_Operators
, BUILTIN
, SidTypeAlias
},
116 { WinBuiltinReplicatorSid
, Replicators
, BUILTIN
, SidTypeAlias
},
117 { WinBuiltinPreWindows2000CompatibleAccessSid
, Pre_Windows_2000_Compatible_Access
, BUILTIN
, SidTypeAlias
},
118 { WinBuiltinRemoteDesktopUsersSid
, Remote_Desktop_Users
, BUILTIN
, SidTypeAlias
},
119 { WinBuiltinNetworkConfigurationOperatorsSid
, Network_Configuration_Operators
, BUILTIN
, SidTypeAlias
},
120 { WinNTLMAuthenticationSid
, NTML_Authentication
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
121 { WinDigestAuthenticationSid
, Digest_Authentication
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
122 { WinSChannelAuthenticationSid
, SChannel_Authentication
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
123 { WinThisOrganizationSid
, This_Organization
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
124 { WinOtherOrganizationSid
, Other_Organization
, NT_AUTHORITY
, SidTypeWellKnownGroup
},
125 { WinBuiltinPerfMonitoringUsersSid
, Performance_Monitor_Users
, BUILTIN
, SidTypeAlias
},
126 { WinBuiltinPerfLoggingUsersSid
, Performance_Log_Users
, BUILTIN
, SidTypeAlias
},
129 /* Interface to ntmarta.dll ***************************************************/
131 NTMARTA NtMartaStatic
= { 0 };
132 static PNTMARTA NtMarta
= NULL
;
134 #define FindNtMartaProc(Name) \
135 NtMartaStatic.Name = (PVOID)GetProcAddress(NtMartaStatic.hDllInstance, \
137 if (NtMartaStatic.Name == NULL) \
139 return GetLastError(); \
143 LoadAndInitializeNtMarta(VOID
)
145 /* this code may be executed simultaneously by multiple threads in case they're
146 trying to initialize the interface at the same time, but that's no problem
147 because the pointers returned by GetProcAddress will be the same. However,
148 only one of the threads will change the NtMarta pointer to the NtMartaStatic
149 structure, the others threads will detect that there were other threads
150 initializing the structure faster and will release the reference to the
153 NtMartaStatic
.hDllInstance
= LoadLibraryW(L
"ntmarta.dll");
154 if (NtMartaStatic
.hDllInstance
== NULL
)
156 return GetLastError();
160 FindNtMartaProc(LookupAccountTrustee
);
161 FindNtMartaProc(LookupAccountName
);
162 FindNtMartaProc(LookupAccountSid
);
163 FindNtMartaProc(SetEntriesInAList
);
164 FindNtMartaProc(ConvertAccessToSecurityDescriptor
);
165 FindNtMartaProc(ConvertSDToAccess
);
166 FindNtMartaProc(ConvertAclToAccess
);
167 FindNtMartaProc(GetAccessForTrustee
);
168 FindNtMartaProc(GetExplicitEntries
);
170 FindNtMartaProc(RewriteGetNamedRights
);
171 FindNtMartaProc(RewriteSetNamedRights
);
172 FindNtMartaProc(RewriteGetHandleRights
);
173 FindNtMartaProc(RewriteSetHandleRights
);
174 FindNtMartaProc(RewriteSetEntriesInAcl
);
175 FindNtMartaProc(RewriteGetExplicitEntriesFromAcl
);
176 FindNtMartaProc(TreeResetNamedSecurityInfo
);
177 FindNtMartaProc(GetInheritanceSource
);
178 FindNtMartaProc(FreeIndexArray
);
180 return ERROR_SUCCESS
;
184 CheckNtMartaPresent(VOID
)
188 if (InterlockedCompareExchangePointer((PVOID
)&NtMarta
,
192 /* we're the first one trying to use ntmarta, initialize it and change
193 the pointer after initialization */
194 ErrorCode
= LoadAndInitializeNtMarta();
196 if (ErrorCode
== ERROR_SUCCESS
)
198 /* try change the NtMarta pointer */
199 if (InterlockedCompareExchangePointer((PVOID
)&NtMarta
,
203 /* another thread initialized ntmarta in the meanwhile, release
204 the reference of the dll loaded. */
205 FreeLibrary(NtMartaStatic
.hDllInstance
);
211 ERR("Failed to initialize ntmarta.dll! Error: 0x%x", ErrorCode
);
217 /* ntmarta was already initialized */
218 ErrorCode
= ERROR_SUCCESS
;
224 VOID
UnloadNtMarta(VOID
)
226 if (InterlockedExchangePointer((PVOID
)&NtMarta
,
229 FreeLibrary(NtMartaStatic
.hDllInstance
);
233 /******************************************************************************/
239 AreAllAccessesGranted(DWORD GrantedAccess
,
242 return((BOOL
)RtlAreAllAccessesGranted(GrantedAccess
,
251 AreAnyAccessesGranted(DWORD GrantedAccess
,
254 return((BOOL
)RtlAreAnyAccessesGranted(GrantedAccess
,
259 /******************************************************************************
260 * GetFileSecurityA [ADVAPI32.@]
262 * Obtains Specified information about the security of a file or directory.
265 * lpFileName [I] Name of the file to get info for
266 * RequestedInformation [I] SE_ flags from "winnt.h"
267 * pSecurityDescriptor [O] Destination for security information
268 * nLength [I] Length of pSecurityDescriptor
269 * lpnLengthNeeded [O] Destination for length of returned security information
272 * Success: TRUE. pSecurityDescriptor contains the requested information.
273 * Failure: FALSE. lpnLengthNeeded contains the required space to return the info.
276 * The information returned is constrained by the callers access rights and
282 GetFileSecurityA(LPCSTR lpFileName
,
283 SECURITY_INFORMATION RequestedInformation
,
284 PSECURITY_DESCRIPTOR pSecurityDescriptor
,
286 LPDWORD lpnLengthNeeded
)
288 UNICODE_STRING FileName
;
292 Status
= RtlCreateUnicodeStringFromAsciiz(&FileName
,
294 if (!NT_SUCCESS(Status
))
296 SetLastError(RtlNtStatusToDosError(Status
));
300 bResult
= GetFileSecurityW(FileName
.Buffer
,
301 RequestedInformation
,
306 RtlFreeUnicodeString(&FileName
);
316 GetFileSecurityW(LPCWSTR lpFileName
,
317 SECURITY_INFORMATION RequestedInformation
,
318 PSECURITY_DESCRIPTOR pSecurityDescriptor
,
320 LPDWORD lpnLengthNeeded
)
322 OBJECT_ATTRIBUTES ObjectAttributes
;
323 IO_STATUS_BLOCK StatusBlock
;
324 UNICODE_STRING FileName
;
325 ULONG AccessMask
= 0;
329 TRACE("GetFileSecurityW() called\n");
331 if (RequestedInformation
&
332 (OWNER_SECURITY_INFORMATION
| GROUP_SECURITY_INFORMATION
| DACL_SECURITY_INFORMATION
))
334 AccessMask
|= READ_CONTROL
;
337 if (RequestedInformation
& SACL_SECURITY_INFORMATION
)
339 AccessMask
|= ACCESS_SYSTEM_SECURITY
;
342 if (!RtlDosPathNameToNtPathName_U(lpFileName
,
347 ERR("Invalid path\n");
348 SetLastError(ERROR_INVALID_NAME
);
352 InitializeObjectAttributes(&ObjectAttributes
,
354 OBJ_CASE_INSENSITIVE
,
358 Status
= NtOpenFile(&FileHandle
,
362 FILE_SHARE_READ
| FILE_SHARE_WRITE
| FILE_SHARE_DELETE
,
365 RtlFreeHeap(RtlGetProcessHeap(),
369 if (!NT_SUCCESS(Status
))
371 ERR("NtOpenFile() failed (Status %lx)\n", Status
);
372 SetLastError(RtlNtStatusToDosError(Status
));
376 Status
= NtQuerySecurityObject(FileHandle
,
377 RequestedInformation
,
383 if (!NT_SUCCESS(Status
))
385 ERR("NtQuerySecurityObject() failed (Status %lx)\n", Status
);
386 SetLastError(RtlNtStatusToDosError(Status
));
398 GetKernelObjectSecurity(HANDLE Handle
,
399 SECURITY_INFORMATION RequestedInformation
,
400 PSECURITY_DESCRIPTOR pSecurityDescriptor
,
402 LPDWORD lpnLengthNeeded
)
406 Status
= NtQuerySecurityObject(Handle
,
407 RequestedInformation
,
411 if (!NT_SUCCESS(Status
))
413 SetLastError(RtlNtStatusToDosError(Status
));
420 /******************************************************************************
421 * SetFileSecurityA [ADVAPI32.@]
422 * Sets the security of a file or directory
427 SetFileSecurityA (LPCSTR lpFileName
,
428 SECURITY_INFORMATION SecurityInformation
,
429 PSECURITY_DESCRIPTOR pSecurityDescriptor
)
431 UNICODE_STRING FileName
;
435 Status
= RtlCreateUnicodeStringFromAsciiz(&FileName
,
437 if (!NT_SUCCESS(Status
))
439 SetLastError(RtlNtStatusToDosError(Status
));
443 bResult
= SetFileSecurityW(FileName
.Buffer
,
445 pSecurityDescriptor
);
447 RtlFreeUnicodeString(&FileName
);
453 /******************************************************************************
454 * SetFileSecurityW [ADVAPI32.@]
455 * Sets the security of a file or directory
460 SetFileSecurityW (LPCWSTR lpFileName
,
461 SECURITY_INFORMATION SecurityInformation
,
462 PSECURITY_DESCRIPTOR pSecurityDescriptor
)
464 OBJECT_ATTRIBUTES ObjectAttributes
;
465 IO_STATUS_BLOCK StatusBlock
;
466 UNICODE_STRING FileName
;
467 ULONG AccessMask
= 0;
471 TRACE("SetFileSecurityW() called\n");
473 if (SecurityInformation
&
474 (OWNER_SECURITY_INFORMATION
| GROUP_SECURITY_INFORMATION
))
476 AccessMask
|= WRITE_OWNER
;
479 if (SecurityInformation
& DACL_SECURITY_INFORMATION
)
481 AccessMask
|= WRITE_DAC
;
484 if (SecurityInformation
& SACL_SECURITY_INFORMATION
)
486 AccessMask
|= ACCESS_SYSTEM_SECURITY
;
489 if (!RtlDosPathNameToNtPathName_U(lpFileName
,
494 ERR("Invalid path\n");
495 SetLastError(ERROR_INVALID_NAME
);
499 InitializeObjectAttributes(&ObjectAttributes
,
501 OBJ_CASE_INSENSITIVE
,
505 Status
= NtOpenFile(&FileHandle
,
509 FILE_SHARE_READ
| FILE_SHARE_WRITE
| FILE_SHARE_DELETE
,
512 RtlFreeHeap(RtlGetProcessHeap(),
516 if (!NT_SUCCESS(Status
))
518 ERR("NtOpenFile() failed (Status %lx)\n", Status
);
519 SetLastError(RtlNtStatusToDosError(Status
));
523 Status
= NtSetSecurityObject(FileHandle
,
525 pSecurityDescriptor
);
528 if (!NT_SUCCESS(Status
))
530 ERR("NtSetSecurityObject() failed (Status %lx)\n", Status
);
531 SetLastError(RtlNtStatusToDosError(Status
));
543 SetKernelObjectSecurity(HANDLE Handle
,
544 SECURITY_INFORMATION SecurityInformation
,
545 PSECURITY_DESCRIPTOR SecurityDescriptor
)
549 Status
= NtSetSecurityObject(Handle
,
552 if (!NT_SUCCESS(Status
))
554 SetLastError(RtlNtStatusToDosError(Status
));
566 ImpersonateAnonymousToken(IN HANDLE ThreadHandle
)
570 Status
= NtImpersonateAnonymousToken(ThreadHandle
);
572 if (!NT_SUCCESS(Status
))
574 SetLastError(RtlNtStatusToDosError(Status
));
586 ImpersonateLoggedOnUser(HANDLE hToken
)
588 SECURITY_QUALITY_OF_SERVICE Qos
;
589 OBJECT_ATTRIBUTES ObjectAttributes
;
596 /* Get the token type */
597 Status
= NtQueryInformationToken (hToken
,
602 if (!NT_SUCCESS(Status
))
604 SetLastError (RtlNtStatusToDosError (Status
));
608 if (Type
== TokenPrimary
)
610 /* Create a duplicate impersonation token */
611 Qos
.Length
= sizeof(SECURITY_QUALITY_OF_SERVICE
);
612 Qos
.ImpersonationLevel
= SecurityImpersonation
;
613 Qos
.ContextTrackingMode
= SECURITY_DYNAMIC_TRACKING
;
614 Qos
.EffectiveOnly
= FALSE
;
616 ObjectAttributes
.Length
= sizeof(OBJECT_ATTRIBUTES
);
617 ObjectAttributes
.RootDirectory
= NULL
;
618 ObjectAttributes
.ObjectName
= NULL
;
619 ObjectAttributes
.Attributes
= 0;
620 ObjectAttributes
.SecurityDescriptor
= NULL
;
621 ObjectAttributes
.SecurityQualityOfService
= &Qos
;
623 Status
= NtDuplicateToken (hToken
,
624 TOKEN_IMPERSONATE
| TOKEN_QUERY
,
629 if (!NT_SUCCESS(Status
))
631 SetLastError (RtlNtStatusToDosError (Status
));
639 /* User the original impersonation token */
644 /* Impersonate the the current thread */
645 Status
= NtSetInformationThread (NtCurrentThread (),
646 ThreadImpersonationToken
,
650 if (Duplicated
== TRUE
)
655 if (!NT_SUCCESS(Status
))
657 SetLastError (RtlNtStatusToDosError (Status
));
669 ImpersonateSelf(SECURITY_IMPERSONATION_LEVEL ImpersonationLevel
)
673 Status
= RtlImpersonateSelf(ImpersonationLevel
);
674 if (!NT_SUCCESS(Status
))
676 SetLastError(RtlNtStatusToDosError(Status
));
692 Status
= NtSetInformationThread(NtCurrentThread(),
693 ThreadImpersonationToken
,
696 if (!NT_SUCCESS(Status
))
698 SetLastError(RtlNtStatusToDosError(Status
));
705 /******************************************************************************
706 * GetUserNameA [ADVAPI32.@]
708 * Get the current user name.
711 * lpszName [O] Destination for the user name.
712 * lpSize [I/O] Size of lpszName.
718 GetUserNameA( LPSTR lpszName
, LPDWORD lpSize
)
720 UNICODE_STRING NameW
;
724 /* apparently Win doesn't check whether lpSize is valid at all! */
726 NameW
.MaximumLength
= (*lpSize
) * sizeof(WCHAR
);
727 NameW
.Buffer
= LocalAlloc(LMEM_FIXED
, NameW
.MaximumLength
);
728 if(NameW
.Buffer
== NULL
)
730 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
735 NameA
.MaximumLength
= ((*lpSize
) < 0xFFFF ? (USHORT
)(*lpSize
) : 0xFFFF);
736 NameA
.Buffer
= lpszName
;
738 Ret
= GetUserNameW(NameW
.Buffer
,
742 NameW
.Length
= (*lpSize
- 1) * sizeof(WCHAR
);
743 RtlUnicodeStringToAnsiString(&NameA
, &NameW
, FALSE
);
745 *lpSize
= NameA
.Length
+ 1;
748 LocalFree(NameW
.Buffer
);
753 /******************************************************************************
754 * GetUserNameW [ADVAPI32.@]
761 GetUserNameW ( LPWSTR lpszName
, LPDWORD lpSize
)
763 HANDLE hToken
= INVALID_HANDLE_VALUE
;
766 TOKEN_USER
* token_user
= NULL
;
768 SID_NAME_USE snu
= SidTypeUser
;
769 WCHAR
* domain_name
= NULL
;
772 if ( !OpenThreadToken ( GetCurrentThread(), TOKEN_QUERY
, FALSE
, &hToken
) )
774 DWORD dwLastError
= GetLastError();
775 if ( dwLastError
!= ERROR_NO_TOKEN
776 && dwLastError
!= ERROR_NO_IMPERSONATION_TOKEN
)
778 /* don't call SetLastError(),
779 as OpenThreadToken() ought to have set one */
782 if ( !OpenProcessToken ( GetCurrentProcess(), TOKEN_QUERY
, &hToken
) )
784 /* don't call SetLastError(),
785 as OpenProcessToken() ought to have set one */
789 tu_buf
= LocalAlloc ( LMEM_FIXED
, 36 );
792 SetLastError ( ERROR_NOT_ENOUGH_MEMORY
);
793 CloseHandle ( hToken
);
796 if ( !GetTokenInformation ( hToken
, TokenUser
, tu_buf
, 36, &tu_len
) || tu_len
> 36 )
798 LocalFree ( tu_buf
);
799 tu_buf
= LocalAlloc ( LMEM_FIXED
, tu_len
);
802 SetLastError ( ERROR_NOT_ENOUGH_MEMORY
);
803 CloseHandle ( hToken
);
806 if ( !GetTokenInformation ( hToken
, TokenUser
, tu_buf
, tu_len
, &tu_len
) )
808 /* don't call SetLastError(),
809 as GetTokenInformation() ought to have set one */
810 LocalFree ( tu_buf
);
811 CloseHandle ( hToken
);
815 CloseHandle ( hToken
);
816 token_user
= (TOKEN_USER
*)tu_buf
;
820 domain_name
= LocalAlloc ( LMEM_FIXED
, dn_len
* sizeof(WCHAR
) );
823 LocalFree ( tu_buf
);
824 SetLastError ( ERROR_NOT_ENOUGH_MEMORY
);
827 if ( !LookupAccountSidW ( NULL
, token_user
->User
.Sid
, lpszName
, &an_len
, domain_name
, &dn_len
, &snu
)
832 LocalFree ( domain_name
);
833 domain_name
= LocalAlloc ( LMEM_FIXED
, dn_len
* sizeof(WCHAR
) );
836 LocalFree ( tu_buf
);
837 SetLastError ( ERROR_NOT_ENOUGH_MEMORY
);
842 if ( !LookupAccountSidW ( NULL
, token_user
->User
.Sid
, lpszName
, &an_len
, domain_name
, &dn_len
, &snu
) )
844 /* don't call SetLastError(),
845 as LookupAccountSid() ought to have set one */
846 LocalFree ( domain_name
);
847 LocalFree ( tu_buf
);
853 LocalFree ( domain_name
);
854 LocalFree ( tu_buf
);
855 *lpSize
= an_len
+ 1;
860 /******************************************************************************
861 * LookupAccountSidA [ADVAPI32.@]
866 LookupAccountSidA (LPCSTR lpSystemName
,
870 LPSTR lpReferencedDomainName
,
871 LPDWORD cchReferencedDomainName
,
874 UNICODE_STRING NameW
, ReferencedDomainNameW
, SystemNameW
;
875 DWORD szName
, szReferencedDomainName
;
879 * save the buffer sizes the caller passed to us, as they may get modified and
880 * we require the original values when converting back to ansi
883 szReferencedDomainName
= *cchReferencedDomainName
;
886 * allocate buffers for the unicode strings to receive
892 NameW
.MaximumLength
= szName
* sizeof(WCHAR
);
893 NameW
.Buffer
= (PWSTR
)LocalAlloc(LMEM_FIXED
, NameW
.MaximumLength
);
894 if(NameW
.Buffer
== NULL
)
896 SetLastError(ERROR_OUTOFMEMORY
);
903 if(szReferencedDomainName
> 0)
905 ReferencedDomainNameW
.Length
= 0;
906 ReferencedDomainNameW
.MaximumLength
= szReferencedDomainName
* sizeof(WCHAR
);
907 ReferencedDomainNameW
.Buffer
= (PWSTR
)LocalAlloc(LMEM_FIXED
, ReferencedDomainNameW
.MaximumLength
);
908 if(ReferencedDomainNameW
.Buffer
== NULL
)
912 LocalFree(NameW
.Buffer
);
914 SetLastError(ERROR_OUTOFMEMORY
);
919 ReferencedDomainNameW
.Buffer
= NULL
;
922 * convert the system name to unicode - if present
925 if(lpSystemName
!= NULL
)
927 ANSI_STRING SystemNameA
;
929 RtlInitAnsiString(&SystemNameA
, lpSystemName
);
930 RtlAnsiStringToUnicodeString(&SystemNameW
, &SystemNameA
, TRUE
);
933 SystemNameW
.Buffer
= NULL
;
936 * it's time to call the unicode version
939 Ret
= LookupAccountSidW(SystemNameW
.Buffer
,
943 ReferencedDomainNameW
.Buffer
,
944 cchReferencedDomainName
,
949 * convert unicode strings back to ansi, don't forget that we can't convert
950 * more than 0xFFFF (USHORT) characters! Also don't forget to explicitly
951 * terminate the converted string, the Rtl functions don't do that!
958 NameA
.MaximumLength
= ((szName
<= 0xFFFF) ? (USHORT
)szName
: 0xFFFF);
959 NameA
.Buffer
= lpName
;
961 RtlUnicodeStringToAnsiString(&NameA
, &NameW
, FALSE
);
962 NameA
.Buffer
[NameA
.Length
] = '\0';
965 if(lpReferencedDomainName
!= NULL
)
967 ANSI_STRING ReferencedDomainNameA
;
969 ReferencedDomainNameA
.Length
= 0;
970 ReferencedDomainNameA
.MaximumLength
= ((szReferencedDomainName
<= 0xFFFF) ?
971 (USHORT
)szReferencedDomainName
: 0xFFFF);
972 ReferencedDomainNameA
.Buffer
= lpReferencedDomainName
;
974 RtlUnicodeStringToAnsiString(&ReferencedDomainNameA
, &ReferencedDomainNameW
, FALSE
);
975 ReferencedDomainNameA
.Buffer
[ReferencedDomainNameA
.Length
] = '\0';
980 * free previously allocated buffers
983 if(SystemNameW
.Buffer
!= NULL
)
985 RtlFreeUnicodeString(&SystemNameW
);
987 if(NameW
.Buffer
!= NULL
)
989 LocalFree(NameW
.Buffer
);
991 if(ReferencedDomainNameW
.Buffer
!= NULL
)
993 LocalFree(ReferencedDomainNameW
.Buffer
);
1000 /******************************************************************************
1001 * LookupAccountSidW [ADVAPI32.@]
1007 LPCWSTR pSystemName
,
1009 LPWSTR pAccountName
,
1010 LPDWORD pdwAccountName
,
1012 LPDWORD pdwDomainName
,
1013 PSID_NAME_USE peUse
)
1015 LSA_UNICODE_STRING SystemName
;
1016 LSA_OBJECT_ATTRIBUTES ObjectAttributes
= {0};
1017 LSA_HANDLE PolicyHandle
= NULL
;
1019 PLSA_REFERENCED_DOMAIN_LIST ReferencedDomain
= NULL
;
1020 PLSA_TRANSLATED_NAME TranslatedName
= NULL
;
1023 RtlInitUnicodeString ( &SystemName
, pSystemName
);
1024 Status
= LsaOpenPolicy ( &SystemName
, &ObjectAttributes
, POLICY_LOOKUP_NAMES
, &PolicyHandle
);
1025 if ( !NT_SUCCESS(Status
) )
1027 SetLastError ( LsaNtStatusToWinError(Status
) );
1030 Status
= LsaLookupSids ( PolicyHandle
, 1, &pSid
, &ReferencedDomain
, &TranslatedName
);
1032 LsaClose ( PolicyHandle
);
1034 if ( !NT_SUCCESS(Status
) || Status
== STATUS_SOME_NOT_MAPPED
)
1036 SetLastError ( LsaNtStatusToWinError(Status
) );
1042 if ( TranslatedName
)
1044 DWORD dwSrcLen
= TranslatedName
->Name
.Length
/ sizeof(WCHAR
);
1045 if ( *pdwAccountName
<= dwSrcLen
)
1047 *pdwAccountName
= dwSrcLen
+ 1;
1052 *pdwAccountName
= dwSrcLen
;
1055 RtlCopyMemory ( pAccountName
, TranslatedName
->Name
.Buffer
, TranslatedName
->Name
.Length
);
1056 pAccountName
[TranslatedName
->Name
.Length
/ sizeof(WCHAR
)] = L
'\0';
1060 *peUse
= TranslatedName
->Use
;
1063 if ( ReferencedDomain
)
1065 if ( ReferencedDomain
->Entries
> 0 )
1067 DWORD dwSrcLen
= ReferencedDomain
->Domains
[0].Name
.Length
/ sizeof(WCHAR
);
1068 if ( *pdwDomainName
<= dwSrcLen
)
1070 *pdwDomainName
= dwSrcLen
+ 1;
1075 *pdwDomainName
= dwSrcLen
;
1076 RtlCopyMemory ( pDomainName
, ReferencedDomain
->Domains
[0].Name
.Buffer
, ReferencedDomain
->Domains
[0].Name
.Length
);
1077 pDomainName
[ReferencedDomain
->Domains
[0].Name
.Length
/ sizeof(WCHAR
)] = L
'\0';
1083 SetLastError(ERROR_INSUFFICIENT_BUFFER
);
1086 if ( ReferencedDomain
)
1087 LsaFreeMemory ( ReferencedDomain
);
1088 if ( TranslatedName
)
1089 LsaFreeMemory ( TranslatedName
);
1096 /******************************************************************************
1097 * LookupAccountNameA [ADVAPI32.@]
1102 LookupAccountNameA (LPCSTR SystemName
,
1106 LPSTR ReferencedDomainName
,
1107 LPDWORD hReferencedDomainNameLength
,
1108 PSID_NAME_USE SidNameUse
)
1111 UNICODE_STRING lpSystemW
;
1112 UNICODE_STRING lpAccountW
;
1113 LPWSTR lpReferencedDomainNameW
= NULL
;
1115 RtlCreateUnicodeStringFromAsciiz(&lpSystemW
, SystemName
);
1116 RtlCreateUnicodeStringFromAsciiz(&lpAccountW
, AccountName
);
1118 if (ReferencedDomainName
)
1119 lpReferencedDomainNameW
= HeapAlloc(GetProcessHeap(), 0, *hReferencedDomainNameLength
* sizeof(WCHAR
));
1121 ret
= LookupAccountNameW(lpSystemW
.Buffer
, lpAccountW
.Buffer
, Sid
, SidLength
, lpReferencedDomainNameW
,
1122 hReferencedDomainNameLength
, SidNameUse
);
1124 if (ret
&& lpReferencedDomainNameW
)
1126 WideCharToMultiByte(CP_ACP
, 0, lpReferencedDomainNameW
, *hReferencedDomainNameLength
,
1127 ReferencedDomainName
, *hReferencedDomainNameLength
, NULL
, NULL
);
1130 RtlFreeUnicodeString(&lpSystemW
);
1131 RtlFreeUnicodeString(&lpAccountW
);
1132 HeapFree(GetProcessHeap(), 0, lpReferencedDomainNameW
);
1138 /******************************************************************************
1139 * LookupAccountNameW [ADVAPI32.@]
1143 BOOL WINAPI
LookupAccountNameW(LPCWSTR lpSystemName
, LPCWSTR lpAccountName
, PSID Sid
,
1144 LPDWORD cbSid
, LPWSTR ReferencedDomainName
,
1145 LPDWORD cchReferencedDomainName
, PSID_NAME_USE peUse
)
1147 /* Default implementation: Always return a default SID */
1148 SID_IDENTIFIER_AUTHORITY identifierAuthority
= {SECURITY_NT_AUTHORITY
};
1151 static const WCHAR dm
[] = {'D','O','M','A','I','N',0};
1154 TRACE("%s %s %p %p %p %p %p - stub\n", lpSystemName
, lpAccountName
,
1155 Sid
, cbSid
, ReferencedDomainName
, cchReferencedDomainName
, peUse
);
1157 for (i
= 0; i
< (sizeof(ACCOUNT_SIDS
) / sizeof(ACCOUNT_SIDS
[0])); i
++)
1159 if (!wcscmp(lpAccountName
, ACCOUNT_SIDS
[i
].account
))
1161 if (*cchReferencedDomainName
)
1162 *ReferencedDomainName
= '\0';
1163 *cchReferencedDomainName
= 0;
1164 *peUse
= SidTypeWellKnownGroup
;
1165 return CreateWellKnownSid(ACCOUNT_SIDS
[i
].type
, NULL
, Sid
, cbSid
);
1169 ret
= AllocateAndInitializeSid(&identifierAuthority
,
1171 SECURITY_BUILTIN_DOMAIN_RID
,
1172 DOMAIN_ALIAS_RID_ADMINS
,
1179 if (!RtlValidSid(pSid
))
1185 if (Sid
!= NULL
&& (*cbSid
>= GetLengthSid(pSid
)))
1186 CopySid(*cbSid
, Sid
, pSid
);
1187 if (*cbSid
< GetLengthSid(pSid
))
1189 SetLastError(ERROR_INSUFFICIENT_BUFFER
);
1192 *cbSid
= GetLengthSid(pSid
);
1194 if (ReferencedDomainName
!= NULL
&& (*cchReferencedDomainName
> wcslen(dm
)))
1195 wcscpy(ReferencedDomainName
, dm
);
1197 if (*cchReferencedDomainName
<= wcslen(dm
))
1199 SetLastError(ERROR_INSUFFICIENT_BUFFER
);
1203 *cchReferencedDomainName
= wcslen(dm
)+1;
1211 /**********************************************************************
1212 * LookupPrivilegeValueA EXPORTED
1217 LookupPrivilegeValueA (LPCSTR lpSystemName
,
1221 UNICODE_STRING SystemName
;
1222 UNICODE_STRING Name
;
1225 /* Remote system? */
1226 if (lpSystemName
!= NULL
)
1228 RtlCreateUnicodeStringFromAsciiz (&SystemName
,
1229 (LPSTR
)lpSystemName
);
1232 /* Check the privilege name is not NULL */
1235 SetLastError (ERROR_INVALID_PARAMETER
);
1239 RtlCreateUnicodeStringFromAsciiz (&Name
,
1242 Result
= LookupPrivilegeValueW ((lpSystemName
!= NULL
) ? SystemName
.Buffer
: NULL
,
1246 RtlFreeUnicodeString (&Name
);
1248 /* Remote system? */
1249 if (lpSystemName
!= NULL
)
1251 RtlFreeUnicodeString (&SystemName
);
1258 /**********************************************************************
1259 * LookupPrivilegeValueW EXPORTED
1264 LookupPrivilegeValueW (LPCWSTR SystemName
,
1268 static const WCHAR
* const DefaultPrivNames
[] =
1270 L
"SeCreateTokenPrivilege",
1271 L
"SeAssignPrimaryTokenPrivilege",
1272 L
"SeLockMemoryPrivilege",
1273 L
"SeIncreaseQuotaPrivilege",
1274 L
"SeUnsolicitedInputPrivilege",
1275 L
"SeMachineAccountPrivilege",
1277 L
"SeSecurityPrivilege",
1278 L
"SeTakeOwnershipPrivilege",
1279 L
"SeLoadDriverPrivilege",
1280 L
"SeSystemProfilePrivilege",
1281 L
"SeSystemtimePrivilege",
1282 L
"SeProfileSingleProcessPrivilege",
1283 L
"SeIncreaseBasePriorityPrivilege",
1284 L
"SeCreatePagefilePrivilege",
1285 L
"SeCreatePermanentPrivilege",
1286 L
"SeBackupPrivilege",
1287 L
"SeRestorePrivilege",
1288 L
"SeShutdownPrivilege",
1289 L
"SeDebugPrivilege",
1290 L
"SeAuditPrivilege",
1291 L
"SeSystemEnvironmentPrivilege",
1292 L
"SeChangeNotifyPrivilege",
1293 L
"SeRemoteShutdownPrivilege",
1294 L
"SeUndockPrivilege",
1295 L
"SeSyncAgentPrivilege",
1296 L
"SeEnableDelegationPrivilege",
1297 L
"SeManageVolumePrivilege",
1298 L
"SeImpersonatePrivilege",
1299 L
"SeCreateGlobalPrivilege"
1303 if (NULL
!= SystemName
&& L
'\0' != *SystemName
)
1305 FIXME("LookupPrivilegeValueW: not implemented for remote system\n");
1306 SetLastError(ERROR_CALL_NOT_IMPLEMENTED
);
1310 for (Priv
= 0; Priv
< sizeof(DefaultPrivNames
) / sizeof(DefaultPrivNames
[0]); Priv
++)
1312 if (0 == wcscmp(PrivName
, DefaultPrivNames
[Priv
]))
1314 Luid
->LowPart
= Priv
+ 1;
1320 WARN("LookupPrivilegeValueW: no such privilege %S\n", PrivName
);
1321 SetLastError(ERROR_NO_SUCH_PRIVILEGE
);
1326 /**********************************************************************
1327 * LookupPrivilegeDisplayNameA EXPORTED
1332 LookupPrivilegeDisplayNameA (LPCSTR lpSystemName
,
1334 LPSTR lpDisplayName
,
1335 LPDWORD cbDisplayName
,
1336 LPDWORD lpLanguageId
)
1338 FIXME("%s() not implemented!\n", __FUNCTION__
);
1339 SetLastError (ERROR_CALL_NOT_IMPLEMENTED
);
1344 /**********************************************************************
1345 * LookupPrivilegeDisplayNameW EXPORTED
1350 LookupPrivilegeDisplayNameW (LPCWSTR lpSystemName
,
1352 LPWSTR lpDisplayName
,
1353 LPDWORD cbDisplayName
,
1354 LPDWORD lpLanguageId
)
1356 FIXME("%s() not implemented!\n", __FUNCTION__
);
1357 SetLastError (ERROR_CALL_NOT_IMPLEMENTED
);
1362 /**********************************************************************
1363 * LookupPrivilegeNameA EXPORTED
1368 LookupPrivilegeNameA (LPCSTR lpSystemName
,
1373 FIXME("%s() not implemented!\n", __FUNCTION__
);
1374 SetLastError (ERROR_CALL_NOT_IMPLEMENTED
);
1379 /**********************************************************************
1380 * LookupPrivilegeNameW EXPORTED
1385 LookupPrivilegeNameW (LPCWSTR lpSystemName
,
1390 FIXME("%s() not implemented!\n", __FUNCTION__
);
1391 SetLastError (ERROR_CALL_NOT_IMPLEMENTED
);
1397 pGetSecurityInfoCheck(SECURITY_INFORMATION SecurityInfo
,
1402 PSECURITY_DESCRIPTOR
* ppSecurityDescriptor
)
1404 if ((SecurityInfo
& (OWNER_SECURITY_INFORMATION
|
1405 GROUP_SECURITY_INFORMATION
|
1406 DACL_SECURITY_INFORMATION
|
1407 SACL_SECURITY_INFORMATION
)) &&
1408 ppSecurityDescriptor
== NULL
)
1410 /* if one of the SIDs or ACLs are present, the security descriptor
1412 return ERROR_INVALID_PARAMETER
;
1416 /* reset the pointers unless they're ignored */
1417 if ((SecurityInfo
& OWNER_SECURITY_INFORMATION
) &&
1422 if ((SecurityInfo
& GROUP_SECURITY_INFORMATION
) &&
1427 if ((SecurityInfo
& DACL_SECURITY_INFORMATION
) &&
1432 if ((SecurityInfo
& SACL_SECURITY_INFORMATION
) &&
1438 if (SecurityInfo
& (OWNER_SECURITY_INFORMATION
|
1439 GROUP_SECURITY_INFORMATION
|
1440 DACL_SECURITY_INFORMATION
|
1441 SACL_SECURITY_INFORMATION
))
1443 *ppSecurityDescriptor
= NULL
;
1446 return ERROR_SUCCESS
;
1452 pSetSecurityInfoCheck(PSECURITY_DESCRIPTOR pSecurityDescriptor
,
1453 SECURITY_INFORMATION SecurityInfo
,
1459 /* initialize a security descriptor on the stack */
1460 if (!InitializeSecurityDescriptor(pSecurityDescriptor
,
1461 SECURITY_DESCRIPTOR_REVISION
))
1463 return GetLastError();
1466 if (SecurityInfo
& OWNER_SECURITY_INFORMATION
)
1468 if (RtlValidSid(psidOwner
))
1470 if (!SetSecurityDescriptorOwner(pSecurityDescriptor
,
1474 return GetLastError();
1479 return ERROR_INVALID_PARAMETER
;
1483 if (SecurityInfo
& GROUP_SECURITY_INFORMATION
)
1485 if (RtlValidSid(psidGroup
))
1487 if (!SetSecurityDescriptorGroup(pSecurityDescriptor
,
1491 return GetLastError();
1496 return ERROR_INVALID_PARAMETER
;
1500 if (SecurityInfo
& DACL_SECURITY_INFORMATION
)
1504 if (SetSecurityDescriptorDacl(pSecurityDescriptor
,
1509 /* check if the DACL needs to be protected from being
1510 modified by inheritable ACEs */
1511 if (SecurityInfo
& PROTECTED_DACL_SECURITY_INFORMATION
)
1518 return GetLastError();
1524 /* protect the DACL from being modified by inheritable ACEs */
1525 if (!SetSecurityDescriptorControl(pSecurityDescriptor
,
1529 return GetLastError();
1534 if (SecurityInfo
& SACL_SECURITY_INFORMATION
)
1538 if (SetSecurityDescriptorSacl(pSecurityDescriptor
,
1543 /* check if the SACL needs to be protected from being
1544 modified by inheritable ACEs */
1545 if (SecurityInfo
& PROTECTED_SACL_SECURITY_INFORMATION
)
1552 return GetLastError();
1558 /* protect the SACL from being modified by inheritable ACEs */
1559 if (!SetSecurityDescriptorControl(pSecurityDescriptor
,
1563 return GetLastError();
1568 return ERROR_SUCCESS
;
1572 /**********************************************************************
1573 * GetNamedSecurityInfoW EXPORTED
1578 GetNamedSecurityInfoW(LPWSTR pObjectName
,
1579 SE_OBJECT_TYPE ObjectType
,
1580 SECURITY_INFORMATION SecurityInfo
,
1585 PSECURITY_DESCRIPTOR
*ppSecurityDescriptor
)
1589 if (pObjectName
!= NULL
)
1591 ErrorCode
= CheckNtMartaPresent();
1592 if (ErrorCode
== ERROR_SUCCESS
)
1594 ErrorCode
= pGetSecurityInfoCheck(SecurityInfo
,
1599 ppSecurityDescriptor
);
1601 if (ErrorCode
== ERROR_SUCCESS
)
1603 /* call the MARTA provider */
1604 ErrorCode
= AccRewriteGetNamedRights(pObjectName
,
1611 ppSecurityDescriptor
);
1616 ErrorCode
= ERROR_INVALID_PARAMETER
;
1622 /**********************************************************************
1623 * GetNamedSecurityInfoA EXPORTED
1628 GetNamedSecurityInfoA(LPSTR pObjectName
,
1629 SE_OBJECT_TYPE ObjectType
,
1630 SECURITY_INFORMATION SecurityInfo
,
1635 PSECURITY_DESCRIPTOR
*ppSecurityDescriptor
)
1637 UNICODE_STRING ObjectName
;
1641 Status
= RtlCreateUnicodeStringFromAsciiz(&ObjectName
,
1643 if (!NT_SUCCESS(Status
))
1645 return RtlNtStatusToDosError(Status
);
1648 Ret
= GetNamedSecurityInfoW(ObjectName
.Buffer
,
1655 ppSecurityDescriptor
);
1657 RtlFreeUnicodeString(&ObjectName
);
1663 /**********************************************************************
1664 * SetNamedSecurityInfoW EXPORTED
1669 SetNamedSecurityInfoW(LPWSTR pObjectName
,
1670 SE_OBJECT_TYPE ObjectType
,
1671 SECURITY_INFORMATION SecurityInfo
,
1679 if (pObjectName
!= NULL
)
1681 ErrorCode
= CheckNtMartaPresent();
1682 if (ErrorCode
== ERROR_SUCCESS
)
1684 SECURITY_DESCRIPTOR SecurityDescriptor
;
1686 ErrorCode
= pSetSecurityInfoCheck(&SecurityDescriptor
,
1693 if (ErrorCode
== ERROR_SUCCESS
)
1695 /* call the MARTA provider */
1696 ErrorCode
= AccRewriteSetNamedRights(pObjectName
,
1699 &SecurityDescriptor
);
1704 ErrorCode
= ERROR_INVALID_PARAMETER
;
1710 /**********************************************************************
1711 * SetNamedSecurityInfoA EXPORTED
1716 SetNamedSecurityInfoA(LPSTR pObjectName
,
1717 SE_OBJECT_TYPE ObjectType
,
1718 SECURITY_INFORMATION SecurityInfo
,
1724 UNICODE_STRING ObjectName
;
1728 Status
= RtlCreateUnicodeStringFromAsciiz(&ObjectName
,
1730 if (!NT_SUCCESS(Status
))
1732 return RtlNtStatusToDosError(Status
);
1735 Ret
= SetNamedSecurityInfoW(ObjectName
.Buffer
,
1743 RtlFreeUnicodeString(&ObjectName
);
1749 /**********************************************************************
1750 * GetSecurityInfo EXPORTED
1755 GetSecurityInfo(HANDLE handle
,
1756 SE_OBJECT_TYPE ObjectType
,
1757 SECURITY_INFORMATION SecurityInfo
,
1762 PSECURITY_DESCRIPTOR
* ppSecurityDescriptor
)
1768 ErrorCode
= CheckNtMartaPresent();
1769 if (ErrorCode
== ERROR_SUCCESS
)
1771 ErrorCode
= pGetSecurityInfoCheck(SecurityInfo
,
1776 ppSecurityDescriptor
);
1778 if (ErrorCode
== ERROR_SUCCESS
)
1780 /* call the MARTA provider */
1781 ErrorCode
= AccRewriteGetHandleRights(handle
,
1788 ppSecurityDescriptor
);
1793 ErrorCode
= ERROR_INVALID_HANDLE
;
1799 /**********************************************************************
1800 * SetSecurityInfo EXPORTED
1806 SetSecurityInfo(HANDLE handle
,
1807 SE_OBJECT_TYPE ObjectType
,
1808 SECURITY_INFORMATION SecurityInfo
,
1818 ErrorCode
= CheckNtMartaPresent();
1819 if (ErrorCode
== ERROR_SUCCESS
)
1821 SECURITY_DESCRIPTOR SecurityDescriptor
;
1823 ErrorCode
= pSetSecurityInfoCheck(&SecurityDescriptor
,
1830 if (ErrorCode
== ERROR_SUCCESS
)
1832 /* call the MARTA provider */
1833 ErrorCode
= AccRewriteSetHandleRights(handle
,
1836 &SecurityDescriptor
);
1841 ErrorCode
= ERROR_INVALID_HANDLE
;
1847 /******************************************************************************
1848 * GetSecurityInfoExW EXPORTED
1850 DWORD WINAPI
GetSecurityInfoExA(
1852 SE_OBJECT_TYPE ObjectType
,
1853 SECURITY_INFORMATION SecurityInfo
,
1856 PACTRL_ACCESSA
*ppAccessList
,
1857 PACTRL_AUDITA
*ppAuditList
,
1862 FIXME("%s() not implemented!\n", __FUNCTION__
);
1863 return ERROR_BAD_PROVIDER
;
1867 /******************************************************************************
1868 * GetSecurityInfoExW EXPORTED
1870 DWORD WINAPI
GetSecurityInfoExW(
1872 SE_OBJECT_TYPE ObjectType
,
1873 SECURITY_INFORMATION SecurityInfo
,
1876 PACTRL_ACCESSW
*ppAccessList
,
1877 PACTRL_AUDITW
*ppAuditList
,
1882 FIXME("%s() not implemented!\n", __FUNCTION__
);
1883 return ERROR_BAD_PROVIDER
;
1887 /**********************************************************************
1888 * ImpersonateNamedPipeClient EXPORTED
1893 ImpersonateNamedPipeClient(HANDLE hNamedPipe
)
1895 IO_STATUS_BLOCK StatusBlock
;
1898 TRACE("ImpersonateNamedPipeClient() called\n");
1900 Status
= NtFsControlFile(hNamedPipe
,
1905 FSCTL_PIPE_IMPERSONATE
,
1910 if (!NT_SUCCESS(Status
))
1912 SetLastError(RtlNtStatusToDosError(Status
));
1924 CreatePrivateObjectSecurity(PSECURITY_DESCRIPTOR ParentDescriptor
,
1925 PSECURITY_DESCRIPTOR CreatorDescriptor
,
1926 PSECURITY_DESCRIPTOR
*NewDescriptor
,
1927 BOOL IsDirectoryObject
,
1929 PGENERIC_MAPPING GenericMapping
)
1933 Status
= RtlNewSecurityObject(ParentDescriptor
,
1939 if (!NT_SUCCESS(Status
))
1941 SetLastError(RtlNtStatusToDosError(Status
));
1953 CreatePrivateObjectSecurityEx(PSECURITY_DESCRIPTOR ParentDescriptor
,
1954 PSECURITY_DESCRIPTOR CreatorDescriptor
,
1955 PSECURITY_DESCRIPTOR
* NewDescriptor
,
1957 BOOL IsContainerObject
,
1958 ULONG AutoInheritFlags
,
1960 PGENERIC_MAPPING GenericMapping
)
1962 FIXME("%s() not implemented!\n", __FUNCTION__
);
1971 CreatePrivateObjectSecurityWithMultipleInheritance(PSECURITY_DESCRIPTOR ParentDescriptor
,
1972 PSECURITY_DESCRIPTOR CreatorDescriptor
,
1973 PSECURITY_DESCRIPTOR
* NewDescriptor
,
1976 BOOL IsContainerObject
,
1977 ULONG AutoInheritFlags
,
1979 PGENERIC_MAPPING GenericMapping
)
1981 FIXME("%s() not implemented!\n", __FUNCTION__
);
1990 DestroyPrivateObjectSecurity(PSECURITY_DESCRIPTOR
*ObjectDescriptor
)
1994 Status
= RtlDeleteSecurityObject(ObjectDescriptor
);
1995 if (!NT_SUCCESS(Status
))
1997 SetLastError(RtlNtStatusToDosError(Status
));
2009 GetPrivateObjectSecurity(PSECURITY_DESCRIPTOR ObjectDescriptor
,
2010 SECURITY_INFORMATION SecurityInformation
,
2011 PSECURITY_DESCRIPTOR ResultantDescriptor
,
2012 DWORD DescriptorLength
,
2013 PDWORD ReturnLength
)
2017 Status
= RtlQuerySecurityObject(ObjectDescriptor
,
2018 SecurityInformation
,
2019 ResultantDescriptor
,
2022 if (!NT_SUCCESS(Status
))
2024 SetLastError(RtlNtStatusToDosError(Status
));
2036 SetPrivateObjectSecurity(SECURITY_INFORMATION SecurityInformation
,
2037 PSECURITY_DESCRIPTOR ModificationDescriptor
,
2038 PSECURITY_DESCRIPTOR
*ObjectsSecurityDescriptor
,
2039 PGENERIC_MAPPING GenericMapping
,
2044 Status
= RtlSetSecurityObject(SecurityInformation
,
2045 ModificationDescriptor
,
2046 ObjectsSecurityDescriptor
,
2049 if (!NT_SUCCESS(Status
))
2051 SetLastError(RtlNtStatusToDosError(Status
));
2063 TreeResetNamedSecurityInfoW(LPWSTR pObjectName
,
2064 SE_OBJECT_TYPE ObjectType
,
2065 SECURITY_INFORMATION SecurityInfo
,
2071 FN_PROGRESSW fnProgress
,
2072 PROG_INVOKE_SETTING ProgressInvokeSetting
,
2077 if (pObjectName
!= NULL
)
2079 ErrorCode
= CheckNtMartaPresent();
2080 if (ErrorCode
== ERROR_SUCCESS
)
2084 case SE_FILE_OBJECT
:
2085 case SE_REGISTRY_KEY
:
2087 /* check the SecurityInfo flags for sanity (both, the protected
2088 and unprotected dacl/sacl flag must not be passed together) */
2089 if (((SecurityInfo
& DACL_SECURITY_INFORMATION
) &&
2090 (SecurityInfo
& (PROTECTED_DACL_SECURITY_INFORMATION
| UNPROTECTED_DACL_SECURITY_INFORMATION
)) ==
2091 (PROTECTED_DACL_SECURITY_INFORMATION
| UNPROTECTED_DACL_SECURITY_INFORMATION
))
2095 ((SecurityInfo
& SACL_SECURITY_INFORMATION
) &&
2096 (SecurityInfo
& (PROTECTED_SACL_SECURITY_INFORMATION
| UNPROTECTED_SACL_SECURITY_INFORMATION
)) ==
2097 (PROTECTED_SACL_SECURITY_INFORMATION
| UNPROTECTED_SACL_SECURITY_INFORMATION
)))
2099 ErrorCode
= ERROR_INVALID_PARAMETER
;
2103 /* call the MARTA provider */
2104 ErrorCode
= AccTreeResetNamedSecurityInfo(pObjectName
,
2113 ProgressInvokeSetting
,
2119 /* object type not supported */
2120 ErrorCode
= ERROR_INVALID_PARAMETER
;
2126 ErrorCode
= ERROR_INVALID_PARAMETER
;
2131 #ifdef HAS_FN_PROGRESSW
2133 typedef struct _INERNAL_FNPROGRESSW_DATA
2135 FN_PROGRESSA fnProgress
;
2137 } INERNAL_FNPROGRESSW_DATA
, *PINERNAL_FNPROGRESSW_DATA
;
2140 InternalfnProgressW(LPWSTR pObjectName
,
2142 PPROG_INVOKE_SETTING pInvokeSetting
,
2146 PINERNAL_FNPROGRESSW_DATA pifnProgressData
= (PINERNAL_FNPROGRESSW_DATA
)Args
;
2150 ObjectNameSize
= WideCharToMultiByte(CP_ACP
,
2159 if (ObjectNameSize
> 0)
2161 pObjectNameA
= RtlAllocateHeap(RtlGetProcessHeap(),
2164 if (pObjectNameA
!= NULL
)
2166 pObjectNameA
[0] = '\0';
2167 WideCharToMultiByte(CP_ACP
,
2176 pifnProgressData
->fnProgress((LPWSTR
)pObjectNameA
, /* FIXME: wrong cast!! */
2179 pifnProgressData
->Args
,
2182 RtlFreeHeap(RtlGetProcessHeap(),
2195 TreeResetNamedSecurityInfoA(LPSTR pObjectName
,
2196 SE_OBJECT_TYPE ObjectType
,
2197 SECURITY_INFORMATION SecurityInfo
,
2203 FN_PROGRESSA fnProgress
,
2204 PROG_INVOKE_SETTING ProgressInvokeSetting
,
2207 #ifndef HAS_FN_PROGRESSW
2208 /* That's all this function does, at least up to w2k3... Even MS was too
2209 lazy to implement it... */
2210 return ERROR_CALL_NOT_IMPLEMENTED
;
2212 INERNAL_FNPROGRESSW_DATA ifnProgressData
;
2213 UNICODE_STRING ObjectName
;
2217 Status
= RtlCreateUnicodeStringFromAsciiz(&ObjectName
,
2219 if (!NT_SUCCESS(Status
))
2221 return RtlNtStatusToDosError(Status
);
2224 ifnProgressData
.fnProgress
= fnProgress
;
2225 ifnProgressData
.Args
= Args
;
2227 Ret
= TreeResetNamedSecurityInfoW(ObjectName
.Buffer
,
2235 (fnProgress
!= NULL
? InternalfnProgressW
: NULL
),
2236 ProgressInvokeSetting
,
2239 RtlFreeUnicodeString(&ObjectName
);