I would like to see what hosts are in my known_hosts file but it doesn’t appear to be human readable. Is it possible to read it?
More specifically there is a host that I can connect to via several names and I want to find out what the fingerprint I expect for it from my known hosts file.
Update: I’m using OpenSSH_5.3p1 Debian-3ubuntu7, OpenSSL 0.9.8k 25 Mar 2009
A line from my known_hosts file looks something like this,
|1|guO7PbLLb5FWIpxNZHF03ESTTKg=|r002DA8L2JUYRVykUh7jcVUHeYE= ssh-rsa AAAAB3NzaC1yc2EAAFADAQABAAABAQDWp73ulfigmbbzif051okmDMh5yZt/DlZnsx3DEOYHu3Nu/+THJnUAfkfEc1XkOFiFgbUyK/08Ty0K6ExUaffb1ERfXXyyp63rpCTHOPonSrnK7adl7YoPDd4BcIUZd1Dk7HtuShMmuk4l83X623cr9exbfm+DRaeyFNMFSEkMzztBYIkhpA2DWlDkd90OfVAvyoOrJPxztmIZR82qu/5t2z58sJ6Jm2xdp2ckySgXulq6S4k+hnnGuz2p1klviYCWGJMZfyAB+V+MTjGGD/cj0SkL5v/sa/Fie1zcv1SLs466x3H0kMllz6gAk0/FMi7eULspwnIp65g45qUAL3Oj
Answers:
Thank you for visiting the Q&A section on Magenaut. Please note that all the answers may not help you solve the issue immediately. So please treat them as advisements. If you found the post helpful (or not), leave a comment & I’ll get back to you as soon as possible.
Method 1
You’ve got HashKnownHosts set to “yes” in your ssh_config file, so the hostnames aren’t available in plaintext.
If you know the hostname you’re looking for ahead of time, you can search for it with:
ssh-keygen -H -F hostname
# Or, if SSH runs on port other than 22. Use literal brackets [].
ssh-keygen -H -F '[hostname]:2222'
Here’s the relevant section from the ssh-keygen(1) man page:
-FhostnameSearch for the specified hostname in a
known_hostsfile, listing any
occurrences found. This option is useful to find hashed host names
or addresses and may also be used in conjunction with the-Hoption
to print found keys in a hashed format.
Method 2
For future searchers, this article (non-disclaimer: I’m not affilated) has a relatively simple Perl script to brute-force hashed IPs and hostnames in known_hosts.
http://blog.rootshell.be/2010/11/03/bruteforcing-ssh-known_hosts-files/
It allows starting from a particular IP address. It could also easily be modified to use a dictionary.
Also, in June 2014, the John the Ripper project added support for known_hosts cracking, which can take advantage of multiple CPU cores, GPUs, dictionary mangling, etc.
Overall, it’s an exercise similar to password cracking, with a somewhat more predictable (or at least constrained) target space.
For private IPs, you can use this nmap snippet to generate a dictionary of all RFC1918 IP addresses to use as a dictionary:
nmap -sL -Pn -n 192.168.0.0/16 172.16.0.0/12 10.0.0.0/8 |
grep '^Nmap scan report for' | cut -d -f5 >ips.list
If public IPs are included, it may be more efficient to use rules. This hashcat ruleset may need additional work to adapt to work with JtR, but does most of the heavy lifting and should give you a starting point.
Hostnames are more idiosyncratic to the user and environment, but there are trends in host naming. Fully qualified hostnames can be correlated in DNS, /etc/hosts, shell history, etc. with any discovered IP addresses. Since destination systems can be entirely unrelated to the host system, public dumps of common domains and hostnames can be acquired from the DNS data from various Internet-wide scanning efforts (such as Censys).
Using John the Ripper is likely to be more efficient and scale better than the native SSH solution in the accepted answer for all but the most simple cases.
Method 3
Does ssh-keygen -l -f ~/.ssh/known_hosts help? It shows the fingerprints for each host in that file. (Using -vyou also get nice little treasure maps, e.g.
+--[ RSA 2048]----+ | . | | + . | | . B . | | o * + | | X * S | | + O o . . | | . E . o | | . . o | | . . | +-----------------+
Method 4
Use the -l option to ssh-keygen to list fingerprints, and the -F option to search for a hostname in your known_hosts file.
$ ssh-keygen -l -F sdf.org # Host sdf.org found: line 835 type RSA 2048 6e:cd:53:4f:75:a1:e8:5b:63:74:32:4f:0c:85:05:17 |1|9J47PEllvWk/HJ6LPz5pOB2/7rc=|ld0BtQh5V3NdhBHBwR/ZqSv8bqY= (RSA)
You can use ssh-keyscan to compare the fingerprint in your known_hosts to the one from the server.
$ ssh-keyscan sdf.org | awk '{print $3}' | base64 -d | openssl md5 -c
# sdf.org SSH-2.0-OpenSSH_7.1
# sdf.org SSH-2.0-OpenSSH_7.1
no hostkey alg
(stdin)= 6e:cd:53:4f:75:a1:e8:5b:63:74:32:4f:0c:85:05:17
Method 5
There is host string/ip at the beginning of each “known_hosts” line (before the “ssh-dss” or “ssh-rsa” string):
hostgn6 ssh-dss AAAB3NzaC1kc3MAAACBAIfGV4+/28Zr+dT/i+ifydUBS0dMRUjCtExIThOj3Yexynu+wSRGjMm4GfF+og2kAljZyUjhBFeM+WYbJzcDSDB [...] == yumyumn6.dik6.dir2g.some.net ssh-dss AAAAB3NzaC1kc3MAAACBAIfGV4+/28Zr+dT/i+ifydUBS0dMRUjCtExITh [...] ==
All methods was sourced from stackoverflow.com or stackexchange.com, is licensed under cc by-sa 2.5, cc by-sa 3.0 and cc by-sa 4.0