Setting up GPG

One of the cornerstones of my home infrastructure is GPG. GPG is an encryption/signing/authentication tool, and is used for all three purposes in my network. I use it for SSH connections (authentication), my password store (encryption/decryption), and signing emails.  For added security, this is done via a smart card purchased from kernel concepts. My personal machine is a Lenovo T420, and I use the embedded card reader.

Setting up the card with current versions of GPG (2.0.21 as of today) is different from most tutorials you can find. This is due to GPG versions 2.0.18 and later supporting 4096 bit keys for the kernel concept smart card. Before you start configuring the card, you need to install all necessary software. For me, that is:

gpg2, gpgsm, pcscd, gnupg-agent

Once those are installed, you can begin to create your keys. While these instructions assume you have a smart card, they will work with minimal effort even absent one.

USERNAME@phoenix ~ % gpg --card-status 
Application ID ...: D276000124010200000500001ABD0000
Version ..........: 2.0
Manufacturer .....: ZeitControl
Serial number ....: 00001ABD
Name of cardholder: [not set]
Language prefs ...: en
Sex ..............: unspecified
URL of public key : [not set]
Login data .......: [not set]
Signature PIN ....: forced
Max. PIN lengths .: 32 32 32
PIN retry counter : 3 0 3
Signature counter : 0
Signature key ....: [none]
Encryption key....: [none]
Authentication key: [none]
General key info..: [none]

Your smart card information should look similar to this. First, here’s some important safety information: The card accepts up to three wrong PINs in a row and then block, until unblocked by the admin PIN. Three wrong admin PINs and your card bricks itself, to prevent access to the information. Don’t do this, unless you need to know that the information has to be destroyed.

Now we’ll begin to edit the smart card. With your card, you can either transfer pre-existing keys to the card, or generate new ones. I am going to generate keys on the card, as demonstrated below.

USERNAME@phoenix ~ % gpg --card-edit                        

Application ID ...: D276000124010200000500001ABD0000
Version ..........: 2.0
Manufacturer .....: ZeitControl
Serial number ....: 00001ABD
Name of cardholder: [not set]
Language prefs ...: en
Sex ..............: unspecified
URL of public key : [not set]
Login data .......: [not set]
Signature PIN ....: forced
Max. PIN lengths .: 32 32 32
PIN retry counter : 3 0 3
Signature counter : 0
Signature key ....: [none]
Encryption key....: [none]
Authentication key: [none]
General key info..: [none]

Command> admin
Admin commands are allowed

Command> name
Cardholder's surname: O'Connell
Cardholder's given name: Patrick
gpg: 3 Admin PIN attempts remaining before card is permanently locked

Admin PIN
gpg: gpg-agent is not available in this session

Command> lang
Language preferences: en

Command> sex
Sex ((M)ale, (F)emale or space): m

gpg/card> generate 

Admin-only command

gpg/card> admin
Admin commands are allowed

gpg/card> generate
Make off-card backup of encryption key? (Y/n) y

What keysize do you want for the Signature key? (2048) 4096
The card will now be re-configured to generate a key of 4096 bits
NOTE: There is no guarantee that the card supports the requested size.
      If the key generation does not succeed, please check the
      documentation of your card to see what sizes are allowed.
What keysize do you want for the Encryption key? (2048) 4096
The card will now be re-configured to generate a key of 4096 bits
What keysize do you want for the Authentication key? (2048) 4096
The card will now be re-configured to generate a key of 4096 bits
Please specify how long the key should be valid.
         0 = key does not expire
        = key expires in n days
      w = key expires in n weeks
      m = key expires in n months
      y = key expires in n years
Key is valid for? (0) 0
Key does not expire at all
Is this correct? (y/N) y

GnuPG needs to construct a <a class="zem_slink" title="User identifier" href="http://en.wikipedia.org/wiki/User_identifier" target="_blank" rel="wikipedia">user ID</a> to identify your key.

Real name: Patrick O'Connell
Email address: pat@aeriagloris.net
Comment: 
You selected this USER-ID:
    "Patrick O'Connell <pat@aeriagloris.net>"

Change (N)ame, (C)omment, (E)mail or (O)kay/(Q)uit? O

You need a Passphrase to protect your secret key.

gpg: NOTE: backup of card key saved to `/home//.gnupg/sk_16A65751AA333CD9.gpg'
gpg: key F7D12196 marked as ultimately trusted
public and secret key created and signed.

gpg: checking the trustdb
gpg: 3 marginal(s) needed, 1 complete(s) needed, PGP trust model
gpg: depth: 0  valid:   2  signed:   0  trust: 0-, 0q, 0n, 0m, 0f, 2u
pub   4096R/F7D12196 2013-09-22
      Key fingerprint = 0059 EA3C CC54 D92F E203  DE29 12F2 C901 F7D1 2196
uid                  Patrick O'Connell <pat@aeriagloris.net>
sub   4096R/43DDE8B2 2013-09-22
sub   4096R/AA333CD9 2013-09-22

gpg/card> quit

With those initial keys set up, we can now configure some settings. The first we want to get to is changing the preferences for how to do signatures.

USERNAME@phoenix [2] ~ % gpg --edit-key pat@aeriagloris.net 
gpg (GnuPG) 2.0.21; Copyright (C) 2013 Free Software Foundation, Inc.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Secret key is available.

pub  2048R/14F0F412  created: 2013-07-27  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  2048R/61DBC4A3  created: 2013-07-27  expires: never       usage: A   
sub  2048R/2081E3C6  created: 2013-07-27  expires: never       usage: E   
[ultimate] (1). Patrick O'Connell <pat@aeriagloris.net>

gpg> uid 1

pub  2048R/14F0F412  created: 2013-07-27  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  2048R/61DBC4A3  created: 2013-07-27  expires: never       usage: A   
sub  2048R/2081E3C6  created: 2013-07-27  expires: never       usage: E   
[ultimate] (1)* Patrick O'Connell <pat@aeriagloris.net>

gpg> setpref SHA512 SHA384 SHA256 SHA224 AES256 AES192 AES CAST5 ZLIB BZIP2 ZIP Uncompressed
Set preference list to:
     Cipher: AES256, AES192, AES, CAST5, 3DES
     Digest: SHA512, SHA384, SHA256, SHA224, SHA1
     Compression: ZLIB, BZIP2, ZIP, Uncompressed
     Features: MDC, Keyserver no-modify
Really update the preferences for the selected user IDs? (y/N) y

pub  4096R/F7D12196  created: 2013-09-22  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  4096R/43DDE8B2  created: 2013-09-22  expires: never       usage: A   
sub  4096R/AA333CD9  created: 2013-09-22  expires: never       usage: E   
[ultimate] (1)* Patrick O'Connell <pat@aeriagloris.net>

gpg> save
USERNAME@phoenix ~ %

You can now add any other uids you need to your key. This can be done with the edit-keys command followed by the adduid command.

USERNAME@phoenix ~ % gpg --edit-key pat@aeriagloris.net
gpg (GnuPG) 2.0.21; Copyright (C) 2013 Free Software Foundation, Inc.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Secret key is available.

pub  4096R/F7D12196  created: 2013-09-22  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  4096R/43DDE8B2  created: 2013-09-22  expires: never       usage: A   
sub  4096R/AA333CD9  created: 2013-09-22  expires: never       usage: E   
[ultimate] (1). Patrick O'Connell <pat@aeriagloris.net>

gpg> adduid 
Real name: Patrick O'Connell
Email address: 
Comment: 
You selected this USER-ID:
    "Patrick O'Connell "

Change (N)ame, (C)omment, (E)mail or (O)kay/(Q)uit? O

pub  4096R/F7D12196  created: 2013-09-22  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  4096R/43DDE8B2  created: 2013-09-22  expires: never       usage: A   
sub  4096R/AA333CD9  created: 2013-09-22  expires: never       usage: E   
[ultimate] (1)  Patrick O'Connell <pat@aeriagloris.net>
[ unknown] (2). Patrick O'Connell 

gpg>  save
USERNAME@phoenix ~ %

Initializing the card generated both authentication and encryption subkeys, and the next stage is to add a separate signing subkey. Subkeys are keys that cannot sign other keys, but depend on the initial keys set up for their trust. These are used to avoid having to use the ultimately trusted key everywhere. This also helps demonstrate how to add other subkeys later, if needed.

USERNAME@phoenix ~ % gpg --edit-key pat@aeriagloris.net
gpg (GnuPG) 2.0.21; Copyright (C) 2013 Free Software Foundation, Inc.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Secret key is available.

gpg: checking the trustdb
gpg: 3 marginal(s) needed, 1 complete(s) needed, PGP trust model
gpg: depth: 0  valid:   1  signed:   0  trust: 0-, 0q, 0n, 0m, 0f, 1u
pub  4096R/F7D12196  created: 2013-09-22  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  4096R/43DDE8B2  created: 2013-09-22  expires: never       usage: A   
sub  4096R/AA333CD9  created: 2013-09-22  expires: never       usage: E   
[ultimate] (1). Patrick O'Connell 
[ultimate] (2)  Patrick O'Connell <pat@aeriagloris.net>

gpg> uid 2

pub  4096R/F7D12196  created: 2013-09-22  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  4096R/43DDE8B2  created: 2013-09-22  expires: never       usage: A   
sub  4096R/AA333CD9  created: 2013-09-22  expires: never       usage: E   
[ultimate] (1). Patrick O'Connell 
[ultimate] (2)* Patrick O'Connell <pat@aeriagloris.net>

gpg> addkey 
Secret parts of primary key are stored on-card.
Please select what kind of key you want:
   (3) DSA (sign only)
   (4) RSA (sign only)
   (5) Elgamal (encrypt only)
   (6) RSA (encrypt only)
Your selection? 4
RSA keys may be between 1024 and 4096 bits long.
What keysize do you want? (2048) 4096
Requested keysize is 4096 bits
Please specify how long the key should be valid.
         0 = key does not expire
        = key expires in n days
      w = key expires in n weeks
      m = key expires in n months
      y = key expires in n years
Key is valid for? (0) 0
Key does not expire at all
Is this correct? (y/N) y
Really create? (y/N) y
You need a Passphrase to protect your secret key.

We need to generate a lot of random bytes. It is a good idea to perform
some other action (type on the keyboard, move the mouse, utilize the
disks) during the prime generation; this gives the random number
generator a better chance to gain enough entropy.

pub  4096R/F7D12196  created: 2013-09-22  expires: never       usage: SC  
                     trust: ultimate      validity: ultimate
sub  4096R/43DDE8B2  created: 2013-09-22  expires: never       usage: A   
sub  4096R/AA333CD9  created: 2013-09-22  expires: never       usage: E   
sub  4096R/31FED8A5  created: 2013-09-22  expires: never       usage: S   
[ultimate] (1). Patrick O'Connell 
[ultimate] (2)* Patrick O'Connell <pat@aeriagloris.net>

gpg> save
USERNAME@phoenix ~ %

The next step, and critical to the security of the entire GPG infrastructure, is creating revocation certificates. These can be posted to GPG key servers to announce that you cannot trust them anymore, typically if you lose physical control over your smart card. This is the only possible way to revoke the trust of a certificate, so do not skip this step!

USERNAME@phoenix ~ % gpg --output pat@aeriagloris.net.gpg-revocation-certificate --gen-revoke pat@aeriagloris.net  

sec  4096R/F7D12196 2013-09-22 Patrick O'Connell <pat@aeriagloris.net>

Create a revocation certificate for this key? (y/N) y
Please select the reason for the revocation:
  0 = No reason specified
  1 = Key has been compromised
  2 = Key is superseded
  3 = Key is no longer used
  Q = Cancel
(Probably you want to select 1 here)
Your decision? 0
Enter an optional description; end it with an empty line:
> 
Reason for revocation: No reason specified
(No description given)
Is this okay? (y/N) y
ASCII armored output forced.
Revocation certificate created.Please move it to a medium which you can hide away; if Mallory gets
access to this certificate he can use it to make your key unusable.
It is smart to print this certificate and store it away, just in case
your media become unreadable.  But have some caution:  The print system of
your machine might store the data and make it available to others!
USERNAME@phoenix ~ %

Next, we will upload our GPG key to remote key servers. This allows for people to gain access to our public keys, and is necessary if anyone is going to send us encrypted information, or give us access via our authentication keys. For this I will just send you to the GPG instructions as to how to do so, in case they change in future versions.

Now, we can start actually using the keys we have just generated. First, lets set up SSH. For SSH, using a key is the only way I recommend connections. You do not want to allow password authentication to any machine you control. Additionally, you want to only be able to log in with a non-root user, and then authenticate to higher permissions. There is countless documentation as to why this is true, but in general someone is going to be able to crack your passwords far easier than any key-based login. We will use our authentication subkey, which for me is 43DDE8B2. The following commands, run on a remote machine, would immediately allow us to gain immediate SSH access to that machine.

USERNAME@phoenix ~ % gpg --recv-key 43DDE8B2
USERNAME@phoenix ~ % gpgkey2ssh 43DDE8B2 >> ~/.ssh/authorized_keys
USERNAME@phoenix ~ %

As for the password store, password managers are useful and allow for much easier management of per-account passwords. I do not re-use passwords between websites, which is always nice when you find out that a service has been compromised, I do not have to scurry around and figure out what websites I need to change things for. What I like most about using zx2c4’s Pass for this is that it integrates with GPG. Trust doesn’t have to be given to another service, nor do I need to embed any other plugins.

This sets up a fairly sound foundation for future work, such as enabling automatic GPG signing or encryption of email. It also encourages you to use more secure passwords for other services, and prevents security incident avalanches.

2 thoughts on “Setting up GPG

  1. Pingback: Basic Technology Security | Aeria Gloris

  2. Pingback: Securing SSH | Aeria Gloris

Comments are closed.