Load Keys into YubiKey
This page covers setting up the YubiKey and loading your PGP keys into it.
Initial Setup
These are things you should do when you start using a new YubiKey.
Reset the OpenPGP app
If you want to "erase" everything about OpenPGP from the YubiKey and "start fresh", you can reset the OpenPGP app. Doing this will erase any keys stored in the YubiKey, and reset the PINs back to their factory-original state (which are explained below.)
Note that this is the only way to recover if you have entered the wrong Admin PIN too many times and totally locked up the OpenPGP app.
Yubico's documentation explains how to reset the OpenPGP app. Rather than trying to copy it, I'll just point you there.
⇒ Resetting the OpenPGP Application on the YubiKey
Set PINs
If you have not already done so, you should set your own PIN and Admin PIN codes.
-
The PIN code is what you will use on a regular basis, to do things like generate signatures, decrypt messages, or perform SSH authentication. If somebody enters the wrong PIN code too many times, the OpenPGP app will lock itself, and you will need to use the Admin PIN code (or PUK code, if you set one) to "unlock" the PIN.
ℹ️ For a new (or newly reset) YubiKey, this is
123456
. -
The Admin PIN code is used to load PGP keys into the YubiKey, or to change the YubiKey's OpenPGP settings. It can also be used to unlock the PIN code after the wrong PIN was entered too many times.
Note that it cannot be used to perform the day-to-day operations that you would normally use the PIN code for, and it cannot be used to "force-set" the PIN code. If you don't know the PIN code,
ℹ️ For a new (or newly reset) YubiKey, this is
12345678
. -
There is a third code, known as an "Reset Code". (You may also see the term "PUK code", which is the term used with the SIM cards used with GSM phones.)
If this code is set, it can be used to "unlock" the PIN code after too many invalid attempts, without allowing access to change settings or load new keys.
ℹ️ For a new (or newly reset) YubiKey, this code is not set.
ℹ️ These PINs only apply to the OpenPGP app.
If you use the same YubiKey for FIDO2, U2F, or PIV/CCID, and those systems require you to set up a PIN, they each have their own PINs which are totally separate from the PINs you use for OpenPGP.
Set Admin PIN
$ gpg --change-pin
gpg: OpenPGP card no. D27600012401xxxxxxxxxxxxxxxxxxxx detected
1 - change PIN
2 - unblock PIN
3 - change Admin PIN
4 - set the Reset Code
Q - quit
Your selection? 3
At this point your workstation will ask for the following, usually as separate prompts:
- The current Admin PIN (it will probably just say "the Admin PIN").
- The new Admin PIN.
- The new Admin PIN again, to verify that you typed it correctly.
PIN changed.
Set PIN
Next, set the PIN you'll use on a regular basis in order to generate signatures, decrypt messages, or perform SSH authentication.
1 - change PIN
2 - unblock PIN
3 - change Admin PIN
4 - set the Reset Code
Q - quit
Your selection? 1
- Enter the current PIN.
- Enter the new PIN.
- Enter the new PIN again.
Note that if the current PIN was wrong, this command will fail, you will receive a "Error changing the PIN: Bad PIN
" error, and the PIN failure counter will be updated. If you enter the wrong PIN too many times (usually 3, although this can be changed), the PIN will be "locked" and cannot be used without resetting it.
PIN changed.
Set a Reset Code
Once the PIN is set, you may want to set a Reset Code, but it isn't any less secure if you don't.
Personally I don't have one, but if I were managing YubiKeys for a company and might need to help a user who locked their YubiKey by entering the wrong PIN too many times, and they weren't able to physically bring the YubiKey to me, I would definitely want to be able to give them a code which unlocks their PIN without giving them full access to change everything on the card.
1 - change PIN
2 - unblock PIN
3 - change Admin PIN
4 - set the Reset Code
Q - quit
Your selection? 4
- Enter the Admin PIN (which you just set above).
- Enter the new Reset Code.
- Enter the new Reset Code again.
PIN changed.
ℹ️ Using the Reset Code
If you ever lock your normal PIN and need to use the Reset Code to reset it, do the following:
gpg --card-edit
admin
(to enable admin-level commands)unblock
For the record, I've only ever done this once, while writing this documentation, to make sure it worked as advertised. It accepted the PUK and allowed me to set a new PIN, which also reset the "bad PIN" counter back to zero.
Finished
When you're finished setting the PIN codes, use "q
" to finish.
1 - change PIN
2 - unblock PIN
3 - change Admin PIN
4 - set the Reset Code
Q - quit
Your selection? q
Personalize the Card
This section will involve storing information on the YubiKey which identifies you as the owner of the key.
$ gpg --card-edit
Enter some basic info about the "owner" of the card, along with their preferred language. This information is stored on the YubiKey, and will be visible to anybody who runs "gpg --card-info
" or "gpg --card-edit
" while the YubiKey is plugged in.
gpg/card> name
Cardholder's surname: Simpson
Cardholder's given name: John
gpg/card> login
Login data (account name): j..1@j....net
gpg/card> lang
Language preferences: en
You can also enter a URL where the corresponding public key can be downloaded. Doing this allows you to use the "gpg --edit-card
" command's "fetch
" sub-command to load your public keys into a new computer's keyring. PGPCards only hold secret keys - they don't hold public keys, user IDs, signatures, or expiration dates.
This is not required. If you don't have, or don't want, a copy of your public key saved on a web site somewhere, feel free to skip this step.
gpg/card> url
URL to retrieve public key: https://jms1.pub/jms1.pub.asc
You can also set a flag which tells the YubiKey to require the PIN to be entered, every time a signature is generated. Without this, you will be asked for the PIN the first time you generate one, and the YubiKey will "stay unlocked" and generate more signatures as requested, until it is unplugged from the computer.
gpg/card> forcesig
To see the updated state of the card, just hit RETURN at the "gpg/card>
" prompt.
gpg/card>
Reader ...........: Yubico Yubikey 4 OTP U2F CCID
Application ID ...: D27600012401xxxxxxxxxxxxxxxxxxxx
Version ..........: 2.1
Manufacturer .....: Yubico
Serial number ....: 06940447
Name of cardholder: John Simpson
Language prefs ...: en
Sex ..............: unspecified
URL of public key : https://jms1.pub/jms1.pub.asc
Login data .......: j..1@j....net
Signature PIN ....: forced
Key attributes ...: rsa4096 rsa4096 rsa4096
Max. PIN lengths .: 127 127 127
PIN retry counter : 3 0 3
Signature counter : 0
Signature key ....: [none]
Encryption key....: [none]
Authentication key: [none]
General key info..: [none]
When you're happy with the settings, use "q
" to exit the "gpg --card-edit
" command.
gpg/card> q
Remove and re-insert the Yubikey.
From this point forward, you will need to enter the PIN in order to make use of any keys, and you will need to enter the Admin PIN in order to load keys or change settings.
Load secret keys
The YubiKey's OpenPGP app has three "slots", each of which can hold the secret half of a PGP key or subkey. The slots are intended for keys with the Signature, Encryption, and Authentication flags. Be sure the keys you load into each slot have the appropriate capability flag (i.e. if a subkey only has the [E]
capability, don't load it into a slot other than the Encryption slot).
Which keys need to be sent?
If you only plan to use the YubiKey for SSH, you only need to load an Authentication key on the YubiKey. If you also plan to use the YubiKey for other PGP operations, you should load encryption and signature keys as well.
How do you clear the key from a slot?
I'm only aware of two ways to do this.
-
Load a different key into the same slot, which overwrites whatever key is currently there.
-
Reset the OpenPGP app. This clears all of the slots.
Of course, you then have to set everything up from scratch again. I've done this several times, once you're used to it the longest part of the process is waiting for Tails to finish booting on that ancient netbook with the world's slowest supposedly USB-3 port... 😒
Open the PGP key
Use "gpg --edit-key
" to work with the key.
$ gpg --edit-key 6353320118E1DEA2F38EAE806B2EDC90B5C6DC30
gpg (GnuPG/MacGPG2) 2.2.0; Copyright (C) 2017 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.
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg>
We will be using the key
command below to select or de-select subkeys. This command toggles the selection status of a subkey.
-
Each subkey is "numbered", although the numbers are not shown. Entering "
key 1
" will toggle the asterisk on the first "ssb
" entry, and so forth. -
It is possible to have multiple subkeys selected at the same time, however only one key or subkey can be selected when sending them to the YubiKey.
-
If no subkeys are selected (as in the example above), the primary key will be considered as selected, even though it will not have an asterisk after the "
sec
" label.
Be very careful about which key or subkey is selected when sending keys to the YubiKey.
Load the Authentication key
Make sure the Authentication subkey (the one with "usage: A
") is the only one selected.
gpg>
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg> key 2
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb* rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg>
As you can see, there is now an asterisk next to the second subkey, which has the "A
" capability, and there are no asterisks on any other subkeys.
Send the selected sub-key to the Authentication slot on the Yubikey (or the "card", as gpg
calls it.)
gpg> keytocard
Please select where to store the key:
(3) Authentication key
Your selection? 3
gpg>
Load the encryption key
In this case, we want to send the subkey with the "E
" capability, so first turn off the asterisk on the authentication subkey, then turn on the asterisk on the encryption subkey.
gpg>
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb* rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg> key 2
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg > key 1
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb* rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg>
Next, send the key to the card.
gpg> keytocard
Please select where to store the key:
(2) Encryption key
Your selection? 2
gpg>
Load the signature key
For this key, you're going to need a key or subkey with the "S
" capability.
-
In most cases, the primary key will be the only one with the "
S
" capability. If so, use thekey
command to make sure that NO subkeys have an asterisk next to them. (The example below shows this.) -
If you have a separate signing subkey, make sure that key is selected.
gpg>
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb* rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg > key 1
sec rsa4096/0x6B2EDC90B5C6DC30
created: 2017-05-27 expires: never usage: SC
trust: ultimate validity: ultimate
ssb rsa4096/0x297E5961AB566594
created: 2017-05-27 expires: never usage: E
ssb rsa4096/0xBA6C2A169C6C0F60
created: 2017-11-10 expires: never usage: A
[ultimate] (1). John M. Simpson <j..1@v......com>
[ultimate] (2) John M. Simpson <j..1@j....net>
gpg>
Send the key to the YubiKey.
gpg> keytocard
Really move the primary key? (y/N) y
Please select where to store the key:
(1) Signature key
(3) Authentication key
Your selection? 1
gpg>
Exit
Technically we're finished, BUT ... we need to be careful.
This next command will quit out of the "gpg --card-edit
" command, and it will ask if you want to save changes. IF YOU SAY YES, the secret keys you just installed on the YubiKey will be REMOVED from the secret keyring files on the computer.
Unless you are 100% sure that's what you want to do (i.e. if you have a known-good backup of the secret keys), BE SURE TO SAY NO.
gpg> q
Save changes? (y/N) n
Quit without saving? (y/N) y
Now if you query the card, you will see the keys in the three slots.
$ gpg --card-status
Reader ...........: Yubico Yubikey 4 OTP U2F CCID
Application ID ...: D27600012401xxxxxxxxxxxxxxxxxxxx
Version ..........: 2.1
Manufacturer .....: Yubico
Serial number ....: 06940447
Name of cardholder: John Simpson
Language prefs ...: en
Sex ..............: unspecified
URL of public key : https://jms1.net/6B2EDC90B5C6DC30.pub.asc
Login data .......: j..1@j....net
Signature PIN ....: not forced
Key attributes ...: rsa4096 rsa4096 rsa4096
Max. PIN lengths .: 127 127 127
PIN retry counter : 3 0 3
Signature counter : 0
Signature key ....: 6353 3201 18E1 DEA2 F38E AE80 6B2E DC90 B5C6 DC30
created ....: 2017-05-27 22:28:31
Encryption key....: 0660 766F 2768 F41F D4B9 1DB7 297E 5961 AB56 6594
created ....: 2017-05-27 22:28:31
Authentication key: BBA5 C6BB 23D2 B53B 0D0F 6C0B BA6C 2A16 9C6C 0F60
created ....: 2017-11-10 23:29:14
General key info..: pub rsa4096/0x6B2EDC90B5C6DC30 2017-05-27 John M. Simpson <j..1@v......com>
sec rsa4096/0x6B2EDC90B5C6DC30 created: 2017-05-27 expires: never
ssb rsa4096/0x297E5961AB566594 created: 2017-05-27 expires: never
ssb rsa4096/0xBA6C2A169C6C0F60 created: 2017-11-10 expires: never
Note that the information under "General key info" is coming from the keyring files on your computer. If you run "gpg --card-status
" on a computer whose keyring doesn't have your file yet, the last line will be ...
General key info..: [none]