I never remember how to deal with all of those, so I write an article for myself :) To choose options and method, I followed several articles on the web:
- Debian key generation
- Hacksanity serie, part 1 to 5
- Using an offline GnuPG master key
- Using GnuPG for SSH authentication
And a few others (french):
Ensuring a clean setup
I consider not having an existing key. If so first kill gpg-agent
and move the keyring.
$ gpgconf --kill gpg-agent
$ unset GPG_AGENT_INFO
# also check there is no other security related process running
# mostly from any desktop environment or web browsers or what's not
$ tar -cf previous-keyring.tar ~/path/to/current-gnupg-home
Set the new GnuPGg home (I prefer XDG standard directories)
$ export GNUPGHOME=$XDG_CONFIG_DIR/gnupg
$ mkdir -p $GNUPGHOME
$ chmod 700 $GNUPGHOME
$ gpg -k
GnuPG config should be ok by default so no need to edit it.
For the sake of examples, I’ll use the following environment variables and/or values for some specific purpose:
- email (identity):
example@freedom.email
- fingerprint:
$FINGERPRINT
- key grip:
$KEYGRIP
Create the keys the hard way
Master key
The goal will be to have a detached master key, not using it but for managing keys (no sign, no crypt, no auth) so we can choose the algo we want without worrying about compatibility for recipients.
To create only a certifying master key, you must enter the expert mode (not much more than the classic mode):
$ gpg --expert --full-generate-key
# * choose ECC (set your own capabilities)
# * keep Certifiate only (remove Sign) then Quit
# * choose the 25519 Curve
# * I keep my master key valid for 2 years (2y)
#
# * choose an identity (name then email), no comment
# * choose a very strong passphrase
GnuPG creates a revocation certificate that wont be used. It’s better to generate one when needed, and to delete the one that was created.
Elliptic Curve subkeys
We will create elliptic curve (EC) because now they seem to be the default. So lets create subkeys for each role (sign, crypt and auth), editing the key from its fingerprint (printed when then key has been generated, under the pub part, can use only the 4 bytes (8 hexa characters):
$ gpg --edit-key --expert $FINGERPRINT
gpg> addkey
# select ECC (sign only)
# then the type Curve 25519
# and a one year validity (1y), less than the master key
Do the same for ECC (encrypt only), and ECC (set your own capabilities, then choose authenticate only).
So we have a master key (sec) with 3 elliptic curve subkeys:
- a Signing key
- an enCrypting key
- an Authentication key
Let’s save to be sure they are stored.
gpg> save
Adding another identity
If I want to add another email to my master key:
$ gpg --edit-key --expert $FINGERPRINT
gpg> adduid
# then set one primary first selecting it (let's say it's the second one we just
# created)
gpg> uid 2
gpg> primary
gpg> save
The primary identity is shown with a dot (.
) after the identity number.
Publish keys
Using keys.openpgp.org
:
$ grep keyserver $GNUPGHOME/gpg.conf
keyserver hkps://keys.openpgp.org
$ gpg --send-keys $FINGERPRINT
Backup keys
Create a temporary folder:
$ mkdir $HOME/gpg-backup
$ chmod 700 $HOME/gpg-backup
$ cd $HOME/gpg-backup
Then generate the backup of private/public keys with master key:
$ gpg -o identity-backup.gpg --export-secret-keys example@freedom.email
When we will have people using our keys and us using their keys, we will import their public keys and set a trust level on them, so it’s good to save those when they change too:
$ pwd
/home/me/gpg-backup
$ gpg -o public-keys.gpg --export
$ gpg --export-ownertrust > ownertrust.txt
Now it’s good to move that backup to a secure place, or better, two of them. Of course do not put the backup on an encrypted usbkey that’s encrypted with this key…
Backup on a physical paper
It’s said making a paper backup of the private key is a good idea:
$ paperkey --secret-key backup.gpg > paperkey.txt
To restore, scanning the paper with OCR will be needed, and use again:
$ paperkey --pubring public-keys.gpg --secrets paperkey.txt --output identity-backup.gpg
Restore backup
# if needed:
$ mkdir $GNUPGHOME; chmod 700 $GNUPGHOME
# then from the backup directory:
$ gpg --import identity-backup.gpg
$ gpg --import public-keys.gpg
$ gpg --import-owertrust < ownertrust.txt
Set master key offline
I will be necessary to restore the master key each time an action will be needed on the set of keys (adding or revoking keys, signing others key):
# get the keygrip of the master key (the one with `sec`):
$ gpg --list-keys --with-keygrip example@freedom.email
# move it to a secure storage:
$ mv $GNUPGHOME/private-keys-v1.d/${KEYGRIP}.key /my/secure/location
Reuse it
Do the exact opposite action
$ cp /my/secure/location/${KEYGRIP}.key $GNUPGHOME/private-keys-v1.d
# then actions needing the private master key can be done
$ gpg --edit-keys example@freedom.email
Revoke a key
Sub-key
# once in gpg, select the key in the list (start from 0), it will appear with
# an asterisk
$ gpg --edit-key example@freedom.email
gpg> key 2
gpg> revkey
gpg> save
# update servers
$ gpg --send-keys $FINGERPRINT
Master-key
# create revoke key
$ gpg --output revoke-${FINGERPRINT}.asc --gen-revoke ${FINGERPRINT}
# import the revoke key in our key
$ gpg --import revoke-${FINGERPRINT}.asc
# update servers
$ gpg --send-keys $FINGERPRINT
Delete a revoked key
For a subkey use the same logic than to revoke a subkey, but use delkey
command in gpg
instead.
For the masterkey, it’s necessary to delete the private key before deleting the public one
$ gpg --delete-secret-key $FINGERPRINT
$ gpg --delete-key $FINGERPRINT