CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutSign UpSign In
rapid7

Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.

GitHub Repository: rapid7/metasploit-framework
Path: blob/master/modules/post/multi/gather/dns_bruteforce.rb
Views: 11784
1
##
2
# This module requires Metasploit: https://metasploit.com/download
3
# Current source: https://github.com/rapid7/metasploit-framework
4
##
5
6
class MetasploitModule < Msf::Post
7
8
def initialize(info = {})
9
super(
10
update_info(
11
info,
12
'Name' => 'Multi Gather DNS Forward Lookup Bruteforce',
13
'Description' => %q{
14
Brute force subdomains and hostnames via wordlist.
15
},
16
'License' => MSF_LICENSE,
17
'Author' => [ 'Carlos Perez <carlos_perez[at]darkoperator.com>'],
18
'Platform' => %w[bsd linux osx solaris win],
19
'SessionTypes' => [ 'meterpreter', 'shell' ]
20
)
21
)
22
register_options(
23
[
24
25
OptString.new('DOMAIN', [true, 'Domain to do a forward lookup bruteforce against.']),
26
OptPath.new('NAMELIST', [
27
true, 'List of hostnames or subdomains to use.',
28
::File.join(Msf::Config.data_directory, 'wordlists', 'namelist.txt')
29
])
30
31
]
32
)
33
end
34
35
# Run Method for when run command is issued
36
def run
37
domain = datastore['DOMAIN']
38
hostlst = datastore['NAMELIST']
39
a = []
40
41
print_status("Performing DNS Forward Lookup Bruteforce for Domain #{domain}")
42
43
name_list = []
44
if ::File.exist?(hostlst)
45
::File.open(hostlst).each do |n|
46
name_list << n
47
end
48
end
49
50
case session.platform
51
when 'windows'
52
cmd = 'nslookup'
53
when 'solaris'
54
cmd = '/usr/sbin/host '
55
else
56
cmd = '/usr/bin/host '
57
end
58
59
while !name_list.nil? && !name_list.empty?
60
1.upto session.max_threads do
61
a << framework.threads.spawn("Module(#{refname})", false, name_list.shift) do |n|
62
next if n.nil?
63
64
vprint_status("Trying #{n.strip}.#{domain}")
65
r = cmd_exec(cmd, "#{n.strip}.#{domain}")
66
67
case session.platform
68
when 'windows'
69
proccess_win(r, "#{n.strip}.#{domain}")
70
else
71
process_nix(r, "#{n.strip}.#{domain}")
72
end
73
end
74
a.map(&:join)
75
end
76
end
77
end
78
79
# Process the data returned by nslookup
80
def proccess_win(data, ns_opt)
81
if data =~ /Name/
82
# Remove unnecessary data and get the section with the addresses
83
returned_data = data.split(/Name:/)[1]
84
# check each element of the array to see if they are IP
85
returned_data.gsub(/\r\n\t |\r\n|Aliases:|Addresses:/, ' ').split(' ').each do |e|
86
if Rex::Socket.dotted_ip?(e)
87
print_good("#{ns_opt} #{e}")
88
report_host(host: e, name: ns_opt.strip)
89
end
90
end
91
end
92
end
93
94
# Process the data returned by the host command
95
def process_nix(r, ns_opt)
96
r.each_line do |l|
97
data = l.scan(/(\S*) has address (\S*)$/)
98
next if data.empty?
99
100
data.each do |e|
101
print_good("#{ns_opt} #{e[1]}")
102
report_host(host: e[1], name: ns_opt.strip)
103
end
104
end
105
end
106
end
107
108