jspωiki
ObjectSID

Overview#

In Microsoft Active Directory the ObjectSID contains the value for the Security Identifier (SID) of the entry.

ObjectSID Trouble#

ObjectSID is painful to work with from LDAP.

The binary data is in the form:

  • byte(0) - - The revision level of the SID structure
  • byte(1) - count of sub-authorities
  • byte(2-7) - A 48-bit identifier authority value that identifies the authority that issued this SID (in Big-Endian format)
  • A variable number of Relative IDentifier (RID) values that uniquely identify the trustee relative to the authority that issued this SID

Then you end up with something like:
(1,5,0,0,0,0,0,5,21,0,0,0,37,-20,73,58,97,-107,0,-80,109,-55,112,10,47,-24,5,0) The last sub-authority of a SID is known as the Relative IDentifier (RID), and it is this RID that differentiates objects from within the same AD DOMAIN. This basically means that by replacing the RID in an SID you can generate the SID for a different object. The 'primaryGroupID' attribute from the 'user' class is a RID. So, we can take the SID of the user, and replace the RID part with the primaryGroupID, we can then lookup the group in LDAP using this SID as the key.

A binary SID can be decoded into a string, which is both easier to understand and can also be used for subsequent queries within Microsoft Active Directory LDAP. The specifics of the SID string format can be found here.

The string expression of a SID has the following format:
“S-{Revision}-{Authority}-{SubAuthority1}-{SubAuthority2}...-{SubAuthorityN}” or:
“S-1-5-21-977923109-2952828257-175163757-387119”

In Java you can do this with:

/**
* The String value is: S-Revision-Authority-SubAuthority[n]...
* 
* Based on code from here - http://forums.oracle.com/forums/thread.jspa?threadID=1155740&tstart=0
*/
public static String decodeSID(byte[] sid) {

    final StringBuilder strSid = new StringBuilder("S-");
    
    // get byte(0) - revision level
    final int revision = sid[0];
    strSid.append(Integer.toString(revision));
    
    //next byte byte(1) - count of sub-authorities
    final int countSubAuths = sid[1] & 0xFF;
    
    //byte(2-7) - 48 bit authority ([Big-Endian])
    long authority = 0;
    //String rid = "";
    for(int i = 2; i <= 7; i++) {
        authority |= ((long)sid[i]) << (8 * (5 - (i - 2)));
    }
    strSid.append("-");
    strSid.append(Long.toHexString(authority));
    
    //iterate all the sub-auths and then countSubAuths x 32 bit sub authorities ([Little-Endian])
    int offset = 8;
    int size = 4; //4 bytes for each sub auth
    for(int j = 0; j < countSubAuths; j++) {
        long subAuthority = 0;
        for(int k = 0; k < size; k++) {
            subAuthority |= (long)(sid[offset + k] & 0xFF) << (8 * k);
        }
        // format it
        strSid.append("-");
        strSid.append(subAuthority);
        offset += size;
    }
    return strSid.toString();    
}

LDAP Attribute Definition#

The ObjectSID AttributeTypes is defined as:

More Information#

There might be more information for this subject on one of the following: