1 // Licensed to the .NET Foundation under one or more agreements. 2 // The .NET Foundation licenses this file to you under the MIT license. 3 // See the LICENSE file in the project root for more information. 4 5 // Licensed under the MIT license. See LICENSE file in the project root for full license information. 6 // 7 // Managed ACL wrapper for directories 8 9 10 using Microsoft.Win32.SafeHandles; 11 using Microsoft.Win32; 12 using System.Collections; 13 using System.Diagnostics; 14 using System.IO; 15 using System.Reflection; 16 using System.Runtime.InteropServices; 17 using System.Runtime.Versioning; 18 using System.Security.AccessControl; 19 using System.Security.Principal; 20 using System; 21 22 namespace System.Security.AccessControl 23 { 24 public abstract class DirectoryObjectSecurity : ObjectSecurity 25 { 26 #region Private Members 27 28 internal CommonSecurityDescriptor _securityDescriptor; 29 30 #endregion 31 32 #region Constructors 33 DirectoryObjectSecurity()34 protected DirectoryObjectSecurity() 35 : base(true, true) 36 { 37 return; 38 } 39 DirectoryObjectSecurity(CommonSecurityDescriptor securityDescriptor)40 protected DirectoryObjectSecurity(CommonSecurityDescriptor securityDescriptor) 41 : base(securityDescriptor) 42 { 43 if (securityDescriptor == null) 44 { 45 throw new ArgumentNullException(nameof(securityDescriptor)); 46 } 47 48 _securityDescriptor = securityDescriptor; 49 } 50 51 #endregion 52 53 #region Private Methods 54 55 // Ported from NDP\clr\src\BCL\System\Security\Principal\SID.cs since we can't access System.Security.Principal.IdentityReference's internals IsValidTargetTypeStatic(Type targetType)56 private static bool IsValidTargetTypeStatic(Type targetType) 57 { 58 if (targetType == typeof(NTAccount)) 59 { 60 return true; 61 } 62 else if (targetType == typeof(SecurityIdentifier)) 63 { 64 return true; 65 } 66 else 67 { 68 return false; 69 } 70 } 71 GetRules(bool access, bool includeExplicit, bool includeInherited, System.Type targetType)72 private AuthorizationRuleCollection GetRules(bool access, bool includeExplicit, bool includeInherited, System.Type targetType) 73 { 74 ReadLock(); 75 76 try 77 { 78 AuthorizationRuleCollection result = new AuthorizationRuleCollection(); 79 80 if (!IsValidTargetTypeStatic(targetType)) 81 { 82 throw new ArgumentException(SR.Arg_MustBeIdentityReferenceType, nameof(targetType)); 83 } 84 85 CommonAcl acl = null; 86 87 if (access) 88 { 89 if ((_securityDescriptor.ControlFlags & ControlFlags.DiscretionaryAclPresent) != 0) 90 { 91 acl = _securityDescriptor.DiscretionaryAcl; 92 } 93 } 94 else // !access == audit 95 { 96 if ((_securityDescriptor.ControlFlags & ControlFlags.SystemAclPresent) != 0) 97 { 98 acl = _securityDescriptor.SystemAcl; 99 } 100 } 101 102 if (acl == null) 103 { 104 // 105 // The required ACL was not present; return an empty collection. 106 // 107 return result; 108 } 109 110 IdentityReferenceCollection irTarget = null; 111 112 if (targetType != typeof(SecurityIdentifier)) 113 { 114 IdentityReferenceCollection irSource = new IdentityReferenceCollection(acl.Count); 115 116 for (int i = 0; i < acl.Count; i++) 117 { 118 // 119 // Calling the indexer on a common ACL results in cloning, 120 // (which would not be the case if we were to use the internal RawAcl property) 121 // but also ensures that the resulting order of ACEs is proper 122 // However, this is a big price to pay - cloning all the ACEs just so that 123 // the canonical order could be ascertained just once. 124 // A better way would be to have an internal method that would canonicalize the ACL 125 // and call it once, then use the RawAcl. 126 // 127 QualifiedAce ace = acl[i] as QualifiedAce; 128 129 if (ace == null) 130 { 131 // 132 // Only consider qualified ACEs 133 // 134 continue; 135 } 136 137 if (ace.IsCallback == true) 138 { 139 // 140 // Ignore callback ACEs 141 // 142 continue; 143 } 144 145 if (access) 146 { 147 if (ace.AceQualifier != AceQualifier.AccessAllowed && ace.AceQualifier != AceQualifier.AccessDenied) 148 { 149 continue; 150 } 151 } 152 else 153 { 154 if (ace.AceQualifier != AceQualifier.SystemAudit) 155 { 156 continue; 157 } 158 } 159 160 irSource.Add(ace.SecurityIdentifier); 161 } 162 163 irTarget = irSource.Translate(targetType); 164 } 165 166 for (int i = 0; i < acl.Count; i++) 167 { 168 // 169 // Calling the indexer on a common ACL results in cloning, 170 // (which would not be the case if we were to use the internal RawAcl property) 171 // but also ensures that the resulting order of ACEs is proper 172 // However, this is a big price to pay - cloning all the ACEs just so that 173 // the canonical order could be ascertained just once. 174 // A better way would be to have an internal method that would canonicalize the ACL 175 // and call it once, then use the RawAcl. 176 // 177 QualifiedAce ace = acl[i] as CommonAce; 178 179 if (ace == null) 180 { 181 ace = acl[i] as ObjectAce; 182 if (ace == null) 183 { 184 // 185 // Only consider common or object ACEs 186 // 187 continue; 188 } 189 } 190 191 if (ace.IsCallback == true) 192 { 193 // 194 // Ignore callback ACEs 195 // 196 continue; 197 } 198 199 if (access) 200 { 201 if (ace.AceQualifier != AceQualifier.AccessAllowed && ace.AceQualifier != AceQualifier.AccessDenied) 202 { 203 continue; 204 } 205 } 206 else 207 { 208 if (ace.AceQualifier != AceQualifier.SystemAudit) 209 { 210 continue; 211 } 212 } 213 214 if ((includeExplicit && ((ace.AceFlags & AceFlags.Inherited) == 0)) || (includeInherited && ((ace.AceFlags & AceFlags.Inherited) != 0))) 215 { 216 IdentityReference iref = (targetType == typeof(SecurityIdentifier)) ? ace.SecurityIdentifier : irTarget[i]; 217 218 if (access) 219 { 220 AccessControlType type; 221 222 if (ace.AceQualifier == AceQualifier.AccessAllowed) 223 { 224 type = AccessControlType.Allow; 225 } 226 else 227 { 228 type = AccessControlType.Deny; 229 } 230 231 if (ace is ObjectAce) 232 { 233 ObjectAce objectAce = ace as ObjectAce; 234 235 result.AddRule(AccessRuleFactory(iref, objectAce.AccessMask, objectAce.IsInherited, objectAce.InheritanceFlags, objectAce.PropagationFlags, type, objectAce.ObjectAceType, objectAce.InheritedObjectAceType)); 236 } 237 else 238 { 239 CommonAce commonAce = ace as CommonAce; 240 241 if (commonAce == null) 242 { 243 continue; 244 } 245 246 result.AddRule(AccessRuleFactory(iref, commonAce.AccessMask, commonAce.IsInherited, commonAce.InheritanceFlags, commonAce.PropagationFlags, type)); 247 } 248 } 249 else 250 { 251 if (ace is ObjectAce) 252 { 253 ObjectAce objectAce = ace as ObjectAce; 254 255 result.AddRule(AuditRuleFactory(iref, objectAce.AccessMask, objectAce.IsInherited, objectAce.InheritanceFlags, objectAce.PropagationFlags, objectAce.AuditFlags, objectAce.ObjectAceType, objectAce.InheritedObjectAceType)); 256 } 257 else 258 { 259 CommonAce commonAce = ace as CommonAce; 260 261 if (commonAce == null) 262 { 263 continue; 264 } 265 266 result.AddRule(AuditRuleFactory(iref, commonAce.AccessMask, commonAce.IsInherited, commonAce.InheritanceFlags, commonAce.PropagationFlags, commonAce.AuditFlags)); 267 } 268 } 269 } 270 } 271 272 return result; 273 } 274 finally 275 { 276 ReadUnlock(); 277 } 278 } 279 280 // 281 // Modifies the DACL 282 // ModifyAccess(AccessControlModification modification, ObjectAccessRule rule, out bool modified)283 private bool ModifyAccess(AccessControlModification modification, ObjectAccessRule rule, out bool modified) 284 { 285 bool result = true; 286 287 if (_securityDescriptor.DiscretionaryAcl == null) 288 { 289 if (modification == AccessControlModification.Remove || modification == AccessControlModification.RemoveAll || modification == AccessControlModification.RemoveSpecific) 290 { 291 modified = false; 292 return result; 293 } 294 295 //_securityDescriptor.DiscretionaryAcl = new DiscretionaryAcl(IsContainer, IsDS, GenericAcl.AclRevisionDS, 1); 296 //_securityDescriptor.AddControlFlags(ControlFlags.DiscretionaryAclPresent); 297 _securityDescriptor.AddDiscretionaryAcl(GenericAcl.AclRevisionDS, 1); 298 } 299 else if ((modification == AccessControlModification.Add || modification == AccessControlModification.Set || modification == AccessControlModification.Reset) && 300 (rule.ObjectFlags != ObjectAceFlags.None)) 301 { 302 // 303 // This will result in an object ace being added to the dacl, so the dacl revision must be AclRevisionDS 304 // 305 if (_securityDescriptor.DiscretionaryAcl.Revision < GenericAcl.AclRevisionDS) 306 { 307 // 308 // we need to create a new dacl with the same aces as the existing one but the revision should be AclRevisionDS 309 // 310 byte[] binaryForm = new byte[_securityDescriptor.DiscretionaryAcl.BinaryLength]; 311 _securityDescriptor.DiscretionaryAcl.GetBinaryForm(binaryForm, 0); 312 binaryForm[0] = GenericAcl.AclRevisionDS; // revision is the first byte of the binary form 313 314 _securityDescriptor.DiscretionaryAcl = new DiscretionaryAcl(IsContainer, IsDS, new RawAcl(binaryForm, 0)); 315 } 316 } 317 318 SecurityIdentifier sid = rule.IdentityReference.Translate(typeof(SecurityIdentifier)) as SecurityIdentifier; 319 320 if (rule.AccessControlType == AccessControlType.Allow) 321 { 322 switch (modification) 323 { 324 case AccessControlModification.Add: 325 //_securityDescriptor.DiscretionaryAcl.AddAccess(AccessControlType.Allow, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 326 _securityDescriptor.DiscretionaryAcl.AddAccess(AccessControlType.Allow, sid, rule); 327 break; 328 329 case AccessControlModification.Set: 330 //_securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Allow, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 331 _securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Allow, sid, rule); 332 break; 333 334 case AccessControlModification.Reset: 335 _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Deny, sid, -1, InheritanceFlags.ContainerInherit, 0, ObjectAceFlags.None, Guid.Empty, Guid.Empty); 336 //_securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Allow, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 337 _securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Allow, sid, rule); 338 break; 339 340 case AccessControlModification.Remove: 341 //result = _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Allow, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 342 result = _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Allow, sid, rule); 343 break; 344 345 case AccessControlModification.RemoveAll: 346 result = _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Allow, sid, -1, InheritanceFlags.ContainerInherit, 0, ObjectAceFlags.None, Guid.Empty, Guid.Empty); 347 if (result == false) 348 { 349 throw new InvalidOperationException(SR.InvalidOperation_RemoveFail); 350 } 351 352 break; 353 354 case AccessControlModification.RemoveSpecific: 355 //_securityDescriptor.DiscretionaryAcl.RemoveAccessSpecific(AccessControlType.Allow, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 356 _securityDescriptor.DiscretionaryAcl.RemoveAccessSpecific(AccessControlType.Allow, sid, rule); 357 break; 358 359 default: 360 throw new ArgumentOutOfRangeException( 361 nameof(modification), 362 SR.ArgumentOutOfRange_Enum); 363 } 364 } 365 else if (rule.AccessControlType == AccessControlType.Deny) 366 { 367 switch (modification) 368 { 369 case AccessControlModification.Add: 370 //_securityDescriptor.DiscretionaryAcl.AddAccess(AccessControlType.Deny, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 371 _securityDescriptor.DiscretionaryAcl.AddAccess(AccessControlType.Deny, sid, rule); 372 break; 373 374 case AccessControlModification.Set: 375 //_securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Deny, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 376 _securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Deny, sid, rule); 377 break; 378 379 case AccessControlModification.Reset: 380 _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Allow, sid, -1, InheritanceFlags.ContainerInherit, 0, ObjectAceFlags.None, Guid.Empty, Guid.Empty); 381 //_securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Deny, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 382 _securityDescriptor.DiscretionaryAcl.SetAccess(AccessControlType.Deny, sid, rule); 383 break; 384 385 case AccessControlModification.Remove: 386 //result = _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Deny, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 387 result = _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Deny, sid, rule); 388 break; 389 390 case AccessControlModification.RemoveAll: 391 result = _securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Deny, sid, -1, InheritanceFlags.ContainerInherit, 0, ObjectAceFlags.None, Guid.Empty, Guid.Empty); 392 if (result == false) 393 { 394 throw new InvalidOperationException(SR.InvalidOperation_RemoveFail); 395 } 396 397 break; 398 399 case AccessControlModification.RemoveSpecific: 400 //_securityDescriptor.DiscretionaryAcl.RemoveAccessSpecific(AccessControlType.Deny, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 401 _securityDescriptor.DiscretionaryAcl.RemoveAccessSpecific(AccessControlType.Deny, sid, rule); 402 break; 403 404 default: 405 throw new ArgumentOutOfRangeException( 406 nameof(modification), 407 SR.ArgumentOutOfRange_Enum); 408 } 409 } 410 else 411 { 412 throw new ArgumentException(SR.Format(SR.TypeUnrecognized_AccessControl, rule.AccessControlType)); 413 } 414 415 modified = result; 416 AccessRulesModified |= modified; 417 return result; 418 } 419 420 // 421 // Modifies the SACL 422 // ModifyAudit(AccessControlModification modification, ObjectAuditRule rule, out bool modified)423 private bool ModifyAudit(AccessControlModification modification, ObjectAuditRule rule, out bool modified) 424 { 425 bool result = true; 426 427 if (_securityDescriptor.SystemAcl == null) 428 { 429 if (modification == AccessControlModification.Remove || modification == AccessControlModification.RemoveAll || modification == AccessControlModification.RemoveSpecific) 430 { 431 modified = false; 432 return result; 433 } 434 435 //_securityDescriptor.SystemAcl = new SystemAcl(IsContainer, IsDS, GenericAcl.AclRevisionDS, 1); 436 //_securityDescriptor.AddControlFlags(ControlFlags.SystemAclPresent); 437 _securityDescriptor.AddSystemAcl(GenericAcl.AclRevisionDS, 1); 438 } 439 else if ((modification == AccessControlModification.Add || modification == AccessControlModification.Set || modification == AccessControlModification.Reset) && 440 (rule.ObjectFlags != ObjectAceFlags.None)) 441 { 442 // 443 // This will result in an object ace being added to the sacl, so the sacl revision must be AclRevisionDS 444 // 445 if (_securityDescriptor.SystemAcl.Revision < GenericAcl.AclRevisionDS) 446 { 447 // 448 // we need to create a new sacl with the same aces as the existing one but the revision should be AclRevisionDS 449 // 450 byte[] binaryForm = new byte[_securityDescriptor.SystemAcl.BinaryLength]; 451 _securityDescriptor.SystemAcl.GetBinaryForm(binaryForm, 0); 452 binaryForm[0] = GenericAcl.AclRevisionDS; // revision is the first byte of the binary form 453 454 _securityDescriptor.SystemAcl = new SystemAcl(IsContainer, IsDS, new RawAcl(binaryForm, 0)); 455 } 456 } 457 458 SecurityIdentifier sid = rule.IdentityReference.Translate(typeof(SecurityIdentifier)) as SecurityIdentifier; 459 460 switch (modification) 461 { 462 case AccessControlModification.Add: 463 //_securityDescriptor.SystemAcl.AddAudit(rule.AuditFlags, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 464 _securityDescriptor.SystemAcl.AddAudit(sid, rule); 465 break; 466 467 case AccessControlModification.Set: 468 //_securityDescriptor.SystemAcl.SetAudit(rule.AuditFlags, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 469 _securityDescriptor.SystemAcl.SetAudit(sid, rule); 470 break; 471 472 case AccessControlModification.Reset: 473 _securityDescriptor.SystemAcl.RemoveAudit(AuditFlags.Failure | AuditFlags.Success, sid, -1, InheritanceFlags.ContainerInherit, 0, ObjectAceFlags.None, Guid.Empty, Guid.Empty); 474 //_securityDescriptor.SystemAcl.SetAudit(rule.AuditFlags, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 475 _securityDescriptor.SystemAcl.SetAudit(sid, rule); 476 break; 477 478 case AccessControlModification.Remove: 479 //result = _securityDescriptor.SystemAcl.RemoveAudit(rule.AuditFlags, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 480 result = _securityDescriptor.SystemAcl.RemoveAudit(sid, rule); 481 break; 482 483 case AccessControlModification.RemoveAll: 484 result = _securityDescriptor.SystemAcl.RemoveAudit(AuditFlags.Failure | AuditFlags.Success, sid, -1, InheritanceFlags.ContainerInherit, 0, ObjectAceFlags.None, Guid.Empty, Guid.Empty); 485 if (result == false) 486 { 487 throw new InvalidOperationException(SR.InvalidOperation_RemoveFail); 488 } 489 490 break; 491 492 case AccessControlModification.RemoveSpecific: 493 //_securityDescriptor.SystemAcl.RemoveAuditSpecific(rule.AuditFlags, sid, rule.AccessMask, rule.InheritanceFlags, rule.PropagationFlags, rule.ObjectFlags, rule.ObjectType, rule.InheritedObjectType); 494 _securityDescriptor.SystemAcl.RemoveAuditSpecific(sid, rule); 495 break; 496 497 default: 498 throw new ArgumentOutOfRangeException( 499 nameof(modification), 500 SR.ArgumentOutOfRange_Enum); 501 } 502 503 modified = result; 504 AuditRulesModified |= modified; 505 return result; 506 } 507 508 #endregion 509 510 #region public Methods 511 AccessRuleFactory(IdentityReference identityReference, int accessMask, bool isInherited, InheritanceFlags inheritanceFlags, PropagationFlags propagationFlags, AccessControlType type, Guid objectType, Guid inheritedObjectType)512 public virtual AccessRule AccessRuleFactory(IdentityReference identityReference, int accessMask, bool isInherited, InheritanceFlags inheritanceFlags, PropagationFlags propagationFlags, AccessControlType type, Guid objectType, Guid inheritedObjectType) 513 { 514 throw NotImplemented.ByDesign; 515 } 516 AuditRuleFactory(IdentityReference identityReference, int accessMask, bool isInherited, InheritanceFlags inheritanceFlags, PropagationFlags propagationFlags, AuditFlags flags, Guid objectType, Guid inheritedObjectType)517 public virtual AuditRule AuditRuleFactory(IdentityReference identityReference, int accessMask, bool isInherited, InheritanceFlags inheritanceFlags, PropagationFlags propagationFlags, AuditFlags flags, Guid objectType, Guid inheritedObjectType) 518 { 519 throw NotImplemented.ByDesign; 520 } 521 ModifyAccess(AccessControlModification modification, AccessRule rule, out bool modified)522 protected override bool ModifyAccess(AccessControlModification modification, AccessRule rule, out bool modified) 523 { 524 ////if(this.AccessRuleType.IsAssignableFrom(rule.GetType().GetTypeInfo())) 525 ////if (!TypeExtensions.IsAssignableFrom(this.AccessRuleType, rule.GetType())) 526 //{ 527 // throw new ArgumentException( 528 // SR.AccessControl_InvalidAccessRuleType, 529 // "rule"); 530 //} 531 return ModifyAccess(modification, rule as ObjectAccessRule, out modified); 532 } 533 ModifyAudit(AccessControlModification modification, AuditRule rule, out bool modified)534 protected override bool ModifyAudit(AccessControlModification modification, AuditRule rule, out bool modified) 535 { 536 //if (this.AccessRuleType.IsAssignableFrom(rule.GetType().GetTypeInfo())) 537 ////if (!TypeExtensions.IsAssignableFrom(this.AuditRuleType, rule.GetType())) 538 //{ 539 // throw new ArgumentException( 540 // SR.AccessControl_InvalidAuditRuleType, 541 // "rule"); 542 //} 543 return ModifyAudit(modification, rule as ObjectAuditRule, out modified); 544 } 545 #endregion 546 547 #region Public Methods 548 AddAccessRule(ObjectAccessRule rule)549 protected void AddAccessRule(ObjectAccessRule rule) 550 { 551 if (rule == null) 552 { 553 throw new ArgumentNullException(nameof(rule)); 554 } 555 556 WriteLock(); 557 558 try 559 { 560 bool modified; 561 ModifyAccess(AccessControlModification.Add, rule, out modified); 562 } 563 finally 564 { 565 WriteUnlock(); 566 } 567 568 return; 569 } 570 SetAccessRule(ObjectAccessRule rule)571 protected void SetAccessRule(ObjectAccessRule rule) 572 { 573 if (rule == null) 574 { 575 throw new ArgumentNullException(nameof(rule)); 576 } 577 578 WriteLock(); 579 580 try 581 { 582 bool modified; 583 ModifyAccess(AccessControlModification.Set, rule, out modified); 584 } 585 finally 586 { 587 WriteUnlock(); 588 } 589 } 590 ResetAccessRule(ObjectAccessRule rule)591 protected void ResetAccessRule(ObjectAccessRule rule) 592 { 593 if (rule == null) 594 { 595 throw new ArgumentNullException(nameof(rule)); 596 } 597 598 WriteLock(); 599 600 try 601 { 602 bool modified; 603 ModifyAccess(AccessControlModification.Reset, rule, out modified); 604 } 605 finally 606 { 607 WriteUnlock(); 608 } 609 } 610 RemoveAccessRule(ObjectAccessRule rule)611 protected bool RemoveAccessRule(ObjectAccessRule rule) 612 { 613 if (rule == null) 614 { 615 throw new ArgumentNullException(nameof(rule)); 616 } 617 618 WriteLock(); 619 620 try 621 { 622 if (_securityDescriptor == null) 623 { 624 return true; 625 } 626 627 bool modified; 628 return ModifyAccess(AccessControlModification.Remove, rule, out modified); 629 } 630 finally 631 { 632 WriteUnlock(); 633 } 634 } 635 RemoveAccessRuleAll(ObjectAccessRule rule)636 protected void RemoveAccessRuleAll(ObjectAccessRule rule) 637 { 638 if (rule == null) 639 { 640 throw new ArgumentNullException(nameof(rule)); 641 } 642 643 WriteLock(); 644 645 try 646 { 647 if (_securityDescriptor == null) 648 { 649 return; 650 } 651 652 bool modified; 653 ModifyAccess(AccessControlModification.RemoveAll, rule, out modified); 654 } 655 finally 656 { 657 WriteUnlock(); 658 } 659 } 660 RemoveAccessRuleSpecific(ObjectAccessRule rule)661 protected void RemoveAccessRuleSpecific(ObjectAccessRule rule) 662 { 663 if (rule == null) 664 { 665 throw new ArgumentNullException(nameof(rule)); 666 } 667 668 if (_securityDescriptor == null) 669 { 670 return; 671 } 672 673 WriteLock(); 674 675 try 676 { 677 bool modified; 678 ModifyAccess(AccessControlModification.RemoveSpecific, rule, out modified); 679 } 680 finally 681 { 682 WriteUnlock(); 683 } 684 } 685 AddAuditRule(ObjectAuditRule rule)686 protected void AddAuditRule(ObjectAuditRule rule) 687 { 688 if (rule == null) 689 { 690 throw new ArgumentNullException(nameof(rule)); 691 } 692 693 WriteLock(); 694 695 try 696 { 697 bool modified; 698 ModifyAudit(AccessControlModification.Add, rule, out modified); 699 } 700 finally 701 { 702 WriteUnlock(); 703 } 704 } 705 SetAuditRule(ObjectAuditRule rule)706 protected void SetAuditRule(ObjectAuditRule rule) 707 { 708 if (rule == null) 709 { 710 throw new ArgumentNullException(nameof(rule)); 711 } 712 713 WriteLock(); 714 715 try 716 { 717 bool modified; 718 ModifyAudit(AccessControlModification.Set, rule, out modified); 719 } 720 finally 721 { 722 WriteUnlock(); 723 } 724 } 725 RemoveAuditRule(ObjectAuditRule rule)726 protected bool RemoveAuditRule(ObjectAuditRule rule) 727 { 728 if (rule == null) 729 { 730 throw new ArgumentNullException(nameof(rule)); 731 } 732 733 WriteLock(); 734 735 try 736 { 737 bool modified; 738 return ModifyAudit(AccessControlModification.Remove, rule, out modified); 739 } 740 finally 741 { 742 WriteUnlock(); 743 } 744 } 745 RemoveAuditRuleAll(ObjectAuditRule rule)746 protected void RemoveAuditRuleAll(ObjectAuditRule rule) 747 { 748 if (rule == null) 749 { 750 throw new ArgumentNullException(nameof(rule)); 751 } 752 753 WriteLock(); 754 755 try 756 { 757 bool modified; 758 ModifyAudit(AccessControlModification.RemoveAll, rule, out modified); 759 } 760 finally 761 { 762 WriteUnlock(); 763 } 764 } 765 RemoveAuditRuleSpecific(ObjectAuditRule rule)766 protected void RemoveAuditRuleSpecific(ObjectAuditRule rule) 767 { 768 if (rule == null) 769 { 770 throw new ArgumentNullException(nameof(rule)); 771 } 772 773 WriteLock(); 774 775 try 776 { 777 bool modified; 778 ModifyAudit(AccessControlModification.RemoveSpecific, rule, out modified); 779 } 780 finally 781 { 782 WriteUnlock(); 783 } 784 } 785 GetAccessRules(bool includeExplicit, bool includeInherited, System.Type targetType)786 public AuthorizationRuleCollection GetAccessRules(bool includeExplicit, bool includeInherited, System.Type targetType) 787 { 788 return GetRules(true, includeExplicit, includeInherited, targetType); 789 } 790 GetAuditRules(bool includeExplicit, bool includeInherited, System.Type targetType)791 public AuthorizationRuleCollection GetAuditRules(bool includeExplicit, bool includeInherited, System.Type targetType) 792 { 793 return GetRules(false, includeExplicit, includeInherited, targetType); 794 } 795 796 #endregion 797 } 798 } 799