# Lightweight Directory Access Protocol LDAP is an open- an cross-platform [[Protocol]] which provides means of communication between applications like [[Outlook]] and directory services like [[Active Directory]]. By default it is running on [[TCP]] [[Port|Ports]] `389` and `636` if you use the more secure varient which uses [[TLS]] LDAPS. A good example of LDAP would be Microsofts [[Active Directory]] (also called AD) which is relying on LDAP to function. Whenever a client performs a search an LDAP Query is utilized to query relevant objects and return the correct results. Microsoft [[Outlook]] for example is an LDAP-enabled windows program that sends queries automaticaly to get the information the user wants. Here are some statements that might help you understand better what LDAP is. ``` LDAP is a way of speaking to Active Directory. LDAP is a protocol that many different directory services and access management solutions can understand. The relationship between AD and LDAP is much like the relationship between Apache and HTTP: - HTTP is a web protocol. - Apache is a web server that uses the HTTP protocol. - LDAP is a directory services protocol. - Active Directory is a directory server that uses the LDAP protocol. Occasionally you’ll hear someone say, “We don’t have Active Directory, but we have LDAP.” What they probably mean is that they have another product, such as OpenLDAP, which is an LDAP server. It’s kind of like someone saying “We have HTTP” when they really meant “We have an Apache web server.” LDAP is a protocol, and Active Directory is a server. LDAP authenticates Active Directory – it’s a set of guidelines to send and receive information (like usernames and passwords) to Active Directory. ``` <button type="button">[[Active Directory]]</button> ## What does LDAP do? LDAPs primary functionality is to enable users to find data about organizations, persons, files and more. It does that by storing data in the LDAP directory (basically a database) and allowing authorized users to access the directory. Not only that but it also organizes objects in the directory such as users, computers and general organizational units. A popular way of implementing LDAP is to leave authentication to [[Kerberos]], see [[LDAP#Security|Security]] for more info. From my understanding the best course of action is leaving group-based authorization to LDAP and everything else to Kerberos since this protocol is more focused on security and will put less strain on the LDAP network. ## How does LDAP work? Basically the LDAP server which authenticates the clients and replies to the LDAP queries the clients send is directly connected to a database aka the LDAP directory. ### Directory Information Tree This directory has a hierarchy also called the **Directory Information Tree** (DIT) of all the entries inside. Here you can see a simple hierarchy. Each of the boxes is an entry. ![[LDAP - Hierarchy.png]] ### LDAP Entries and Attributes Each of the entries in the [[LDAP#Directory Information Tree|DIT]] has a distinguished name, a collection of attributes, and a collection of object classes. For example the entry for user John has the attribute `cn` (stands for common name) which has the value `John Doe`. This is called an `RDN` or a **relative distinguished name**. Every attribute can be found by it's `DN` or **distinguished name** which is a sequence of `RDNs`. For example here is the `DN` for Johns common name or `cn`: `CN=Jeff Smith,OU=Sales,DC=Fabrikam,DC=COM`. Here are some typical `RDN` attribute types | Acronym | Long Form | Explanation | Example | | ------- | ------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------- | -------- | | DC | Domain Component | I.e. if the [[Active Directory\|AD]] [[DNS]] name is company.com, there would be two domain components. One would be `Company` and the other `com`. | company | | c | Country | The entry is a country | DE | | o | Organization | The entry is an organzation | Corp | | ou | Organizational Unit | Most of the time this is a group in an organization | Sales | | uid | User ID | The ID of a user i.e. in an organizational uni | 1000 | | cn | Common Name | I.e. instead of using the uid this is the persons name | John Doe | >[!WARNING]+ DC can also mean Domain Controller A Domain Controller is in [[Active Directory|Active Directory's]] terminology a server that manages network and identity security. Here is how you would access an attribute with an LDAP [[URL]] ``` LDAP://HostName[:PortNumber][/DistinguishedName] ``` ### LDIF - LDAP Data Interchange Format LDIF is an [[ASCII]] format to exchange data and enable synchronazation between different LDAP servers. Here is an example of an LDIF file. ``` dn: o=burlesontech.com objectclass: top objectclass: organization o: burlesontech.com dn: ou=People, o=burlesontech.com objectclass: organizationalUnit ou: people dn: ou=marketing, o=burlesontech.com objectclass: organizationalUnit ou: marketing dn: cn=Cody Burleson, ou=people, o=burlesontech.com objectclass: top objectclass: organizationalPerson cn: Cody Burleson sn: Burleson givenname: Cody uid: cburleson ou: marketing ``` ## Accessing LDAP How do I access information on an LDAP server? Generally speaking it is pretty simple and all you need is connect with your credentials and start retrieving files. To do that I recommend the [[Python]] module [LDAP3](https://ldap3.readthedocs.io/en/latest/). Here you can see how to connect to a server. ``` >>> import ldap3 >>> server = ldap3.Server('<IP>', get_info = ldap3.ALL, port = <PORT>, use_ssl = True/False) >>> connection = ldap3.Connection(server) >>> connection.bind() True # If the response is true you can start enumerating the server >>> server.info DSA info (from DSE): Supported LDAP versions: 3 Naming contexts: dc=DOMAIN,dc=DOMAIN ``` You can use the `search_filter` argument in the `connection.search` function to specify what you are looking and to filter you results. See [here](https://ldap3.readthedocs.io/en/latest/searches.html) for documentation and [[LDAP#Hacking|here]] for examples. ## Security ### Authentication LDAP offers two main methods of [[Authentication]]: simple authentication and simple authentication secure layer ([[SASL]]). Alternatevly to help LDAP you can use the more secure [[Protocol]] [[Kerberos]]. Kerberos will *authenticate* users which later can be *authorized* by LDAP to access certain information. There is also Anonymous authentication and Unauthenticated Authentication which is for logging purposes only and should not grant access to a client. #### Simple Authentication Simple authentication is quite simple to use, all it requires is the client to send a fully qualified and distinguished name to the server along with a clear text password in what's called a bind request for authentication from the server. This is quite unsecure if implemented without an encrypted tunnel and can lead to attackers [[Snooping]] the traffic and capturing the credentials. #### Simple Authentication Secure Layer In short [[SASL]] is a [[Framework]] for Authentication and data security. It allows the authentication method to be decoupled from the application protocol, in our case LDAP. Depending on the application protocol used with SASL you can use protocols like [[TLS]] to encrypt the traffic sent. For more information please check the [[SASL]] note. #### Anonymous Authentication As an anonymous use you could have access to some LDAP resources. See [[LDAP#Accessing LDAP|here]] to find out how to do it. #### LDAP with Kerberos LDAP and Kerberos together make for a great combination. Kerberos is used to manage credentials securely ([[Authentication]]) while LDAP is used for holding authoritative information about the accounts, such as what they're allowed to access ([[Authorization]]), the user's full name and uid. To learn more, see the [[Kerberos]] note. ### Authorization LDAP offers a way to authorize users using group-based authorization. To do that the administrator has to assign users to specific groups which determine to which resources in the LDAP directory those users have access to. ## Hacking Generally having access to LDAP is very good since it allows the attacker to retrieve all kinds of information like passwords and usernames. This for example will retrieve all `userPassword` attributes of the `objectClass=person`. Basically dumping all the passwords of all users. (See [[LDAP#Accessing LDAP]] to know how to get here) ``` >> connection.search(search_base='DC=DOMAIN,DC=DOMAIN', search_filter='(&(objectClass=person))', search_scope='SUBTREE', attributes='userPassword') True >>> connection.entries ``` If you have valid credentials you can use [[LDAPDomainDump]] to dump all the information about the domain admin. ``` pip3 install ldapdomaindump ldapdomaindump <IP>/<HOSTNAME> -u '<domain>\<username>' -p '<password>' [--authtype SIMPLE] --no-json --no-grep [-o /path/dir] ``` You can also use [[LDAPSearch]] to search LDAP. Here is how to check if you can use null credentials aka as an [[LDAP#|Anonymous User]] followed by a situation where you have credentials. ``` ldapsearch -x -h <IP> -D '' -w '' -b "DC=<1_SUBDOMAIN>,DC=<TDL>" ldapsearch -x -h <IP> -D '<DOMAIN>\<username>' -w '<password>' -b "DC=<1_SUBDOMAIN>,DC=<TDL>" ``` >[!QUESTION]- What is DC? >Check [[LDAP#LDAP Entries and Attributes]] Here is how to extract Users, Enterprise Admins and Administrators. ``` Users: ldapsearch -x -h <IP> -D '<DOMAIN>\<username>' -w '<password>' -b "CN=Users,DC=<1_SUBDOMAIN>,DC=<TDL>" #Example: ldapsearch -x -h <IP> -D 'MYDOM\john' -w 'johnpassw' -b "CN=Users,DC=mydom,DC=local" Enterprise Admins: ldapsearch -x -h <IP> -D '<DOMAIN>\<username>' -w '<password>' -b "CN=Enterprise Admins,CN=Users,DC=<1_SUBDOMAIN>,DC=<TDL>" Adminstrators: ldapsearch -x -h <IP> -D '<DOMAIN>\<username>' -w '<password>' -b "CN=Administrators,CN=Builtin,DC=<1_SUBDOMAIN>,DC=<TDL>" ``` For more information and general help refer to: **[Hacktricks](https://book.hacktricks.xyz/pentesting/pentesting-ldap)** ### LAPS - Local Administrator Password Solution [[LAPS]] is a solution from microsoft to manage local account passwords. For more information see the [[LAPS]] note. Here is a quick [[Python]] script [LAPSDumper](https://github.com/n00py/LAPSDumper) that will retrieve LAPS passwords over LDAP. Here is the command to use it. ``` python laps.py -u user -p password[can be a hash too] -d domain.local ``` ## Useful Sources [Hacktricks](https://book.hacktricks.xyz/pentesting/pentesting-ldap) [Python LDAP3 Library](https://ldap3.readthedocs.io/en/latest/index.html) [Python LDAP3 Library - SEARCH operation](https://ldap3.readthedocs.io/en/latest/searches.html) [LDAP + Kerberos](https://wiki.debian.org/LDAP/Kerberos) [What is LDAP, Kerberos, Active Directory](https://social.technet.microsoft.com/Forums/en-US/cb6b05cc-3162-456d-a987-d113821fbdd6/difference-between-kerberos-and-ldap-in-active-directory?forum=winserverDS) [Entries, Attributes and Values](https://docs.oracle.com/cd/E19182-01/820-6573/6nht2e5a4/index.html) [Basic LDAP Concepts](https://ldap.com/basic-ldap-concepts/) [LDIF](https://www.techtarget.com/whatis/definition/LDIF-Lightweight-Directory-Interchange-Format) [Distinguished Names](https://docs.microsoft.com/en-us/previous-versions/windows/desktop/ldap/distinguished-names) [Directory Information Tree](https://ldapwiki.com/wiki/Directory%20Information%20Tree)