How SIDs and Account Names Can Be Mapped in Windows

Updated: June 18, 2013

Applies To: Windows 7, Windows Server 2000, Windows Server 2003, Windows Server 2008, Windows Server 2008 R2, Windows Vista, Windows XP

Windows uses Security identifiers (SIDs) to control access to resources. A SID represents an account either in a local Security Accounts Manager (SAM) database or in Active Directory Domain Services (AD DS). In general, the SIDs of accounts should be kept in persistent storage and the SIDs should be converted to the account names for display. On the other hand, account names are often taken as input data and in order to store it in a Security Descriptor or similar storage, an application needs to retrieve the SID for the account.

SIDs can be mapped to account names in Windows in multiple ways. Each way has a different implementation and purpose in order to serve different scenarios. So you might prefer one approach over another.

Methods for mapping SIDs to account names

These are the methods available to map between SIDs and account names:

  • DsCrackNames/IADsNameTranslate

  • LsaLookupSids, LookupAccountSid

  • LsaLookupNames, LsaLookupNames2, LookupAccountName

  • LDAP queries for account names

  • LDAP queries for SIDs

DsCrackNames/IADsNameTranslate

MSDN references

Implementation

The API is implemented as an RPC call for the Active Directory replication RPC interface to the domain controller specified in the first parameter, and thus the success of the call is governed by the database scope of the domain controller. If the server is a global catalog, it can map all account names and SIDs in the forest, including SidHistory.

If an account name should be mapped to a SID, you can use multiple formats, such as object distinguished name (DN), Windows NT 4-style user name (domain\user), user principal name (UPN), or service principal name (SPN), and it will help if you can give a hint indicating what format the name is in (parameter formatOffered).

This function accepts and returns multiple name formats and also accepts and returns SID strings.

The ADSI-Counterpart IADsNameTranslate has a different usage methodology. For example, formatOffered is specified as an attribute of the name set on the object in the ADS_NAME_TYPE_ENUM enumerate type.

Security

The account is only mapped if the calling user is allowed to see the name and SID passed or requested.

Caching

There is no caching of the query results, positive or negative.

Scope

The search is done against the domain controller addressed by the first parameter; it does not extend beyond the domain controller addressed by the first parameter.

Logging

DsCrackNames has no logging capability, but LSA Policy logging is available in Windows 7 and Windows Server 2008 R2 for other methods that are discussed later in this topic.

LsaLookupSids, LookupAccountSid

MSDN references

Implementation

LookupAccountSid will call into LsaLookupSids with a single SID to resolve. So LsaLookupSids is covered in this section.

LSA on the computer that the call is sent to (using the LSA RPC interface) will resolve the SIDs it can map and send on the remaining unresolved SIDs to a domain controller in the primary domain. The domain controller will resolve additional SIDs to account names from the local database, including SIDs found in SidHistory on a global catalog.

If SIDs cannot be resolved there, the domain controller will send remaining SIDs to domain controllers in a trusted domain where the domain part of the SID matches the trust information.

Security

There is no access check that would require the caller to be able to read the SID or account name to perform the mapping. The domain administrator may however configure a policy that requires an authenticated RPC session with the server to make the mapping. All Windows operating systems beginning with Windows 2000 support performing authentication on these sessions by default. For more information, see article 942428 (https://go.microsoft.com/fwlink/?LinkId=181477) in the Microsoft Knowledge Base.

Caching

Successful mappings are cached on the computer that is addressed by the call. There is no negative cache.

Important

If the SID is found in SidHistory, the name-SID mapping is not added to the cache (in order to avoid cache pollution).

The cache parameters on Windows XP and later are in the following table.

Registry key: HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Lsa

Entry name Type Value Description

LsaLookupCacheRefreshTime

REG_DWORD

Time in Minutes (default 10)

Item is refreshed after LsaLookupCacheRefreshTime minutes if a new request for the cache item comes in.

LsaLookupCacheExpireTime

REG_DWORD

Time in Minutes (default 10080)

Item is removed after LsaLookupCacheExpireTime minutes from the cache.

LsaLookupCacheMaxSize

REG_DWORD

Number of entries

Number of entries in the name-SID cache.

Scope

The search begins at the computer that the API is called against, and extends to a domain controller in the primary domain, a global catalog server in the forest the domain controller is located in and to domain controllers that the primary domain has trusts with.

Logging

Windows Server 2008 introduces logging for LSA Policy and to some degree also LSA API logging (see details below). This can help with troubleshooting domain controller high load problems with excessive SID-Name mapping calls. Changes to the registry entries in this section are read dynamically. A reboot is not required to enable or disable logging.

To speed up the investigation around excessive LSA API calls on clients, you should set following registry keys:

HKLM\System\CurrentControlSet\Control\Lsa

  • LspDbgInfoLevel (REG_DWORD) TraceLevel values OR’ed

  • LspDbgTraceOptions (REG_DWORD) TraceOptions

TraceLevel values are in the following table.

  Name Value

TRACE_LEVEL_ALWAYS

0x80000000

TRACE_LEVEL_TRACE

0x40000000

TRACE_LEVEL_ERRORS

0x20000000

LSP information levels

TRACE_LEVEL_LSP_CORE_POLICY

0x20

TRACE_LEVEL_LSP_ACCOUNT

0x10000

TRACE_LEVEL_LSP_TRUSTED_DOMAIN

0x20000

TRACE_LEVEL_LSP_SECRET

0x40000

LSP operation levels

TRACE_LEVEL_LSP_DS_NOTIFY

0x200

TRACE_LEVEL_LSP_LOOKUP

Note

Windows Server 2008 R2 adds detailed logging of the LsaLookupSids and LsaLookupNames calls when using the TRACE_LEVEL_LSP_LOOKUP flag.

    <p></p>
  </div>
</td>
<td>
  <p>0x800</p>
</td>

TRACE_LEVEL_LSP_NT4_REPLICATION

0x8000

TRACE_LEVEL_LSP_SNMC

0x80000

TRACE_LEVEL_LSP_POLICY_NOTIFY

0x100000

TRACE_LEVEL_LSP_ENCRYPTION

0x200000

TRACE_LEVEL_LSP_IDENTITY_CACHE

0x400000

TraceOptions are in the following table

Name Value

TRACE_OPTION_NONE

0x0

TRACE_OPTION_LOG_TO_FILE

Note
When using TRACE_OPTION_LOG_TO_FILE, the log file is at %windir%\debug\lsp.log.

0x1

TRACE_OPTION_LOG_TO_KERNEL_DBG

0x2

LsaLookupNames, LsaLookupNames2, LookupAccountName

MSDN references

Implementation

LookupAccountName calls LsaLookupNames2 with a single name to resolve. LsaLookupNames and LsaLookupNames2 call into the same worker function.

Names can be either isolated (just “username”) or composite (“contoso\user_name”, “contoso.com\user_name” or “user_name@contoso.com”). Composite names are the simpler case as the name tells LSA where to look for the object that carries the SID. If the domain is not the primary domain or one of the trusted domains, the SID lookup for this name fails.

If the name is isolated, it has to be passed to all trusted domains unless this is restricted. For more information, see article 818024 (https://go.microsoft.com/fwlink/?LinkId=181265) in the Microsoft Knowledge Base

If the restriction is in place, the SID lookup fails, even if the name would be present in a trusted domain.

LSA on the computer that the call is sent to (using the LSA RPC interface) will resolve the names it can map and send on the remaining unresolved names to a domain controller in the primary domain. The domain controller will resolve additional account names to SIDs from the local database.

If an account name cannot be resolved there, the domain controller will send remaining SIDs to domain controllers in a trusted domain where the domain part of the SID matches the trust information.

When a name is not resolved yet, and it is isolated and LsaLookupRestrictIsolatedNameLevel is set to 0, the mapping request is forwarded to all trusted domains simultaneously. This can cause quite some load on domain controllers if many clients try to resolve isolated names to SIDs.

Note

If there are no trusts, there is no risk of overloading domain controllers. But as the number of trusts increases for any given domain or forest, then the risk of overloading domain controllers increases exponentially.
If you place resource servers in the same domain where all of the users are, you limit risk to almost zero for that set of resources. If you place resource servers in domain A, and all of your users are in domain B, you increase risk by a factor of the number of domains that need to be traversed to authenticate the user.
The following documents cover details about some of the same risks:

Security

There is no access check that would require the caller to be able to read the SID or account name to perform the mapping. The domain administrator may however configure a policy that requires an authenticated RPC session with the server to make the mapping. All Windows operating systems beginning with Windows 2000 support performing authentication on these sessions by default. For more information, see article 942428 (https://go.microsoft.com/fwlink/?LinkId=181477) in the Microsoft Knowledge Base.

Caching

Successful mappings are cached on the computer that is addressed by the call. There is no negative cache.

The cache is the same as in LsaLookupSids, LookupAccountSid on SID-to-Name resolution using LsaLookupSids.

Scope

The search begins at the computer the API is called against, and extends to a domain controller in the primary domain, a global catalog server in the forest that the domain controller is located in and to domain controllers that the primary domain has trusts with. If the name is an isolated name and LsaLookupRestrictIsolatedNameLevel is set to 0, the request is sent to all trusted domains.

LDAP queries for account names

MSDN references

There are multiple interfaces that can be used to issue LDAP queries:

  • C LDAP interface

  • Active Directory Service Interfaces (ADSI)

  • .NET System.DirectoryServices

In all interfaces, you can search for security principals using various search scopes (such as the whole database, or a whole naming context versus sub-OUs) and data sources (such as domain naming context versus global catalog).

Implementation

The Directory Service Agent serves LDAP queries against the database according to the rules implied by the LDAP directory server. The following are good attributes to filter for but this list is not exhaustive:

  • SamAccountName (append “$” to computer name)

  • UserPrincipalName (users only)

  • ServicePrincipalName (users and computers)

  • DisplayName

Security

The account is only mapped if the calling user is allowed to see the name and SID passed or requested.

Caching

There is no caching of the query results, positive or negative.

Scope

The search is done against the domain controller connected for the LDAP search.

LDAP queries for SIDs

MSDN references

There are multiple interfaces that can be used to issue LDAP queries:

  • C LDAP interface

  • Active Directory Service Interfaces (ADSI)

  • .NET System.DirectoryServices

In all interfaces, you can search for security principals using various search scopes (such as the whole database, or a whole naming context versus sub-OUs) and data sources (such as domain naming context versus global catalog).

Implementation

There are two attributes where SIDs are stored:

  • objectSid

  • SidHistory

If you already know that an account is in a certain domain, you can target a domain controller in the domain and search the domain naming context. If you suspect domain controllers in the domain are only reachable through slow links you can also target a global catalog server for the search and use the domain distinguished name (DN) as the base object for the search.

When you know that you are looking for a SID in objectSid and the domain the object is in, you can use this DN to address the object:

<SID=S-1-5-21-…>

This lookup only works for SIDs that are actually stored in the Active Directory database. Local accounts and generic accounts (such as S-1-1-0 for Everyone) cannot be resolved using this method.

Note

This method also does not work against the global catalog ports 3268 or 3269.

Otherwise, you can query for the SID in a regular LDAP query. Because the SIDs are stored in the LDAP database as binary data, you need to use the raw, little Endian format of the SID to search the directory. For example, the SID S-1-5-21-1417001333-412668190-1801674531-7125 translates to hexadecimal version S-1-5-15-5475B975-1898D11E-6B635F23-1BD5.

The raw storage for the SID is:

01 05 00 00 00 00 00 05 15 00 00 00 75 b9 75 54 1e d1 98 18 23 5f 63 6b d5 1b 00 00

If you look at the bytes and their ordering you see that, except the counter for the relative identifiers (RIDs), byte 4 through 7, the RIDs are the little- Endian byte-swapped DWORDs from the hexadecimal version of the SID.

Note

This is how LDP.exe exports the data in binary value parsing mode (in dialog invoked through Options\General).

In an LDAP filter, this values can be used like this:

(objectsid=\01\05\00\00\00\00\00\05\15\00\00\00\75\b9\75\54\1e\d1\98\18\23\5f\63\6b\d5\1b\00\00)

You can use this to search for primary SID and SidHistory on both the domain naming context and the global catalog.

Security

The account is only mapped if the calling user is allowed to see the name and SID passed or requested.

Caching

There is no caching of the query results, positive or negative.

Scope

The search is done against the domain controller connected for the LDAP search.