2016-08-15 2 views
1

Итак, я пытаюсь получить список ACE из определенного подразделения. Я узнал о классе правил ActiveDirectoryAccess.Правила доступа к Active Directory не так специфичны, как dsacls

Приводимые от выхода не кажется, быть как на выходе из команды DSACLs (https://technet.microsoft.com/en-us/library/cc771151%28v=ws.11%29.aspx?f=255&MSPPError=-2147217396)

Как я могу сделать мой C# код получить более описательные результаты, аналогичные DSACLs? (Лучше отображаемое_имя)

Вот подмножество выходных результатов из моего теста

Domain\myGroup 
Inherits - Descendents 
ObjectType - 00299570-246d-11d0-a768-00aa006e0529 
InheritedObjectType - bf967aba-0de6-11d0-a285-00aa003049e2 
ObjectFlags - ObjectAceTypePresent, InheritedObjectAceTypePresent 
AccessControlType - Allow 
ActiveDirectoryRights - ExtendedRight 
IsInherited - True 
PropagationFlags - InheritOnly 
------- 
Domain\myGroup 
Inherits - Descendents 
ObjectType - bf967a0a-0de6-11d0-a285-00aa003049e2 
InheritedObjectType - bf967aba-0de6-11d0-a285-00aa003049e2 
ObjectFlags - ObjectAceTypePresent, InheritedObjectAceTypePresent 
AccessControlType - Allow 
ActiveDirectoryRights - ReadProperty, WriteProperty 
IsInherited - True 
PropagationFlags - InheritOnly 
------- 
Domain\myGroup 
Inherits - Descendents 
ObjectType - 28630ebf-41d5-11d1-a9c1-0000f80367c1 
InheritedObjectType - bf967aba-0de6-11d0-a285-00aa003049e2 
ObjectFlags - ObjectAceTypePresent, InheritedObjectAceTypePresent 
AccessControlType - Allow 
ActiveDirectoryRights - ReadProperty, WriteProperty 
IsInherited - True 
PropagationFlags - InheritOnly 

Вот выход из DSACLS

Allow Domain\myGroup   Reset Password <Inherited from parent> 
Allow Domain\myGroup   SPECIAL ACCESS for lockoutTime <Inherited from parent> 
             WRITE PROPERTY 
             READ PROPERTY 
Allow Domain\myGroup     SPECIAL ACCESS for pwdLastSet <Inherited from parent> 
             WRITE PROPERTY 
             READ PROPERTY 

Глядя на некоторые из кодов OBJECTTYPE по LDAP: // сп = Расширенные-права, CN = Configuration, DC = MYDOMAIN

Я могу сказать, что 00299570-246d-11d0-a768-00aa006e0529 карты Сбросить пароль , но я не могу найти соответствие для - 28630ebf-41d5-11d1-a9c1-0000f80367c1 или bf967a0a-0de6-11d0-a285-00aa003049e2

код, чтобы получить мой вывод ACE конкретного подразделения.

[Test] 
     public void ForStackOverflow() 
     { 
      var cfg = new DirectoryEntry("LDAP://PathToMyOU"); 
      var cfgsearch = new DirectorySearcher(cfg); 

      cfgsearch.Filter = "(name=*)"; 
      cfgsearch.PropertiesToLoad.Add("distinguishedName"); 
      cfgsearch.SearchScope = SearchScope.Subtree; 


      var res = cfgsearch.FindAll(); 

      var ouDE = res[0].GetDirectoryEntry(); 

      var accessRules = ouDE.ObjectSecurity.GetAccessRules(true, true, typeof(NTAccount)); 

      foreach (ActiveDirectoryAccessRule ar in accessRules) 
      { 
       Console.WriteLine($"{ar.IdentityReference.ToString()}"); 
       Console.WriteLine($"Inherits - {ar.InheritanceType.ToString()}"); 
       Console.WriteLine($"ObjectType - {ar.ObjectType.ToString()}"); 
       Console.WriteLine($"InheritedObjectType - {ar.InheritedObjectType.ToString()}"); 
       Console.WriteLine($"ObjectFlags - {ar.ObjectFlags.ToString()}"); 
       Console.WriteLine($"AccessControlType - {ar.AccessControlType.ToString()}"); 
       Console.WriteLine($"ActiveDirectoryRights - {ar.ActiveDirectoryRights.ToString()}"); 


       Console.WriteLine($"IsInherited - {ar.IsInherited.ToString()}"); 
       Console.WriteLine($"PropagationFlags - {ar.PropagationFlags.ToString()}"); 
       Console.WriteLine("-------"); 
      } 
     } 

код я использовал, чтобы получить некоторые из объекта Guid DisplayName

[Test] 
public void ForStackOverflowAllExtendedRights() 
{ 
    DirectoryEntry rootdse = new DirectoryEntry("LDAP://RootDSE"); 
    DirectoryEntry cfg = new DirectoryEntry("LDAP://" + rootdse.Properties["configurationnamingcontext"].Value); 
    DirectoryEntry exRights = new DirectoryEntry("LDAP://cn=Extended-rights," + rootdse.Properties["configurationnamingcontext"].Value); 
    Hashtable exRighthash = new Hashtable(); 

    foreach (DirectoryEntry chent in exRights.Children) 
    { 
     if (chent.Properties["rightsGuid"].Value != null && !exRighthash.ContainsKey(chent.Properties["rightsGuid"].Value)) 
     { 
      exRighthash.Add(chent.Properties["rightsGuid"].Value, chent.Properties["DisplayName"].Value); 
      Console.WriteLine($"{chent.Properties["rightsGuid"].Value}, {chent.Properties["DisplayName"].Value}"); 
     } 
    } 
} 

Update # 1 мне удалось найти код надрезается (из этой книги https://www.amazon.com/s/?url=search-alias=stripbooks&field-keywords=0321350170&tag=technicalibra-20&link_code=wql&camp=212361&creative=380601&_encoding=UTF-8) , чтобы проверить, какой тип учетной записи затрагивается.

Теперь я немного ближе. Некоторые из этих терминов не совпадают (например, сброс пароля в User-Force-Change-Password), а некоторые из них не отображаются

Вот результаты для моего предыдущего примера.

Identity: Domain\Mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: ExtendedRight 
    InheritanceType: Descendents 
    ObjectType: 00299570-246d-11d0-a768-00aa006e0529 
    InheritedObjectType: bf967aba-0de6-11d0-a285-00aa003049e2 
ObjectFlags: ObjectAceTypePresent, InheritedObjectAceTypePresent 
{00299570-246d-11d0-a768-00aa006e0529}= 
{00299570-246d-11d0-a768-00aa006e0529}=User-Force-Change-Password 

    Identity: Domain\Mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: ReadProperty, WriteProperty 
    InheritanceType: Descendents 
    ObjectType: bf967a0a-0de6-11d0-a285-00aa003049e2 
    InheritedObjectType: bf967aba-0de6-11d0-a285-00aa003049e2 
ObjectFlags: ObjectAceTypePresent, InheritedObjectAceTypePresent 
{bf967a0a-0de6-11d0-a285-00aa003049e2}=pwdLastSet 
{bf967a0a-0de6-11d0-a285-00aa003049e2}= 

    Identity: Domain\Mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: ReadProperty, WriteProperty 
    InheritanceType: Descendents 
    ObjectType: 28630ebf-41d5-11d1-a9c1-0000f80367c1 
    InheritedObjectType: bf967aba-0de6-11d0-a285-00aa003049e2 
ObjectFlags: ObjectAceTypePresent, InheritedObjectAceTypePresent 
{28630ebf-41d5-11d1-a9c1-0000f80367c1}=lockoutTime 
{28630ebf-41d5-11d1-a9c1-0000f80367c1}= 

Новый тест

[Test] 
     public void ForStackOverflow() 
     { 
      var cfg = new DirectoryEntry("LDAP://OU=CountryTestSync,OU=EDS,DC=d,DC=r,DC=dfait-maeci,DC=gc,DC=ca"); 
      var cfgsearch = new DirectorySearcher(cfg); 

      cfgsearch.Filter = "(name=*)"; 
      cfgsearch.PropertiesToLoad.Add("distinguishedName"); 
      cfgsearch.SearchScope = SearchScope.Subtree; 


      var res = cfgsearch.FindAll(); 

      var ouDE = res[0].GetDirectoryEntry(); 

      var accessRules = ouDE.ObjectSecurity.GetAccessRules(true, true, typeof(NTAccount)); 

      SchemaGuidConversion.PrintSD(ouDE.ObjectSecurity); 

      string extendedRightsDN = "CN=Extended-Rights,"; 
      string schemaAtt = "schemaNamingContext"; 
      string configAtt = "configurationNamingContext"; 
      Guid samGuid = new Guid("3e0abfd0-126a-11d0-a060-00aa006c33ed"); 

      var rootDse = new DirectoryEntry("LDAP://rootDSE"); 
      var schemaDN = rootDse.Properties[schemaAtt].Value.ToString(); 
      extendedRightsDN += rootDse.Properties[configAtt].Value.ToString(); 

      var schemaRoot = new DirectoryEntry("LDAP://" + schemaDN); 
      var extendedRightsRoot = new DirectoryEntry("LDAP://" + extendedRightsDN); 

      foreach (ActiveDirectoryAccessRule ar in accessRules) 
      { 
       SchemaGuidConversion.PrintAce(ar); 
       Console.WriteLine("{0}={1}", ar.ObjectType.ToString("B"), SchemaGuidConversion.GetNameForSchemaGuid(ar.ObjectType, schemaRoot)); 
       Console.WriteLine("{0}={1}", ar.ObjectType.ToString("B"), SchemaGuidConversion.GetNameForRightsGuid(ar.ObjectType, extendedRightsRoot)); 
      } 


      if (rootDse != null) 
      { 
       rootDse.Dispose(); 
      } 

      if (schemaRoot != null) 
      { 
       schemaRoot.Dispose(); 
      } 

     } 

класса, чтобы получить информацию

public class SchemaGuidConversion 
    { 
     public static void PrintAce(ActiveDirectoryAccessRule rule) 
     { 
      Console.WriteLine("=====ACE====="); 
      Console.Write(" Identity: "); 
      Console.WriteLine(rule.IdentityReference.ToString()); 
      Console.Write(" AccessControlType: "); 
      Console.WriteLine(rule.AccessControlType.ToString()); 
      Console.Write("  ActiveDirectoryRights: "); 
      Console.WriteLine(    rule.ActiveDirectoryRights.ToString()); 
      Console.Write(" InheritanceType: "); 
      Console.WriteLine(rule.InheritanceType.ToString()); 
      Console.Write("  ObjectType: "); 
      if (rule.ObjectType == Guid.Empty) 
      { 
       Console.WriteLine("<null>"); 
      } 
      else 
      { 
       Console.WriteLine(rule.ObjectType.ToString()); 
      } 

      Console.Write("  InheritedObjectType: "); 
      if (rule.InheritedObjectType == Guid.Empty) 
      { 
       Console.WriteLine("<null>"); 
      } 
      else 
      { 
       Console.WriteLine(     rule.InheritedObjectType.ToString()); 
      } 

      Console.Write(" ObjectFlags: "); 
      Console.WriteLine(rule.ObjectFlags.ToString()); 
     } 

     public static void PrintSD(ActiveDirectorySecurity sd) 
     { 
      Console.WriteLine("=====Security Descriptor====="); 
      Console.Write(" Owner: "); 
      Console.WriteLine(sd.GetOwner(typeof(NTAccount))); 
      Console.Write(" Group: "); 
      Console.WriteLine(sd.GetGroup(typeof(NTAccount))); 
     } 

     public static string GetNameForRightsGuid(Guid rightsGuid, DirectoryEntry extendedRightsRoot) 
     { 
      string filter = $"(rightsGuid={rightsGuid.ToString("D")})"; 
      return GetNameForGuid(filter, "cn", extendedRightsRoot); 
     } 

     public static string GetNameForSchemaGuid(Guid schemaIDGuid, DirectoryEntry schemaRoot) 
     { 
      string filter = $"(schemaIDGUID={BuildFilterOctetString(schemaIDGuid.ToByteArray())})"; 
      return GetNameForGuid(filter, "ldapDisplayName", schemaRoot); 
     } 

     public static string GetNameForGuid(string filter, string targetAttribute, DirectoryEntry searchRoot) 
     { 
      string attributeName = null; 
      var searcher = new DirectorySearcher(searchRoot); 
      searcher.SearchScope = SearchScope.OneLevel; 
      searcher.PropertiesToLoad.Add(targetAttribute); 
      searcher.Filter = filter; 

      using (searcher) 
      { 
       var result = searcher.FindOne(); 

       if (result != null) 
       { 
        attributeName = result.Properties[targetAttribute][0].ToString(); 
       } 
      } 

      return attributeName; 
     } 

     public static Guid GetRightsGuid(string rightsName, DirectoryEntry extendedRightsRoot) 
     { 
      return GetGuidForName("cn", rightsName, "rightsGuid", extendedRightsRoot); 
     } 

     public static Guid GetSchemaIDGuid(string ldapDisplayName, DirectoryEntry schemaRoot) 
     { 
      return GetGuidForName("ldapDisplayName", ldapDisplayName, "schemaIDGUID", schemaRoot); 
     } 

     private static Guid GetGuidForName(string attributeName, string attributeValue, string targetAttribute, DirectoryEntry root) 
     { 
      Guid targetGuid = Guid.Empty; 
      SearchResult result; 
      object guidValue; 
      DirectorySearcher searcher = new DirectorySearcher(root); 
      searcher.SearchScope = SearchScope.OneLevel; 
      searcher.PropertiesToLoad.Add(targetAttribute); 
      searcher.Filter = $"({attributeName}={attributeValue})"; 

      using (searcher) 
      { 
       result = searcher.FindOne(); 

       if (result != null) 
       { 
        guidValue = result.Properties[targetAttribute][0]; 
        if (guidValue is string) 
        { 
         targetGuid = new Guid((string)guidValue); 
        } 
        else 
        { 
         targetGuid = new Guid((byte[])guidValue); 
        } 
       } 
      } 

      return targetGuid; 
     } 

     public static string BuildFilterOctetString(byte[] bytes) 
     { 
      StringBuilder sb = new StringBuilder(); 

      for (int i = 0; i < bytes.Length; i++) 
      { 
       sb.AppendFormat("\\{0}", bytes[i].ToString("X2")); 
      } 

      return sb.ToString(); 
     } 
    } 

Update 2

Вот пример другого элемента, который отличается

=====ACE===== 
    Identity: domain/mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: CreateChild, DeleteChild 
    InheritanceType: All 
    ObjectType: bf967aba-0de6-11d0-a285-00aa003049e2 
    InheritedObjectType: <null> 
ObjectFlags: ObjectAceTypePresent 
{bf967aba-0de6-11d0-a285-00aa003049e2}=user 
{bf967aba-0de6-11d0-a285-00aa003049e2}= 
=====ACE===== 
    Identity: domain/mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: ReadProperty, WriteProperty 
    InheritanceType: All 
    ObjectType: f30e3bbe-9ff0-11d1-b603-0000f80367c1 
    InheritedObjectType: <null> 
ObjectFlags: ObjectAceTypePresent 
{f30e3bbe-9ff0-11d1-b603-0000f80367c1}=gPLink 
{f30e3bbe-9ff0-11d1-b603-0000f80367c1}= 
=====ACE===== 
    Identity: domain/mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: ReadProperty, WriteProperty 
    InheritanceType: All 
    ObjectType: f30e3bbf-9ff0-11d1-b603-0000f80367c1 
    InheritedObjectType: <null> 
ObjectFlags: ObjectAceTypePresent 
{f30e3bbf-9ff0-11d1-b603-0000f80367c1}=gPOptions 
{f30e3bbf-9ff0-11d1-b603-0000f80367c1}= 
=====ACE===== 
    Identity: domain/mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: GenericAll 
    InheritanceType: Descendents 
    ObjectType: <null> 
    InheritedObjectType: bf967a9c-0de6-11d0-a285-00aa003049e2 
ObjectFlags: InheritedObjectAceTypePresent 
{00000000-0000-0000-0000-000000000000}= 
{00000000-0000-0000-0000-000000000000}= 
=====ACE===== 
    Identity: domain/mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: GenericAll 
    InheritanceType: Descendents 
    ObjectType: <null> 
    InheritedObjectType: bf967aba-0de6-11d0-a285-00aa003049e2 
ObjectFlags: InheritedObjectAceTypePresent 
{00000000-0000-0000-0000-000000000000}= 
{00000000-0000-0000-0000-000000000000}= 
=====ACE===== 
    Identity: domain/mygroup 
    AccessControlType: Allow 
    ActiveDirectoryRights: ReadProperty, GenericExecute 
    InheritanceType: All 
    ObjectType: <null> 
    InheritedObjectType: <null> 
ObjectFlags: None 
{00000000-0000-0000-0000-000000000000}= 
{00000000-0000-0000-0000-000000000000}= 

Вот запись dsacls. Я могу получить соответствующую запись сверху, но я не уверен в FULL Control или Содержание записей ниже.

Allow Domain\mygroup    SPECIAL ACCESS <Inherited from parent> 
             READ PERMISSONS 
             LIST CONTENTS 
             READ PROPERTY 

Allow Domain\mygroup    SPECIAL ACCESS for group <Inherited from parent> 
             CREATE CHILD 
             DELETE CHILD 

Allow Domain\mygroup    SPECIAL ACCESS for user <Inherited from parent> 
             CREATE CHILD 
             DELETE CHILD 

Allow Domain\mygroup    SPECIAL ACCESS for gPLink <Inherited from parent> 
             WRITE PROPERTY 
             READ PROPERTY 

Allow Domain\mygroup    SPECIAL ACCESS for gPOptions <Inherited from parent> 
             WRITE PROPERTY 
             READ PROPERTY 

Inherited to all subobjects 
Allow Domain\mygroup    SPECIAL ACCESS <Inherited from parent> 
             READ PERMISSONS 
             LIST CONTENTS 
             READ PROPERTY 

Allow Domain\mygroup    SPECIAL ACCESS for group <Inherited from parent> 
             CREATE CHILD 
             DELETE CHILD 

Allow Domain\mygroup    SPECIAL ACCESS for user <Inherited from parent> 
             CREATE CHILD 
             DELETE CHILD 

Allow Domain\mygroup    SPECIAL ACCESS for gPLink <Inherited from parent> 
             WRITE PROPERTY 
             READ PROPERTY 

Allow Domain\mygroup    SPECIAL ACCESS for gPOptions <Inherited from parent> 
             WRITE PROPERTY 

Allow Domain\mygroup    FULL CONTROL <Inherited from parent> 
Inherited to group 
Allow Domain\mygroup    FULL CONTROL <Inherited from parent> 
Inherited to user 
             READ PROPERTY 
+0

Это очень полезная информация. Вы забыли одну вещь, но на самом деле вы никогда не задавали вопрос. – Kevin

+0

Done, я отредактировал вопрос и поставил вопрос. – Lareau

ответ

1

Некоторые термины не совпадают (например, сброс пароля для пользователя-Force-Change-Password) и некоторые из них не появляются

Вы хотите, чтобы захватить displayName атрибут, а не CN для протяженных объектов прав:

public static string GetNameForRightsGuid(Guid rightsGuid, DirectoryEntry extendedRightsRoot) 
{ 
    string filter = $"(rightsGuid={rightsGuid.ToString("D")})"; 
    return GetNameForGuid(filter, "displayName", extendedRightsRoot); 
} 

в вашем примере, что приведет к «Сброс пароля»

+0

Удивительный! любая идея, как получить «Полный контроль»? Это эквивалент GenericAll – Lareau

+0

@Lareau Да, «GenericAll» - это термин 'System.DirectoryServices' для« Полный контроль » –

+0

Снова потрясающий! Что относительно содержимого списка? Относится ли это к GenericExecute? – Lareau