Определите имя учетной записи LocalSystem с помощью С#
У нас есть приложение, которое устанавливает SQL Server Express из командной строки и указывает учетную запись службы как учетную запись LocalSystem через параметр SQLACCOUNT = "NT AUTHORITY\SYSTEM".
Это не работает с разными языками, потому что имя учетной записи для LocalSystem отличается. Там таблица с перечислением различий здесь:
http://forums.microsoft.com/MSR/ShowPost.aspx?PostID=685354&SiteID=37
Это не кажется полным (шведская версия не указана). Поэтому я хотел бы иметь возможность определять имя программно, возможно, используя SID?
Я нашел несколько VB Script, чтобы сделать это:
Set objWMI = GetObject("winmgmts:root\cimv2")
Set objSid = objWMI.Get("Win32_SID.SID='S-1-5-18'")
MsgBox objSid.ReferencedDomainName & "\" & objSid.AccountName
Кто-нибудь знает эквивалентный код, который можно использовать в С#?
Ответы
Ответ 1
С этой целью вы можете использовать .NET-встроенный System.Security.Principal.SecurityIdentifier класс: переведя его в экземпляр NtAccount вы можете получить имя учетной записи:
using System.Security.Principal;
SecurityIdentifier sid = new SecurityIdentifier("S-1-5-18");
NTAccount acct = (NTAccount)sid.Translate(typeof(NTAccount));
Console.WriteLine(acct.Value);
Далее отредактируйте в ответ на вопрос в комментариях: вам не нужны специальные привилегии для поиска SID-имен на локальном компьютере - например, даже если учетная запись пользователя, на которой вы работаете, находится только в Группа гостей, этот код должен работать. Все немного отличается, если SID разрешает учетную запись домена, но даже в большинстве случаев это должно работать корректно, если вы вошли в домен (и контроллер домена доступен во время поиска).
Ответ 2
Или вы можете использовать:
string localSystem = new SecurityIdentifier(WellKnownSidType.LocalSystemSid, null).Translate(typeof(NTAccount)).Value;
С помощью WellKnownSidType
вы можете искать другие учетные записи, например NetworkService
.
Ответ 3
Это должно сделать что-то похожее на то, что вы разместили. Я не уверен, как получить конкретные свойства объектов WMI, но это поможет вам начать с синтаксиса:
ManagementObject m = new ManagementObject("winmgmts:root\cimv2");
m.Get();
MessageBox.Show(m["Win32_SID.SID='S-1-5-18'"].ToString());
Ответ 4
Проблема с принятым ответом заключается в том, что имя учетной записи должно быть разрешено локальным компьютером, на котором запущен код.
Если вы читаете списки ACL на удаленном компьютере, вы, возможно, не сможете разрешить SID/локальные SID домена в удаленном поле. Следующее использует WMI и принимает параметр удаленного компьютера и SID, который требуется удаленной машине.
/// <summary>
/// Returns the Account name for the specified SID
// using WMI against the specified remote machine
/// </summary>
private string RemoteSID2AccountName(String MachineName, String SIDString)
{
ManagementScope oScope = new ManagementScope(@"\\" + MachineName +
@"\root\cimv2");
ManagementPath oPath = new ManagementPath("Win32_SID.SID='" + SIDString + "'");
ManagementObject oObject = new ManagementObject(oScope, oPath, null);
return oObject["AccountName"].ToString();
}