-
Notifications
You must be signed in to change notification settings - Fork 9
/
rdp_scanner.rb
103 lines (89 loc) · 3.06 KB
/
rdp_scanner.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
##
# This module requires Metasploit: https://metasploit.com/download
# Current source: https://github.com/rapid7/metasploit-framework
##
class MetasploitModule < Msf::Auxiliary
include Msf::Exploit::Remote::RDP
include Msf::Auxiliary::Scanner
include Msf::Auxiliary::Report
def initialize(info = {})
super(
update_info(
info,
'Name' => 'Identify endpoints speaking the Remote Desktop Protocol (RDP)',
'Description' => %q(
This module attempts to connect to the specified Remote Desktop Protocol port
and determines if it speaks RDP.
When available, the Credential Security Support Provider (CredSSP) protocol will be used to identify the
version of Windows on which the server is running. Enabling the DETECT_NLA option will cause a second
connection to be made to the server to identify if Network Level Authentication (NLA) is required.
),
'Author' => 'Jon Hart <jon_hart[at]rapid7.com>',
'References' =>
[
['URL', 'https://msdn.microsoft.com/en-us/library/cc240445.aspx']
],
'License' => MSF_LICENSE
)
)
register_options(
[
Opt::RPORT(3389),
OptBool.new('DETECT_NLA', [true, 'Detect Network Level Authentication (NLA)', true])
]
)
end
def check_rdp
begin
rdp_connect
is_rdp, version_info = rdp_fingerprint
rescue ::Errno::ETIMEDOUT, Rex::HostUnreachable, Rex::ConnectionTimeout, Rex::ConnectionRefused, ::Timeout::Error, ::EOFError
return false, nil
ensure
rdp_disconnect
end
service_info = nil
if is_rdp
product_version = (version_info && version_info[:product_version]) ? version_info[:product_version] : 'N/A'
info = "Detected RDP on #{peer} (Windows version: #{product_version})"
if datastore['DETECT_NLA']
service_info = "Requires NLA: #{(!version_info[:product_version].nil? && requires_nla?) ? 'Yes' : 'No'}"
info << " (#{service_info})"
end
print_status(info)
end
return is_rdp, service_info
end
def requires_nla?
begin
rdp_connect
is_rdp, server_selected_proto = rdp_check_protocol
rescue ::Errno::ETIMEDOUT, Rex::HostUnreachable, Rex::ConnectionTimeout, Rex::ConnectionRefused, ::Timeout::Error, ::EOFError
return false
ensure
rdp_disconnect
end
return false unless is_rdp
return [RDPConstants::PROTOCOL_HYBRID, RDPConstants::PROTOCOL_HYBRID_EX].include? server_selected_proto
end
def run_host(_ip)
is_rdp = false
begin
rdp_connect
is_rdp, service_info = check_rdp
rescue Rex::ConnectionError => e
vprint_error("Error while connecting and negotiating RDP: #{e}")
return
ensure
rdp_disconnect
end
return unless is_rdp
report_service(
host: rhost,
port: rport,
proto: 'tcp',
name: 'RDP',
info: service_info
)
end
end