6
我需要在C#中得到機器的SID(沒有計算機帳戶的SID)。計算機被指定爲主機名,它不一定是本地計算機,它可以是域計算機或工作組計算機。我使用這個助手類調用LookupAccountName API函數:GET機SID(包括主域控制器)
private static class Helper
{
internal enum SID_NAME_USE
{
SidTypeUser = 1,
SidTypeGroup,
SidTypeDomain,
SidTypeAlias,
SidTypeWellKnownGroup,
SidTypeDeletedAccount,
SidTypeInvalid,
SidTypeUnknown,
SidTypeComputer
}
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern bool LookupAccountName(
string systemName,
string accountName,
byte[] sid,
ref int sidLen,
System.Text.StringBuilder domainName,
ref int domainNameLen,
out SID_NAME_USE peUse);
public static SecurityIdentifier LookupAccountName(
string systemName,
string accountName,
out string strDomainName,
out SID_NAME_USE accountType)
{
const int ERROR_INSUFFICIENT_BUFFER = 122;
int lSidSize = 0;
int lDomainNameSize = 0;
//First get the required buffer sizes for SID and domain name.
LookupAccountName(systemName,
accountName,
null,
ref lSidSize,
null,
ref lDomainNameSize,
out accountType);
if (Marshal.GetLastWin32Error() == ERROR_INSUFFICIENT_BUFFER)
{
//Allocate the buffers with actual sizes that are required
//for SID and domain name.
byte[] sid = new byte[lSidSize];
var sbDomainName = new System.Text.StringBuilder(lDomainNameSize);
if (LookupAccountName(systemName,
accountName,
sid,
ref lSidSize,
sbDomainName,
ref lDomainNameSize,
out accountType))
{
strDomainName = sbDomainName.ToString();
return new SecurityIdentifier(sid, 0);
}
}
throw new Win32Exception();
}
}
,並使用它像這樣:
Helper.SID_NAME_USE accountType;
string refDomain;
SecurityIdentifier sid = Helper.LookupAccountName("falcon.mydomain.local", "falcon", out refDomain, out accountType); //Domain computer
SecurityIdentifier sid = Helper.LookupAccountName("rat", "rat", out refDomain, out accountType); //Workgroup computer
我唯一的問題是,這是行不通的,如果計算機是主域控制器(我需要在這種情況下獲得域SID)。