In the past I wrote about setting up a bastion hosts and why they are important. I thought I’d take the time to explain how to utilize a Yubikey as a mechanism to perform 2FA when you SSH into bastion hosts.
There are a few key components here:
Yubico sells a number of different Yubikeys for specific purposes. A the time of writing, the Yubikey 5 is the flagship device and is perfect for general 2FA. Yubico usually ship within 2 days and their customer service has been great to me in the past.
You will need to configure /etc/ssh/sshd_config
to have the following parameters
PubkeyAuthentication yes
PasswordAuthentication no
UsePAM yes
ChallengeResponseAuthentication yes
AuthenticationMethods publickey,keyboard-interactive:pam
If you’re on EPEL/ RHEL/ CentOS, you can install it via yum
sudo yum install pam_yubico
Otherwise if you’re on a Debian distribution:
sudo add-apt-repository ppa:yubico/stable
sudo apt-get update
sudo apt-get install libpam-yubico
In order to use the PAM module, assuming you’re not running your own Yubico validation servers, you’ll need to register for an API key at: https://upgrade.yubico.com/getapikey/. Simply provide an email address and press your Yubikey and you’ll get an id
and a key
(which ends with an =
).
The Pubico PAM module allows you to configure Yubikey the authorized Yubikeys in one of two ways:
~/.yubico/authorized_yubikeys
. This file is formatted in the following manner:<username>:<Token-ID-1>:<Token-ID-2>:<Token-ID-n>
So it looks something like this:
michael:ccccccrjzigk:ccccccirfkl
/etc/yubikeys
). This file follows the same format, however one user-name per line:michael:ccccccrjzigk:ccccccirfkl
bob:ccccccirkdkx
The way to get the token ID is to press your Yubikey in a text editor and copy the first 12 characters of the string that is produced. I usually do this in Python just to be sure:
michael@laptop~ % python
>>> a = "eibeeliibcjkcljuiieijhcckeerejbikvhhcbchkgin"
>>> b = a[0:12]
>>> b
'eibeeliibcjk'
>>> len(b)
12
There is no security advantage between methods, but depending on if and how you’re using configuration management, there may be a preferred method here. You can find more information at the Yubico site.
In /etc/pam.d/sshd: on the top line, add the following string, replacing the id
and key
from the previous step.
auth required pam_yubico.so id=<id> key=<key> debug
auth required pam_yubico.so id=<id> key=<key> debug authfile=/path/to/mapping/file
You will need to restart sshd
to pick up these changes.
Note: If you’re using pihole, make sure that the api*.yubico.com
is not being blocked.
We recommend that you keep the terminal you’re using to configure your bastion host open and then try and SSH to the bastion in a new tab/ window. When you SSH, you should be prompted for your Yubikey:
michael@laptop ~ % ssh bastion
YubiKey for `michael`:
Last Login: Thu June 10 20:22:53 2020 from 192.168.x.x
[michael@bastion ~]$
Credit to Yubico for the cover image