Wednesday, 9 September 2015

Convert SID to Username using C#

In C#, we can use the P-Invoke function LookupAccountSid to resolve user name from sid and we can also use the C# .NET class SecurityIdentifier to translate security identifier (SID) to user name and use NTAccount class to translate user name to security identifier (SID).

Summary:

Convert SID to Username using P-Invoke:

The below C# code resolve user name from security identifier (SID).
const int NO_ERROR = 0;
const int ERROR_INSUFFICIENT_BUFFER = 122;

enum SID_NAME_USE
{
    SidTypeUser = 1,
    SidTypeGroup,
    SidTypeDomain,
    SidTypeAlias,
    SidTypeWellKnownGroup,
    SidTypeDeletedAccount,
    SidTypeInvalid,
    SidTypeUnknown,
    SidTypeComputer
}

[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
static extern bool LookupAccountSid(
    string lpSystemName, [MarshalAs(UnmanagedType.LPArray)] byte[] Sid, StringBuilder lpName,
    ref uint cchName, StringBuilder ReferencedDomainName, ref uint cchReferencedDomainName, out SID_NAME_USE peUse);

static void Main(string[] args)
{
    // Sid for BUILTIN\Administrators
    GetUsernameFromSID("S-1-5-21-745457877-148782331-813991262-500");
}

private static void GetUsernameFromSID(string strSid)
{
    StringBuilder name = new StringBuilder();
    uint cchName = (uint)name.Capacity;
    StringBuilder referencedDomainName = new StringBuilder();
    uint cchReferencedDomainName = (uint)referencedDomainName.Capacity;
    SID_NAME_USE sidUse;

    var sid = new SecurityIdentifier(strSid);
    byte[] byteSid = new byte[sid.BinaryLength];
    sid.GetBinaryForm(byteSid, 0);

    int err = NO_ERROR;
    if (!LookupAccountSid(null, byteSid, name, ref cchName, referencedDomainName, ref cchReferencedDomainName, out sidUse))
    {
        err = System.Runtime.InteropServices.Marshal.GetLastWin32Error();
        if (err == ERROR_INSUFFICIENT_BUFFER)
        {
            name.EnsureCapacity((int)cchName);
            referencedDomainName.EnsureCapacity((int)cchReferencedDomainName);
            err = NO_ERROR;
            if (!LookupAccountSid(null, byteSid, name, ref cchName, referencedDomainName, ref cchReferencedDomainName, out sidUse))
                err = System.Runtime.InteropServices.Marshal.GetLastWin32Error();
        }
    }
    if (err == 0)
        Console.WriteLine(@"Found account {0} : {1}\{2}", sidUse, referencedDomainName.ToString(), name.ToString());
    else
        Console.WriteLine(@"Error : {0}", err);
}

Convert SID to Username using SecurityIdentifier:

The below C# code translate security identifier (SID) to username using SecurityIdentifier class.
private static void GetUsernameFromSID(string sid)
{
    SecurityIdentifier s = new SecurityIdentifier(sid);
    string username = s.Translate(typeof(NTAccount)).Value;
    Console.WriteLine(username);
}

Convert Username to SID using NTAccount:

The below C# code translate user account to SID using NTAccount class.
private static void GetSIDFromUsername(string username)
{
    NTAccount ntAcc = new NTAccount(username);
    string objectsid = ntAcc.Translate(typeof(SecurityIdentifier)).Value;
    Console.WriteLine(objectsid);
}

Advertisements
Advertisements

No comments:

Post a Comment