Accessing/parsing "msDS-AllowedToActOnBehalfOfOtherIdentity" AD 属性 在 C# 中

Accessing/parsing "msDS-AllowedToActOnBehalfOfOtherIdentity" AD property in C#

我需要在 C# 中管理 Kerberos Resource Based Delegation(我知道在 Powershell 中更容易,但这不是必需的)。 user/computer/service 帐户的属性是 msDS-AllowedToActOnBehalfOfOtherIdentity,但这似乎是一些 COM 对象,我似乎无法在 C#:

中处理
static void Main(string[] args)
{
    string ou = @"OU=some,OU=ou,DC=corp,DC=com";
    string cn = @"someaccount";

    DirectoryEntry de = new DirectoryEntry();

    de.Username = @"CORP\userwithOUrights";
    de.Password = @"password";
    de.AuthenticationType = AuthenticationTypes.Secure;
    de.Path = $"LDAP://CN={cn},{ou}";
    Object a = de.Properties["msDS-AllowedToActOnBehalfOfOtherIdentity"];
}

在此之后,a 与其他属性不同,我似乎无能为力。这是一些 COM 对象,我需要获取其中的帐户。 Powershell 报告说这个 属性 return 是一个 System.DirectoryServices.ActiveDirectorySecurity 对象,我在这个 class 中看到有用的方法来解码存储在 AD 等中的二进制格式。但是这似乎不是 C#.

中 属性 调用的 return 类型

更新: 所有这些现在都在我网站上的一篇文章中有更好的记录:Handling NT Security Descriptor attributes


根据 this the "attribute syntax" for that attribute is 2.5.5.15. According to this, that means it's a "String(NT-Sec-Desc)". According to this, that means it's a IADsSecurityDescriptor COM 对象。

您可以在您的项目中添加一个 COM 引用到 "Active DS Type library" 并将其直接转换为 IADsSecurityDescriptor,如下所示:

var act = (ActiveDs.IADsSecurityDescriptor)
              de.Properties["msDS-AllowedToActOnBehalfOfOtherIdentity"].Value;
Console.WriteLine(act.Owner);

Owner 属性 给你一个 DOMAIN\Username.

根据 this random code I found, it seems you can also use the RawSecurityDescriptor class to interact with it. There is a constructor that takes a plain string,但您似乎也无法从 DirectoryEntry 的属性中获取原始字符串。

但我确实记得有时 DirectorySearcher 会为您提供与 DirectoryEntry 不同类型的值(没有意义,但这是事实)。这似乎是真的。 DirectorySearcher 将此属性作为 byte[] 提供给您,并且 RawSecurityDescriptor 是否具有 a constructor that takes a byte[].

看来你可以这样做:

string ou = @"OU=some,OU=ou,DC=corp,DC=com";
string cn = @"someaccount";

var search = new DirectorySearcher(new DirectoryEntry($"LDAP://{ou}"), $"(cn={cn})");
search.PropertiesToLoad.Add("msDS-AllowedToActOnBehalfOfOtherIdentity");

var result = search.FindOne();

var act = new RawSecurityDescriptor(
    (byte[]) result.Properties["msDS-AllowedToActOnBehalfOfOtherIdentity"][0], 0);

Console.WriteLine(act.Owner);

//make changes to act.DiscretionaryAcl

byte[] descriptor_buffer = new byte[act.BinaryLength];
act.GetBinaryForm(descriptor_buffer, 0);

var de = result.GetDirectoryEntry();
de.Properties["msDS-AllowedToActOnBehalfOfOtherIdentity"].Value = descriptor_buffer;
de.CommitChanges();

这里,act.Owner是一个账号SID。