OpenPGP with GNU Privacy Guard

Use cases

This setup will focus on having an offline (not in your laptop!) master key, with subkeys on your smartcard. This is a flexible setup since it allows you to revoke/add subkeys, give them a relatively short expiry date.

We will cover the following:

We will focus on the second setup.

During most of this guide, you do not want the smartcard to be plugged in.

Exceptions are:

History

Notes

Some Linux distributions install both GnuPG 1.x and also GnuPG 2.0 or 2.1. To be on the safe side, you should always type gpg2 instead of gpg if your distribution does this. (Most sensible distributions don't)

Getting the smartcard to work

In general, you need gnupg version 2.0 or 2.1.

Gentoo

Install:

  • app-crypt/gnupg[usb,smartcard]
  • app-crypt/ccid[usb]
  • sys-apps/pcsc-lite (possibly with [udev])
  • Optionally also install: net-misc/keychain (nice for managing ssh-agent and gpg-agent)

Make sure you are in the group plugdev and usb:

usermod -a -G usb merlijn
usermod -a -G plugdev merlijn

Ensure pcscd is started:

/etc/init.d/pcscd start

Optionally, start it on boot:

rc-update add pcscd default

If you use keychain, put the following in your .bashrc:

eval `keychain --agents gpg --eval`

For gpg 2.1, this works for me, in my .bashrc:

export SSH_AUTH_SOCK=/home/merlijn/.gnupg/S.gpg-agent.ssh
gpg-agent --daemon --enable-ssh-support

Debian / Ubuntu

Run the following command:

sudo apt-get install gnupg2 pcsc-tools pcscd libccid scdaemon

If ubuntu is lower than 13.04, run:

sudo apt-get install gnupg2 pcsc-tools pcscd libccid gpgsm

Arch Linux

Not verified:

pacman -Sy gnupg pcsclite ccid
systemctl enable pcscd
systemctl start pcscd

Macintosh

TODO

Testing if the smartcard is detected

Issue:

gpg --card-status

Configuring the smartcard

Issue:

gpg --card-edit

And edit as you see fit, but you may want to, at least:

Create (and backup) master key

If you already created a master key, you can skip this step, but just in case, make sure you make a backup of your $HOME/.gnupg folder (tar works).

We start with generating the master key

Issue:

gpg --gen-key

And go for 4096 bit RSA; you can decide if you want RSA (default) or RSA (sign only).

Look for pub 4096R/<hex values> and note the hex values. This is your key ID. Alternatively, use:

gpg --list-keys

Type:

export MY_GPG_KEY=0xKEYHERE

Create a backup:

gpg -a --export-secret-keys $MY_GPG_KEY

Configure GnuPG to act as ssh-agent

This is only required if you want to use GnuPG to log in to your servers using you GnuPG key for ssh.

Do the following:

echo "enable-ssh-support" >> .gnupg/gpg-agent.conf

If you use keychain:

keychain -k
eval `keychain --agents gpg --eval`

Otherwise, if you are using GnuPG 2.1:

killall gpg-agent
export SSH_AUTH_SOCK=/home/merlijn/.gnupg/S.gpg-agent.ssh
gpg-agent --daemon --enable-ssh-support

Create revocation certificates

Create a revocation certificate:

gpg --gen-revoke $MY_GPG_KEY > revocation.txt

and store this somewhere. You want to use this revocation certificate in case you lose access to the key, or when the key gets stolen / comprosised.

Create subkeys

Note: This describes creating the keys on your laptop, but you can also create them directly on the card, TODO.

If you want the keys to be generated on the card, plug the card in. Otherwise, remove the cards from the reader. (Or just remove the reader from the system)

Issue:

gpg --expert --edit-key $MY_GPG_KEY

Then, type:

addkey

And RSA (sign only) with 4096 bit.

Repeat for RSA (encrypt only).

If you also want an authentication key, also do the following:

Finish by typing save.

Backup & Remove master key

The following commands makes a full backup of your current keyring, including the master key:

tar cjf gnupg-backup.tar.bz2 .gnupg/

The following steps remove the master key from your keyring:

gpg --export-secret-subkeys $MY_GPG_KEY > subkeys
gpg --delete-secret-keys $MY_GPG_KEY
gpg --import subkeys
shred --remove subkeys

The first commands makes a backup of your subkeys. The second command removes all subkeys and the master key, the third command imports only the subkeys, not the master key. The fourth command nukes your backup that you will no longer need.

Getting the subkeys on the card

If you generated the keys on the card, you can skip this step.

Type the following:

gpg --expert --edit-key $MY_GPG_KEY

Pay special attention to the usage: of each key. This step requires more attention than blind copy pasting, since key numbers and indexes may differ.

Now, you want to store each key on the smartcard. Use the command toggle to enter a mode that allows this:

toggle

Then, use the command key to toggle-(de)select a key. Followed by a keytocard command, again followed by another key to deselect the key:

key 1
keytocard
key 1
save

Now do the same, but replace key 1 with key 2 or key 3, respectively. Or whatever number makes sense in your setup.

keytocard automatically removes the private part of the subkey from your keyring. So you don't need to remove it manually.

Voila!

Sending your keys to the keyserver

If you would like your keys to end up at the keyserver, issue:

gpg --send-keys $MY_GPG_KEY

And wait for it to send your key to the keyserver, and then wait some more for the keyserver to distribute it to other keyservers.

Testing if it works

If you use Thunderbird and Enigmail, you can try to sign and decrypt emails.

Another simple testcase:

echo "You will hopefully see this" | gpg -r $MY_GPG_KEY -e -a | gpg -d

Using SSH with an auth key

Issue the gpgkey2ssh command on your AUTH key. (run gpg --expert --edit-key $MY_GPG_KEY and look for usage: A):

gpgkey2ssh MYAUTHKEYID > .ssh/my-gpg-card-key.pub

Do NOT prefix the authkey with 0x for gpgkey2ssh, it will fail with a cryptic error.

Alternatively, if you are using gpg 2.1:

gpg --export-ssh-key $MY_GPG_KEY > ~/.ssh/my-gpg-card-key.pub

On the remote:

Add: local .ssh/my-gpg-card-key.pub to remote:.ssh/authorized_keys

.ssh/config

Host <foo>
    Hostname <bar>
    IdentityFile .ssh/my-gpg-card-key.pub
    PreferredAuthentications publickey

(Optionally?) Run:

ssh-add

Finally:

ssh -vv user@host

Resources