Create our first SSH key pair
In 2019, the unthinkable happened. A server of mine, that was exposed to the internet and wasn’t properly locked down, got hacked, taking down an entire radio station. I never saw it coming. I’m not T-Mobile or Bank of America — so how did they even find me? Turns out, it’s random. Hackers cast a wide net scanning blocks of IP addresses looking for vulnerabilities. When they find them, they go to work exploiting them. It’s like a game to them.
They injected their own ssh key, malicious code, and managed to give themselves root privileges on my server. I was chasing my tail in circles deleting their ssh key, only to see it reappear every freaking day! It took a week to figure out what was going on. Fortunately, 99% of my data was backed up and I was able to recover most of it, but not without considerable downtime, major frustration, and some corrupted files that weren’t part of the backup.
That unfortunate situation forced me to learn how to harden security and minimize risks. Knock on wood, I haven’t been hacked since. With all of the data breaches in the news almost daily, I can’t help wondering if each one could be prevented by implementing better security, or if it’s impossible at the scale of a massive corporation.
Start by creating an SSH keypair using the ssh-keygen
command in a terminal. The public key can be shared, while the private key must be kept secret. During the process you’ll be asked to choose a location to save the key pair (or accept the default location) and optionally set a passphrase for added security. You can keep the default name, or give it something unique.
TIP: Passphrases add an extra layer of security to your openssh keys but can cause compatibility issues with the putty .ppk protocol if you need to convert it (to connect to a server using SFTP with Filezilla, for example). If you add a passphrase, now would be an excellent time to generate a 2nd key without a passphrase just for the purpose of using for SFTP (thank me later).
ssh-keygen -o -t rsa -b 4096 -C "name@email.com"
Once our key pair is generated, lets import our public key (the one ending in .pub) to our remote server with the following command. Edit the command with your own public key name, path, username and server IP.
Import public key to remote server
cat ~/.ssh/id_rsa.pub | ssh username@1.2.3.4 "mkdir -p ~/.ssh && touch ~/.ssh/authorized_keys && chmod -R go= ~/.ssh && cat >> ~/.ssh/authorized_keys"
Test our private key
Now that we’ve imported our public key on the remote server, lets connect to it with our locally stored private key. Start by creating a config file to manage multiple private keys and remote hosts. Remote servers, VirtualBoxes, and ssh keys can quickly grow out of control, but maintaining a local ssh config file keeps it all manageable. And ssh references it automatically when we log into remote servers.
touch ~/.ssh/config chmod 600 ~/.ssh/config sudo nano ~/.ssh/config
Copy, paste and edit the following in the file you just created and save it. You can add as many Hosts to different servers (and VirtualBoxes) as you’d like and specify different Host (nicknames,) Hostnames, private key files, and Users for each.
Host * IdentitiesOnly yes Host hollywood #nickname Hostname 1.2.3.4 #remote server IP or FQDN IdentityFile ~/.ssh/id1_rsa #your private key User root #remote username Host tokyo Hostname 5.6.7.8 IdentityFile ~/.ssh/id2_rsa User user2
So instead of remembering — ssh -i ~/.ssh/id2_rsa user2@5.6.7.8
— let alone multiple servers with different addresses, users and ssh keys… We can connect to the server using the shorthand: ssh tokyo
and ssh will automatically read the config file and log into the chosen server with the associated ssh key based on the nickname specified by the Host.
TIP: “Host” is a nickname you give your remote server that makes it easy for you to remember. “Hostname” is the remote server’s IP address or domain name.
Harden ssh security on remote server
After importing your SSH key (and confirming you can log back in with it) disable password authentication on the remote server. Don’t skip testing your ssh key, or you risk getting locked out of your remote server permanently. First, backup the default sshd_config file in case you make a mistake and need to restore it.
sudo cp /etc/ssh/sshd_config sshd_config-BAK
Now, edit the sshd_config file with the changes outlined below.
sudo nano /etc/ssh/sshd_config
Make the following changes to your sshd_config file on your remote server to harden security. Combined with UFW (which we covered in another article) you can lock down your remote server to your external IP and limit which ports are exposed to the public.
Add a “#” to comment out the following line:
#Include /etc/ssh/sshd_config.d/*.conf
It’s a really good idea to disable root login over ssh. Once you login as a normal user, you can use sudo to temporarily elevate your user permissions or use su to use the root account.
PermitRootLogin no
Delete the “#” to uncomment the following line:
PubkeyAuthentication yes
Uncomment and change to no:
PasswordAuthentication no
CTRL+O to save and CTRL+X to exit
Restart SSH to apply changes
sudo systemctl restart ssh
What to do if you get the following error:
ssh-keygen -R "111.222.333.444"
Proper ssh key Linux permissions
chmod 700 ~/.ssh chmod 644 ~/.ssh/authorized_keys chmod 644 ~/.ssh/known_hosts chmod 644 ~/.ssh/config chmod 600 ~/.ssh/id_rsa chmod 644 ~/.ssh/id_rsa.pub
Leave a Reply