Mastodon

Use Yubikey and Password-store for Ansible credentials

I spent some time over the last months to improve the security of servers and passwords. In doing so, I started to orchestrate my servers using a configuration management tool called Ansible. This allows me to spin-up fresh servers in a few seconds and to get rid of year-old, polluted and insecure system images.

ansible_loves_yubico

My ’single password for everything‘ has been replaced by a new password policy which enforces individual passwords for every single service. This was easier than I previously expected:

To unlock the ‚paranoid‘ level, I additionally purchased a Yubikey Neo token to handle the decryption of my login credentials in tamper-proof hardware.
pass‚ is just a small shell script to glue several existing Unix tools together: Bash, pwgen, Git, xclip & GnuPG (obeying the Unix philosophy). The passwords are stored in simple text files which are encrypted by PGP and stored in a directory structure which is managed in a Git repository.

IMG_20150526_121142
Yubikey Neo und Neo-n

There are already a tons of tutorials which present the tools I describes above. I do not want to repeat all that stuff. So, this post is dedicated to solve some smaller issues I encountered:

Use One-Time passwords across multiple servers

The Yubikey Neo can do much more than decrypting static passwords via GnuPG:

  • Generate passwords:
    • fixed string (insecure!)
    • with Yubico OTP algorithm
    • with OATH-HOTP algorithm
  • Do challenge response authentication
    • via FIDO’s U2F standard
    • with HMAC-SHA1 algorithm
    • with Yubico OTP algorithm

Some third-party services already support FIDO U2F standard or traditional OATH-{H,T}OTP TFA, like used by the Google authenticator app. I suggest to have a look at: https://twofactorauth.org/.

For private servers there are several PAM modules available to integrate OTP’s or Challenge Response (CR) methods. Unfortunately, support for CR is not widespread across different SSH- and mail clients.

So, you want to use OTP’s which leds to another problem: OTP’s rely on a synchronized counter between the hardware token and the server. Once you use multiple servers, those must be synchronized as well. I’m using a central Radius server to facilitate this.

Integrate ‚pass‘ into your Ansible workflow

Ansible uses SSH and Python scripts to manage several remote machines in parallel. You must use key-based SSH authentication, because you do not want to type every password manually! Additionally you need to get super user privileges for most of your administrative tasks on the remote machine.

The SSH authentication is handled by gpg-agents ‚–enable-ssh-support‘ option and a PGP key on your token.

To get super user privileges, I use the following variable declaration my Ansible „group_vars/all“ file:
---
ansible_sudo_pass: "{{ lookup('pipe', 'pass servers/' + inventory_hostname) }}"

There is a separate root password for every server (e.g. „pass servers/lian.0l.de“). I wrote some ansible roles to easily and periodically roll those passwords.

Integrate ‚pass‘ into OS X

There are already several plugins and extensions to intergrate the ‚pass‘ password store into other Programs like Firefox and Android.

pass_osx_prompt
A prompt for the password you want

I added support for OS X by writing a small AppleScript which can be found here: https://github.com/zx2c4/password-store/blob/master/contrib/pass.applescript

pass_osx_notification
A notification with countdown