If you’ve ever signed up for a Google, Github, or Twitter account then you’ve likely come across two-factor authentication.
It’s a fairly simple concept. A user tries to log in, and even if they enter the correct details, they then get asked to confirm a unique one-time code, often presented in an app or sent to them via SMS.
This ensures that the user logging in must also have access to a physical device that can generate the code, so even if someone was remotely able to get your login details, without having the two-factor code those details are useless to them.
Two-factor for SSH
Adding in two-factor logins to SSH then seems like a no brainer. It provides a much needed extra security layer on an otherwise very vulnerable port of entry to your server.
For this guide, we’re going to use Google Authenticator. This includes their online service and their mobile application. There are of course other places you can generate the code (e.g using the Authy app, or storing your two-factor secret in 1Password) but for this tutorial, we’ll focus on Google’s offering.
Step 1 - Adding Authenticator to your server
Log into your server as a user that is allowed to run commands as sudo. If you’re using a root-level user you can remove
sudo from our commands below.
Debian & Ubuntu
Install the Google Authenticator package using the apt package manager:
sudo apt-get install libpam-google-authenticator
CentOS & RedHat
If you’re using CentOS or another RedHat based distribution you can install the package using yum.
You first need to ensure you’ve got the EPEL (Extra Packages for Enterprise Linux) repository set up.:
sudo yum install epel-release
Once that’s completed, you can go ahead and install Google Authenticator:
sudo yum install google-authenticator
Depending on your Fedora version you may have Yum installed. In which case, you can use the CentOS instructions above.
If however you’ve got Fedora’s “DNF” package manager, you can simply run:
sudo dnf install google-authenticator
Step 2 - Configuration
So you’ve got the package installed, and now it’s time to set it up.
You’ll first be asked if you want authentication tokens to be time-based. It’s a good idea to enable this, so we’ll press ‘Y’.
You’ll now see a huge QRCode output in your terminal, along with a secret key, verification code and emergency scratch codes. You should take a copy of these and store them somewhere safe and secure. The QR code can be scanned inside your Google Authenticator mobile app.
Next, you’ll be asked if you want to update your Google authenticator config file - select yes.
The next question allows you to have a slight delay between tokens, so they don’t expire at exactly 30 seconds. This is handy for when times may not be 100% accurate, so is worth enabling.
Finally, you’ll be asked if you want to enable rate-limiting. This prevents attackers from attempting to crack entry by brute force, so should be enabled.
Authenticator is now configured on your server. So let's dive right in and enable it for SSH.
Step 3 - Enabling SSH 2FA
Using an editor such as nano or vi, open the sshd pam.d configuration file:
sudo nano /etc/pam.d/sshd
We’ll need to load in the Google Authenticator extension in this file. Scroll to the bottom and add the following line:
# Google Authenticator 2FA Extension auth required pam_google_authenticator.so
Save the file to apply the change (in Nano this can be done by pressing CTRL+X and then confirming the change).
Now we need to update the main sshd config file to enable the challenge response.
Open the file in your editor:
sudo nano /etc/ssh/sshd_config
Search the file (in nano you can search by pressing CTRL+W) for ‘ChallengeResponse’ and you should find the full line.
Once you’ve updated the line to be enabled, it should look like this:
# Change to yes to enable challenge-response passwords (beware issues with # some PAM modules and threads) ChallengeResponseAuthentication yes
Save the file (CTRL+X followed by ‘y’ in nano).
Step 4 - Restart SSH & Test
Finally, all that’s left to do is restart the sshd service. This can vary slightly depending on your Linux distribution;
Ubuntu & Debian
sudo service sshd restart
CentOS & Fedora
sudo systemctl restart sshd
Now that you've restarted ssh, keep your current session logged in - this way if something hasn't quite worked you won’t be locked out.
In a new terminal window, ssh to your server. After entering your password and you should now be prompted to enter your two-factor code, which is generated by the Google Authenticator app on your phone.
That about wraps things up! You've now added an easy to use extra layer of security, which makes it much harder for SSH to be attacked on your server.