This article describes a method how to use a USB memory device as an authentication token to log in into a Linux system instead of traditional password. This can be accomplished by use of Pluggable Authentication Modules ( PAM ) and some sort of USB storage device such as USB memory stick of Mobile phone with SD card attached.
This authentication technique can be also further expanded into Two-Factor authentication where two authentication methods involving USB token and one-time password can be merged together to produce a greater security. This article is written using Ubuntu Linux systems. However, users of other Linux distributions should be able to follow below described steps to achieve the same results.
Pluggable Authentication modules are available on most of Linux system in a form of pre-compiled packages accessible from a relevant repository. First we need to install required packages for PAM USB authentication:
$ sudo apt-get install pamusb-tools libpam-usb
In the next step, we will add a USB device which we intend to use with PAM authentication. This can be done with a pamusb-conf command or manually by editing /etc/pamusb.conf file. Using pamusb-conf command greatly reduces time and difficulty of this operation. Connect your USB device and execute a following command with a name of your USB device as an argument. The name can be anything you wish. In this case, we use "my-usb-stick" :
$ sudo pamusb-conf --add-device my-usb-stick Please select the device you wish to add. * Using "Verbatim STORE N GO (Verbatim_STORE_N_GO_07A10D0894492625-0:0)" (only option) Which volume would you like to use for storing data ? 0) /dev/sdb2 (UUID: A842-0654) 1) /dev/sdb1 (UUID: CAAF-0882) [0-1]: 0 Name : my-usb-stick Vendor : Verbatim Model : STORE N GO Serial : Verbatim_STORE_N_GO_07A10D0894492625-0:0 UUID : A842-0654 Save to /etc/pamusb.conf ? [Y/n] Y Done.
The pamusb-conf is smart enough to discover our USB device, including multiple partitions. After completing this step a block of XML code had been added into /etc/pamusb.conf configuration file to define our USB device.
<pre> <device id="my-usb-stick"> <vendor> Verbatim </vendor> <model> STORE N GO </model> <serial> Verbatim_STORE_N_GO_07A10D0894492625-0:0 </serial> <volume_uuid> A842-0654 </volume_uuid> </device> </pre>
It is obvious, but it should be mentioned that we can add several USB devices into PAM configuration, and at the same time we can define multiple users for one or more USB devices. In our example, we will keep things straightforward by defining a USB device to be used as credentials by a single user. If the user "ubuntu-user" exists on our system, we can add him to PAM configuration with a following command:
$ sudo pamusb-conf --add-user ubuntu-user Which device would you like to use for authentication ? * Using "my-usb-stick" (only option) User : ubuntu-user Device : my-usb-stick Save to /etc/pamusb.conf ? [Y/n] y Done.
Definition of a pam_usb user had been added into into /etc/pamusb.conf configuration:
<user id="ubuntu-user"> <device>my-usb-stick</device> </user>
At this point, we have defined a USB device "my-usb-stick" to be used as an authentication credential for a user "ubuntu-user". However, the system wide PAM library is not aware of the pam_usb module yet. To add pam_usb into a system authentication process, we need to edit a /etc/pam.d/common-auth file.
NOTE: If you are using RedHat or Fedora Linux system this file can be known as /etc/pam/system-auth . Your default PAM common-auth configuration should include a following line:
auth required pam_unix.so nullok_secure
This is a current standard which uses /etc/passwd and /etc/shadow to authenticate a user. The "required" option means that the correct password must be supplied in order the user will be granted access to the system. Alter your /etc/pam.d/common-auth configuration to:
NOTE: Before you do any changes to /etc/pam.d/common-auth open-up separate terminal with root access. This is just in case that something goes wrong, and you need a root access to change /etc/pam.d/common-auth back to the original configuration.
auth sufficient pam_usb.so auth required pam_unix.so nullok_secure
At this point, user "ubuntu-user" can authenticate with its relevant USB device pluged-in. This is defined by a "sufficient" option for pam_usb library.
$ su ubuntu-user * pam_usb v0.4.2 * Authentication request for user "ubuntu-user" (su) * Device "my-usb-stick" is connected (good). * Performing one time pad verification... * Regenerating new pads... * Access granted.
NOTE:If you get an error:
Error: device /dev/sdb1 is not removable * Mount failed
Normally this error should not happen however as a temporary solution add a full path to your block USB device into /etc/pmount.allow. For example if a login error or command:
$ sudo fdidk -l
listed my USB device and partition as /dev/sdb1 , add a line:
into /etc/pmount.allow to solve this problem. This is just a temporary solution as your USB device can be recognized differently every time it is connected to the system. In this case one solution can be to write USB udev rules.
In case the USB device defined for a "ubuntu-user" is not present in the system the user will need to enter a correct password. To force user have both authentication routines in place before granting an access to the system change a "sufficient" to "required":
auth required pam_usb.so auth required pam_unix.so nullok_secure
Now the user will need to enter a correct password as well as insert USB device.
$ su ubuntu-user * pam_usb v0.4.2 * Authentication request for user "ubuntu-user" (su) * Device "my-usb-stick" is connected (good). * Performing one time pad verification... * Access granted. Password:
Let's test it with USB device unplugged and correct password:
$ su ubuntu-user * pam_usb v0.4.2 * Authentication request for user "ubuntu-user" (su) * Device "my-usb-stick" is not connected. * Access denied. Password: su: Authentication failure
In addition to USB user authentication a USB device event can be defined to be triggered every time a user disconnect or connect USB device from a system. For example, pam_usb can lock a screen when a user disconnects USB device and unlock it again when a user connects USB device. This can be accomplished by a simple modification of user definition XML code block in /etc/pamusb.conf file.
<user id="ubuntu-user"> <device> my-usb-stick </device> <agent event="lock">gnome-screensaver-command -l</agent> <agent event="unlock">gnome-screensaver-command -d</agent> </user>