3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS kernel
5 * FILE: ntoskrnl/se/sd.c
6 * PURPOSE: Security manager
8 * PROGRAMMERS: David Welch <welch@cwcom.net>
11 /* INCLUDES *****************************************************************/
14 #include <internal/debug.h>
16 /* GLOBALS ******************************************************************/
18 PSECURITY_DESCRIPTOR SePublicDefaultSd
= NULL
;
19 PSECURITY_DESCRIPTOR SePublicDefaultUnrestrictedSd
= NULL
;
20 PSECURITY_DESCRIPTOR SePublicOpenSd
= NULL
;
21 PSECURITY_DESCRIPTOR SePublicOpenUnrestrictedSd
= NULL
;
22 PSECURITY_DESCRIPTOR SeSystemDefaultSd
= NULL
;
23 PSECURITY_DESCRIPTOR SeUnrestrictedSd
= NULL
;
25 /* FUNCTIONS ***************************************************************/
30 /* Create PublicDefaultSd */
31 SePublicDefaultSd
= ExAllocatePoolWithTag(PagedPool
,
32 sizeof(SECURITY_DESCRIPTOR
), TAG_SD
);
33 if (SePublicDefaultSd
== NULL
)
36 RtlCreateSecurityDescriptor(SePublicDefaultSd
,
37 SECURITY_DESCRIPTOR_REVISION
);
38 RtlSetDaclSecurityDescriptor(SePublicDefaultSd
,
43 /* Create PublicDefaultUnrestrictedSd */
44 SePublicDefaultUnrestrictedSd
= ExAllocatePoolWithTag(PagedPool
,
45 sizeof(SECURITY_DESCRIPTOR
), TAG_SD
);
46 if (SePublicDefaultUnrestrictedSd
== NULL
)
49 RtlCreateSecurityDescriptor(SePublicDefaultUnrestrictedSd
,
50 SECURITY_DESCRIPTOR_REVISION
);
51 RtlSetDaclSecurityDescriptor(SePublicDefaultUnrestrictedSd
,
53 SePublicDefaultUnrestrictedDacl
,
56 /* Create PublicOpenSd */
57 SePublicOpenSd
= ExAllocatePoolWithTag(PagedPool
,
58 sizeof(SECURITY_DESCRIPTOR
), TAG_SD
);
59 if (SePublicOpenSd
== NULL
)
62 RtlCreateSecurityDescriptor(SePublicOpenSd
,
63 SECURITY_DESCRIPTOR_REVISION
);
64 RtlSetDaclSecurityDescriptor(SePublicOpenSd
,
69 /* Create PublicOpenUnrestrictedSd */
70 SePublicOpenUnrestrictedSd
= ExAllocatePoolWithTag(PagedPool
,
71 sizeof(SECURITY_DESCRIPTOR
), TAG_SD
);
72 if (SePublicOpenUnrestrictedSd
== NULL
)
75 RtlCreateSecurityDescriptor(SePublicOpenUnrestrictedSd
,
76 SECURITY_DESCRIPTOR_REVISION
);
77 RtlSetDaclSecurityDescriptor(SePublicOpenUnrestrictedSd
,
79 SePublicOpenUnrestrictedDacl
,
82 /* Create SystemDefaultSd */
83 SeSystemDefaultSd
= ExAllocatePoolWithTag(PagedPool
,
84 sizeof(SECURITY_DESCRIPTOR
), TAG_SD
);
85 if (SeSystemDefaultSd
== NULL
)
88 RtlCreateSecurityDescriptor(SeSystemDefaultSd
,
89 SECURITY_DESCRIPTOR_REVISION
);
90 RtlSetDaclSecurityDescriptor(SeSystemDefaultSd
,
95 /* Create UnrestrictedSd */
96 SeUnrestrictedSd
= ExAllocatePoolWithTag(PagedPool
,
97 sizeof(SECURITY_DESCRIPTOR
), TAG_SD
);
98 if (SeUnrestrictedSd
== NULL
)
101 RtlCreateSecurityDescriptor(SeUnrestrictedSd
,
102 SECURITY_DESCRIPTOR_REVISION
);
103 RtlSetDaclSecurityDescriptor(SeUnrestrictedSd
,
113 SeSetWorldSecurityDescriptor(SECURITY_INFORMATION SecurityInformation
,
114 PSECURITY_DESCRIPTOR SecurityDescriptor
,
122 DPRINT("SeSetWorldSecurityDescriptor() called\n");
124 if (SecurityInformation
== 0)
126 return STATUS_ACCESS_DENIED
;
129 SidSize
= RtlLengthSid(SeWorldSid
);
130 SdSize
= sizeof(SECURITY_DESCRIPTOR
) + (2 * SidSize
);
132 if (*BufferLength
< SdSize
)
134 *BufferLength
= SdSize
;
135 return STATUS_BUFFER_TOO_SMALL
;
138 *BufferLength
= SdSize
;
140 Status
= RtlCreateSecurityDescriptor(SecurityDescriptor
,
141 SECURITY_DESCRIPTOR_REVISION
);
142 if (!NT_SUCCESS(Status
))
147 SecurityDescriptor
->Control
|= SE_SELF_RELATIVE
;
148 Current
= (ULONG_PTR
)SecurityDescriptor
+ sizeof(SECURITY_DESCRIPTOR
);
150 if (SecurityInformation
& OWNER_SECURITY_INFORMATION
)
152 RtlCopyMemory((PVOID
)Current
,
155 SecurityDescriptor
->Owner
= (PSID
)((ULONG_PTR
)Current
- (ULONG_PTR
)SecurityDescriptor
);
159 if (SecurityInformation
& GROUP_SECURITY_INFORMATION
)
161 RtlCopyMemory((PVOID
)Current
,
164 SecurityDescriptor
->Group
= (PSID
)((ULONG_PTR
)Current
- (ULONG_PTR
)SecurityDescriptor
);
168 if (SecurityInformation
& DACL_SECURITY_INFORMATION
)
170 SecurityDescriptor
->Control
|= SE_DACL_PRESENT
;
173 if (SecurityInformation
& SACL_SECURITY_INFORMATION
)
175 SecurityDescriptor
->Control
|= SE_SACL_PRESENT
;
178 return STATUS_SUCCESS
;
183 SepCaptureSecurityQualityOfService(IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL
,
184 IN KPROCESSOR_MODE AccessMode
,
185 IN POOL_TYPE PoolType
,
186 IN BOOLEAN CaptureIfKernel
,
187 OUT PSECURITY_QUALITY_OF_SERVICE
*CapturedSecurityQualityOfService
,
188 OUT PBOOLEAN Present
)
190 PSECURITY_QUALITY_OF_SERVICE CapturedQos
;
191 NTSTATUS Status
= STATUS_SUCCESS
;
195 ASSERT(CapturedSecurityQualityOfService
);
198 if(ObjectAttributes
!= NULL
)
200 if(AccessMode
!= KernelMode
)
202 SECURITY_QUALITY_OF_SERVICE SafeQos
;
206 ProbeForRead(ObjectAttributes
,
207 sizeof(ObjectAttributes
),
209 if(ObjectAttributes
->Length
== sizeof(OBJECT_ATTRIBUTES
))
211 if(ObjectAttributes
->SecurityQualityOfService
!= NULL
)
213 ProbeForRead(ObjectAttributes
->SecurityQualityOfService
,
214 sizeof(SECURITY_QUALITY_OF_SERVICE
),
217 if(((PSECURITY_QUALITY_OF_SERVICE
)ObjectAttributes
->SecurityQualityOfService
)->Length
==
218 sizeof(SECURITY_QUALITY_OF_SERVICE
))
220 /* don't allocate memory here because ExAllocate should bugcheck
221 the system if it's buggy, SEH would catch that! So make a local
222 copy of the qos structure.*/
223 RtlCopyMemory(&SafeQos
,
224 ObjectAttributes
->SecurityQualityOfService
,
225 sizeof(SECURITY_QUALITY_OF_SERVICE
));
230 Status
= STATUS_INVALID_PARAMETER
;
235 *CapturedSecurityQualityOfService
= NULL
;
241 Status
= STATUS_INVALID_PARAMETER
;
246 Status
= _SEH_GetExceptionCode();
250 if(NT_SUCCESS(Status
))
254 CapturedQos
= ExAllocatePool(PoolType
,
255 sizeof(SECURITY_QUALITY_OF_SERVICE
));
256 if(CapturedQos
!= NULL
)
258 RtlCopyMemory(CapturedQos
,
260 sizeof(SECURITY_QUALITY_OF_SERVICE
));
261 *CapturedSecurityQualityOfService
= CapturedQos
;
265 Status
= STATUS_INSUFFICIENT_RESOURCES
;
270 *CapturedSecurityQualityOfService
= NULL
;
276 if(ObjectAttributes
->Length
== sizeof(OBJECT_ATTRIBUTES
))
280 if(ObjectAttributes
->SecurityQualityOfService
!= NULL
)
282 if(((PSECURITY_QUALITY_OF_SERVICE
)ObjectAttributes
->SecurityQualityOfService
)->Length
==
283 sizeof(SECURITY_QUALITY_OF_SERVICE
))
285 CapturedQos
= ExAllocatePool(PoolType
,
286 sizeof(SECURITY_QUALITY_OF_SERVICE
));
287 if(CapturedQos
!= NULL
)
289 RtlCopyMemory(CapturedQos
,
290 ObjectAttributes
->SecurityQualityOfService
,
291 sizeof(SECURITY_QUALITY_OF_SERVICE
));
292 *CapturedSecurityQualityOfService
= CapturedQos
;
297 Status
= STATUS_INSUFFICIENT_RESOURCES
;
302 Status
= STATUS_INVALID_PARAMETER
;
307 *CapturedSecurityQualityOfService
= NULL
;
313 *CapturedSecurityQualityOfService
= (PSECURITY_QUALITY_OF_SERVICE
)ObjectAttributes
->SecurityQualityOfService
;
314 *Present
= (ObjectAttributes
->SecurityQualityOfService
!= NULL
);
319 Status
= STATUS_INVALID_PARAMETER
;
325 *CapturedSecurityQualityOfService
= NULL
;
334 SepReleaseSecurityQualityOfService(IN PSECURITY_QUALITY_OF_SERVICE CapturedSecurityQualityOfService OPTIONAL
,
335 IN KPROCESSOR_MODE AccessMode
,
336 IN BOOLEAN CaptureIfKernel
)
340 if(CapturedSecurityQualityOfService
!= NULL
&&
341 (AccessMode
== UserMode
||
342 (AccessMode
== KernelMode
&& CaptureIfKernel
)))
344 ExFreePool(CapturedSecurityQualityOfService
);
354 SeCaptureSecurityDescriptor(
355 IN PSECURITY_DESCRIPTOR OriginalSecurityDescriptor
,
356 IN KPROCESSOR_MODE CurrentMode
,
357 IN POOL_TYPE PoolType
,
358 IN BOOLEAN CaptureIfKernel
,
359 OUT PSECURITY_DESCRIPTOR
*CapturedSecurityDescriptor
362 SECURITY_DESCRIPTOR DescriptorCopy
;
363 PSECURITY_DESCRIPTOR NewDescriptor
;
364 ULONG OwnerSAC
= 0, GroupSAC
= 0;
365 ULONG OwnerSize
= 0, GroupSize
= 0;
366 ULONG SaclSize
= 0, DaclSize
= 0;
367 ULONG DescriptorSize
= 0;
368 NTSTATUS Status
= STATUS_SUCCESS
;
370 if(OriginalSecurityDescriptor
!= NULL
)
372 if(CurrentMode
!= KernelMode
)
374 RtlZeroMemory(&DescriptorCopy
, sizeof(DescriptorCopy
));
378 /* first only probe and copy until the control field of the descriptor
379 to determine whether it's a self-relative descriptor */
380 DescriptorSize
= (ULONG
)((ULONG_PTR
)&OriginalSecurityDescriptor
->Control
-
381 (ULONG_PTR
)OriginalSecurityDescriptor
) +
382 sizeof(OriginalSecurityDescriptor
->Control
);
383 ProbeForRead(OriginalSecurityDescriptor
,
387 if(OriginalSecurityDescriptor
->Revision
!= SECURITY_DESCRIPTOR_REVISION1
)
389 Status
= STATUS_UNKNOWN_REVISION
;
393 /* make a copy on the stack */
394 DescriptorCopy
.Revision
= OriginalSecurityDescriptor
->Revision
;
395 DescriptorCopy
.Sbz1
= OriginalSecurityDescriptor
->Sbz1
;
396 DescriptorCopy
.Control
= OriginalSecurityDescriptor
->Control
;
397 DescriptorSize
= ((DescriptorCopy
.Control
& SE_SELF_RELATIVE
) ?
398 sizeof(SECURITY_DESCRIPTOR_RELATIVE
) : sizeof(SECURITY_DESCRIPTOR
));
400 /* probe and copy the entire security descriptor structure. The SIDs
401 and ACLs will be probed and copied later though */
402 ProbeForRead(OriginalSecurityDescriptor
,
405 if(DescriptorCopy
.Control
& SE_SELF_RELATIVE
)
407 PSECURITY_DESCRIPTOR_RELATIVE RelSD
= (PSECURITY_DESCRIPTOR_RELATIVE
)OriginalSecurityDescriptor
;
409 DescriptorCopy
.Owner
= (PSID
)RelSD
->Owner
;
410 DescriptorCopy
.Group
= (PSID
)RelSD
->Group
;
411 DescriptorCopy
.Sacl
= (PACL
)RelSD
->Sacl
;
412 DescriptorCopy
.Dacl
= (PACL
)RelSD
->Dacl
;
416 DescriptorCopy
.Owner
= OriginalSecurityDescriptor
->Owner
;
417 DescriptorCopy
.Group
= OriginalSecurityDescriptor
->Group
;
418 DescriptorCopy
.Sacl
= OriginalSecurityDescriptor
->Sacl
;
419 DescriptorCopy
.Dacl
= OriginalSecurityDescriptor
->Dacl
;
424 Status
= _SEH_GetExceptionCode();
428 if(!NT_SUCCESS(Status
))
433 else if(!CaptureIfKernel
)
435 if(OriginalSecurityDescriptor
->Revision
!= SECURITY_DESCRIPTOR_REVISION1
)
437 return STATUS_UNKNOWN_REVISION
;
440 *CapturedSecurityDescriptor
= OriginalSecurityDescriptor
;
441 return STATUS_SUCCESS
;
445 if(OriginalSecurityDescriptor
->Revision
!= SECURITY_DESCRIPTOR_REVISION1
)
447 return STATUS_UNKNOWN_REVISION
;
450 /* make a copy on the stack */
451 DescriptorCopy
.Revision
= OriginalSecurityDescriptor
->Revision
;
452 DescriptorCopy
.Sbz1
= OriginalSecurityDescriptor
->Sbz1
;
453 DescriptorCopy
.Control
= OriginalSecurityDescriptor
->Control
;
454 DescriptorSize
= ((DescriptorCopy
.Control
& SE_SELF_RELATIVE
) ?
455 sizeof(SECURITY_DESCRIPTOR_RELATIVE
) : sizeof(SECURITY_DESCRIPTOR
));
456 if(DescriptorCopy
.Control
& SE_SELF_RELATIVE
)
458 PSECURITY_DESCRIPTOR_RELATIVE RelSD
= (PSECURITY_DESCRIPTOR_RELATIVE
)OriginalSecurityDescriptor
;
460 DescriptorCopy
.Owner
= (PSID
)RelSD
->Owner
;
461 DescriptorCopy
.Group
= (PSID
)RelSD
->Group
;
462 DescriptorCopy
.Sacl
= (PACL
)RelSD
->Sacl
;
463 DescriptorCopy
.Dacl
= (PACL
)RelSD
->Dacl
;
467 DescriptorCopy
.Owner
= OriginalSecurityDescriptor
->Owner
;
468 DescriptorCopy
.Group
= OriginalSecurityDescriptor
->Group
;
469 DescriptorCopy
.Sacl
= OriginalSecurityDescriptor
->Sacl
;
470 DescriptorCopy
.Dacl
= OriginalSecurityDescriptor
->Dacl
;
474 if(DescriptorCopy
.Control
& SE_SELF_RELATIVE
)
476 /* in case we're dealing with a self-relative descriptor, do a basic convert
477 to an absolute descriptor. We do this so we can simply access the data
478 using the pointers without calculating them again. */
479 DescriptorCopy
.Control
&= ~SE_SELF_RELATIVE
;
480 if(DescriptorCopy
.Owner
!= NULL
)
482 DescriptorCopy
.Owner
= (PSID
)((ULONG_PTR
)OriginalSecurityDescriptor
+ (ULONG_PTR
)DescriptorCopy
.Owner
);
484 if(DescriptorCopy
.Group
!= NULL
)
486 DescriptorCopy
.Group
= (PSID
)((ULONG_PTR
)OriginalSecurityDescriptor
+ (ULONG_PTR
)DescriptorCopy
.Group
);
488 if(DescriptorCopy
.Dacl
!= NULL
)
490 DescriptorCopy
.Dacl
= (PACL
)((ULONG_PTR
)OriginalSecurityDescriptor
+ (ULONG_PTR
)DescriptorCopy
.Dacl
);
492 if(DescriptorCopy
.Sacl
!= NULL
)
494 DescriptorCopy
.Sacl
= (PACL
)((ULONG_PTR
)OriginalSecurityDescriptor
+ (ULONG_PTR
)DescriptorCopy
.Sacl
);
498 /* determine the size of the SIDs */
499 #define DetermineSIDSize(SidType) \
501 if(DescriptorCopy.SidType != NULL) \
503 SID *SidType = (SID*)DescriptorCopy.SidType; \
505 if(CurrentMode != KernelMode) \
507 /* securely access the buffers! */ \
510 ProbeForRead(&SidType->SubAuthorityCount, \
511 sizeof(SidType->SubAuthorityCount), \
513 SidType##SAC = SidType->SubAuthorityCount; \
514 SidType##Size = RtlLengthRequiredSid(SidType##SAC); \
515 DescriptorSize += ROUND_UP(SidType##Size, sizeof(ULONG)); \
516 ProbeForRead(SidType, \
519 if(!RtlValidSid(SidType)) \
521 Status = STATUS_INVALID_SID; \
526 Status = _SEH_GetExceptionCode(); \
530 if(!NT_SUCCESS(Status)) \
537 SidType##SAC = SidType->SubAuthorityCount; \
538 SidType##Size = RtlLengthRequiredSid(SidType##SAC); \
539 DescriptorSize += ROUND_UP(SidType##Size, sizeof(ULONG)); \
544 DetermineSIDSize(Owner
);
545 DetermineSIDSize(Group
);
547 /* determine the size of the ACLs */
548 #define DetermineACLSize(AclType, AclFlag) \
550 if((DescriptorCopy.Control & SE_##AclFlag##_PRESENT) && \
551 DescriptorCopy.AclType != NULL) \
553 PACL AclType = (PACL)DescriptorCopy.AclType; \
555 if(CurrentMode != KernelMode) \
557 /* securely access the buffers! */ \
560 ProbeForRead(&AclType->AclSize, \
561 sizeof(AclType->AclSize), \
563 AclType##Size = AclType->AclSize; \
564 DescriptorSize += ROUND_UP(AclType##Size, sizeof(ULONG)); \
565 ProbeForRead(AclType, \
568 if(!RtlValidAcl(AclType)) \
570 Status = STATUS_INVALID_ACL; \
575 Status = _SEH_GetExceptionCode(); \
579 if(!NT_SUCCESS(Status)) \
586 AclType##Size = AclType->AclSize; \
587 DescriptorSize += ROUND_UP(AclType##Size, sizeof(ULONG)); \
592 DescriptorCopy.AclType = NULL; \
596 DetermineACLSize(Sacl
, SACL
);
597 DetermineACLSize(Dacl
, DACL
);
599 /* allocate enough memory to store a complete copy of a self-relative
600 security descriptor */
601 NewDescriptor
= ExAllocatePool(PoolType
,
603 if(NewDescriptor
!= NULL
)
605 ULONG_PTR Offset
= sizeof(SECURITY_DESCRIPTOR
);
607 RtlZeroMemory(NewDescriptor
, DescriptorSize
);
608 NewDescriptor
->Revision
= DescriptorCopy
.Revision
;
609 NewDescriptor
->Sbz1
= DescriptorCopy
.Sbz1
;
610 NewDescriptor
->Control
= DescriptorCopy
.Control
| SE_SELF_RELATIVE
;
614 /* setup the offsets and copy the SIDs and ACLs to the new
615 self-relative security descriptor. Probing the pointers is not
616 neccessary anymore as we did that when collecting the sizes! */
617 #define CopySIDOrACL(Type) \
619 if(DescriptorCopy.Type != NULL) \
621 NewDescriptor->Type = (PVOID)Offset; \
622 RtlCopyMemory((PVOID)((ULONG_PTR)NewDescriptor + \
623 (ULONG_PTR)NewDescriptor->Type), \
624 DescriptorCopy.Type, \
626 Offset += ROUND_UP(Type##Size, sizeof(ULONG)); \
637 Status
= _SEH_GetExceptionCode();
641 if(NT_SUCCESS(Status
))
643 /* we're finally done! copy the pointer to the captured descriptor to
645 *CapturedSecurityDescriptor
= NewDescriptor
;
646 return STATUS_SUCCESS
;
650 /* we failed to copy the data to the new descriptor */
651 ExFreePool(NewDescriptor
);
656 Status
= STATUS_INSUFFICIENT_RESOURCES
;
661 /* nothing to do... */
662 *CapturedSecurityDescriptor
= NULL
;
672 SeQuerySecurityDescriptorInfo(IN PSECURITY_INFORMATION SecurityInformation
,
673 IN OUT PSECURITY_DESCRIPTOR SecurityDescriptor
,
674 IN OUT PULONG Length
,
675 IN PSECURITY_DESCRIPTOR
*ObjectsSecurityDescriptor OPTIONAL
)
677 PSECURITY_DESCRIPTOR ObjectSd
;
678 PSECURITY_DESCRIPTOR_RELATIVE RelSD
;
683 ULONG OwnerLength
= 0;
684 ULONG GroupLength
= 0;
685 ULONG DaclLength
= 0;
686 ULONG SaclLength
= 0;
691 RelSD
= (PSECURITY_DESCRIPTOR_RELATIVE
)SecurityDescriptor
;
693 if (*ObjectsSecurityDescriptor
== NULL
)
695 if (*Length
< sizeof(SECURITY_DESCRIPTOR_RELATIVE
))
697 *Length
= sizeof(SECURITY_DESCRIPTOR_RELATIVE
);
698 return STATUS_BUFFER_TOO_SMALL
;
701 *Length
= sizeof(SECURITY_DESCRIPTOR_RELATIVE
);
702 RtlCreateSecurityDescriptorRelative(RelSD
,
703 SECURITY_DESCRIPTOR_REVISION
);
704 return STATUS_SUCCESS
;
707 ObjectSd
= *ObjectsSecurityDescriptor
;
709 /* Calculate the required security descriptor length */
710 Control
= SE_SELF_RELATIVE
;
711 if ((*SecurityInformation
& OWNER_SECURITY_INFORMATION
) &&
712 (ObjectSd
->Owner
!= NULL
))
714 Owner
= (PSID
)((ULONG_PTR
)ObjectSd
->Owner
+ (ULONG_PTR
)ObjectSd
);
715 OwnerLength
= ROUND_UP(RtlLengthSid(Owner
), 4);
716 Control
|= (ObjectSd
->Control
& SE_OWNER_DEFAULTED
);
719 if ((*SecurityInformation
& GROUP_SECURITY_INFORMATION
) &&
720 (ObjectSd
->Group
!= NULL
))
722 Group
= (PSID
)((ULONG_PTR
)ObjectSd
->Group
+ (ULONG_PTR
)ObjectSd
);
723 GroupLength
= ROUND_UP(RtlLengthSid(Group
), 4);
724 Control
|= (ObjectSd
->Control
& SE_GROUP_DEFAULTED
);
727 if ((*SecurityInformation
& DACL_SECURITY_INFORMATION
) &&
728 (ObjectSd
->Control
& SE_DACL_PRESENT
))
730 if (ObjectSd
->Dacl
!= NULL
)
732 Dacl
= (PACL
)((ULONG_PTR
)ObjectSd
->Dacl
+ (ULONG_PTR
)ObjectSd
);
733 DaclLength
= ROUND_UP((ULONG
)Dacl
->AclSize
, 4);
735 Control
|= (ObjectSd
->Control
& (SE_DACL_DEFAULTED
| SE_DACL_PRESENT
));
738 if ((*SecurityInformation
& SACL_SECURITY_INFORMATION
) &&
739 (ObjectSd
->Control
& SE_SACL_PRESENT
))
741 if (ObjectSd
->Sacl
!= NULL
)
743 Sacl
= (PACL
)((ULONG_PTR
)ObjectSd
->Sacl
+ (ULONG_PTR
)ObjectSd
);
744 SaclLength
= ROUND_UP(Sacl
->AclSize
, 4);
746 Control
|= (ObjectSd
->Control
& (SE_SACL_DEFAULTED
| SE_SACL_PRESENT
));
749 SdLength
= OwnerLength
+ GroupLength
+ DaclLength
+
750 SaclLength
+ sizeof(SECURITY_DESCRIPTOR_RELATIVE
);
751 if (*Length
< SdLength
)
754 return STATUS_BUFFER_TOO_SMALL
;
757 /* Build the new security descrtiptor */
758 RtlCreateSecurityDescriptorRelative(RelSD
,
759 SECURITY_DESCRIPTOR_REVISION
);
760 RelSD
->Control
= Control
;
762 Current
= (ULONG_PTR
)(RelSD
+ 1);
764 if (OwnerLength
!= 0)
766 RtlCopyMemory((PVOID
)Current
,
769 RelSD
->Owner
= (ULONG
)(Current
- (ULONG_PTR
)SecurityDescriptor
);
770 Current
+= OwnerLength
;
773 if (GroupLength
!= 0)
775 RtlCopyMemory((PVOID
)Current
,
778 RelSD
->Group
= (ULONG
)(Current
- (ULONG_PTR
)SecurityDescriptor
);
779 Current
+= GroupLength
;
784 RtlCopyMemory((PVOID
)Current
,
787 RelSD
->Dacl
= (ULONG
)(Current
- (ULONG_PTR
)SecurityDescriptor
);
788 Current
+= DaclLength
;
793 RtlCopyMemory((PVOID
)Current
,
796 RelSD
->Sacl
= (ULONG
)(Current
- (ULONG_PTR
)SecurityDescriptor
);
797 Current
+= SaclLength
;
802 return STATUS_SUCCESS
;
810 SeReleaseSecurityDescriptor(
811 IN PSECURITY_DESCRIPTOR CapturedSecurityDescriptor
,
812 IN KPROCESSOR_MODE CurrentMode
,
813 IN BOOLEAN CaptureIfKernelMode
818 /* WARNING! You need to call this function with the same value for CurrentMode
819 and CaptureIfKernelMode that you previously passed to
820 SeCaptureSecurityDescriptor() in order to avoid memory leaks! */
821 if(CapturedSecurityDescriptor
!= NULL
&&
822 (CurrentMode
== UserMode
||
823 (CurrentMode
== KernelMode
&& CaptureIfKernelMode
)))
825 /* only delete the descriptor when SeCaptureSecurityDescriptor() allocated one! */
826 ExFreePool(CapturedSecurityDescriptor
);
829 return STATUS_SUCCESS
;
836 SeSetSecurityDescriptorInfo(IN PVOID Object OPTIONAL
,
837 IN PSECURITY_INFORMATION SecurityInformation
,
838 IN PSECURITY_DESCRIPTOR SecurityDescriptor
,
839 IN OUT PSECURITY_DESCRIPTOR
*ObjectsSecurityDescriptor
,
840 IN POOL_TYPE PoolType
,
841 IN PGENERIC_MAPPING GenericMapping
)
844 return STATUS_NOT_IMPLEMENTED
;
852 SeSetSecurityDescriptorInfoEx(
853 IN PVOID Object OPTIONAL
,
854 IN PSECURITY_INFORMATION SecurityInformation
,
855 IN PSECURITY_DESCRIPTOR ModificationDescriptor
,
856 IN OUT PSECURITY_DESCRIPTOR
*ObjectsSecurityDescriptor
,
857 IN ULONG AutoInheritFlags
,
858 IN POOL_TYPE PoolType
,
859 IN PGENERIC_MAPPING GenericMapping
863 return STATUS_NOT_IMPLEMENTED
;
871 SeValidSecurityDescriptor(IN ULONG Length
,
872 IN PSECURITY_DESCRIPTOR SecurityDescriptor
)
878 if (Length
< SECURITY_DESCRIPTOR_MIN_LENGTH
)
880 DPRINT1("Invalid Security Descriptor revision\n");
884 if (SecurityDescriptor
->Revision
!= SECURITY_DESCRIPTOR_REVISION1
)
886 DPRINT1("Invalid Security Descriptor revision\n");
890 if (!(SecurityDescriptor
->Control
& SE_SELF_RELATIVE
))
892 DPRINT1("No self-relative Security Descriptor\n");
896 SdLength
= sizeof(SECURITY_DESCRIPTOR
);
898 /* Check Owner SID */
899 if (SecurityDescriptor
->Owner
== NULL
)
901 DPRINT1("No Owner SID\n");
905 if ((ULONG_PTR
)SecurityDescriptor
->Owner
% sizeof(ULONG
))
907 DPRINT1("Invalid Owner SID alignment\n");
911 Sid
= (PISID
)((ULONG_PTR
)SecurityDescriptor
+ (ULONG_PTR
)SecurityDescriptor
->Owner
);
912 if (Sid
->Revision
!= SID_REVISION
)
914 DPRINT1("Invalid Owner SID revision\n");
918 SdLength
+= (sizeof(SID
) + (Sid
->SubAuthorityCount
- 1) * sizeof(ULONG
));
919 if (Length
< SdLength
)
921 DPRINT1("Invalid Owner SID size\n");
925 /* Check Group SID */
926 if (SecurityDescriptor
->Group
!= NULL
)
928 if ((ULONG_PTR
)SecurityDescriptor
->Group
% sizeof(ULONG
))
930 DPRINT1("Invalid Group SID alignment\n");
934 Sid
= (PSID
)((ULONG_PTR
)SecurityDescriptor
+ (ULONG_PTR
)SecurityDescriptor
->Group
);
935 if (Sid
->Revision
!= SID_REVISION
)
937 DPRINT1("Invalid Group SID revision\n");
941 SdLength
+= (sizeof(SID
) + (Sid
->SubAuthorityCount
- 1) * sizeof(ULONG
));
942 if (Length
< SdLength
)
944 DPRINT1("Invalid Group SID size\n");
950 if (SecurityDescriptor
->Dacl
!= NULL
)
952 if ((ULONG_PTR
)SecurityDescriptor
->Dacl
% sizeof(ULONG
))
954 DPRINT1("Invalid DACL alignment\n");
958 Acl
= (PACL
)((ULONG_PTR
)SecurityDescriptor
+ (ULONG_PTR
)SecurityDescriptor
->Dacl
);
959 if ((Acl
->AclRevision
< MIN_ACL_REVISION
) &&
960 (Acl
->AclRevision
> MAX_ACL_REVISION
))
962 DPRINT1("Invalid DACL revision\n");
966 SdLength
+= Acl
->AclSize
;
967 if (Length
< SdLength
)
969 DPRINT1("Invalid DACL size\n");
975 if (SecurityDescriptor
->Sacl
!= NULL
)
977 if ((ULONG_PTR
)SecurityDescriptor
->Sacl
% sizeof(ULONG
))
979 DPRINT1("Invalid SACL alignment\n");
983 Acl
= (PACL
)((ULONG_PTR
)SecurityDescriptor
+ (ULONG_PTR
)SecurityDescriptor
->Sacl
);
984 if ((Acl
->AclRevision
< MIN_ACL_REVISION
) ||
985 (Acl
->AclRevision
> MAX_ACL_REVISION
))
987 DPRINT1("Invalid SACL revision\n");
991 SdLength
+= Acl
->AclSize
;
992 if (Length
< SdLength
)
994 DPRINT1("Invalid SACL size\n");