GPG on your computer
This walkthrough takes you from a fresh badge to a working OpenPGP key on your computer: generate the keys on the badge, get the public key into GnuPG, then sign, encrypt and decrypt real files. The private keys never leave the badge.
For the feature reference (key roles, curves, PIN semantics, every serial command) see GPG / OpenPGP & SSH.
What you need
Section titled “What you need”- A badge with GPG keys (this page generates them in step 1).
- GnuPG on your computer:
- macOS:
brew install gnupg pinentry-mac - Linux (Debian/Ubuntu):
sudo apt install gnupg scdaemon - Windows: install Gpg4win (
winget install GnuPG.Gpg4win).
- macOS:
- A serial terminal at 115200 baud to read the badge console (any terminal
works; the firmware repo ships
tools/helpers).
Check GnuPG is installed:
$ gpg --version1. Generate keys on the badge
Section titled “1. Generate keys on the badge”From the badge main menu open GPG ▸ Generate Keys and follow the wizard:
- Enter a Name.
- Enter an optional Email (combined into a
Name <email>user-id). - Choose the Curve: Ed25519 (recommended) or P-256.
One run creates all three keys: a signature key, a decryption key and an authentication key. The signature and authentication keys are the chosen curve; the decryption key is always P-256.
2. Plug in and find the card
Section titled “2. Plug in and find the card”Plug the badge into USB. The badge presents an OpenPGP smartcard, so GnuPG sees it like a YubiKey:
$ gpg --card-statusReader ...........: CDC BadgeV1Application type .: OpenPGPSerial number ....: BA755010Signature key ....: A88F A2BB B450 CB1E 3A20 A170 ABC0 15BA 827C 44E0Encryption key....: E487 CB0B B44C 6708 857A 2CCF 38F1 4AB4 9DCE F583Authentication key: 080F E598 AB94 1D27 9B80 478B 0F93 0164 13AA 70D2The Reader line names the badge and Application type is OpenPGP. If the
reader is not found, restart the smartcard daemon with gpgconf --kill scdaemon
and try again. Only one program can hold the card at a time.
3. Import your key and link it to the badge
Section titled “3. Import your key and link it to the badge”The badge generated the keys itself, so GnuPG does not have the public key yet:
gpg --card-status only shows the fingerprints. Export the public key over the
serial console and import it.
In your serial terminal (115200 baud), type:
GPG EXPORTThe badge prints an ASCII-armored OpenPGP block:
-----BEGIN PGP PUBLIC KEY BLOCK-----...-----END PGP PUBLIC KEY BLOCK-----Copy the whole block (including the BEGIN/END lines and the blank line after
the header) into a file mykey.asc, then import and link it to the card:
$ gpg --import mykey.asc$ gpg --card-statusConfirm the key is there with both a signing primary key [SCA] and an
encryption [E] subkey:
$ gpg --list-keyspub ed25519 ... [SCA] A88FA2BBB450CB1E3A20A170ABC015BA827C44E0uid Your Name <you@example.com>sub nistp256 ... [E]That [E] subkey is what lets other people encrypt to you and what the badge
decrypts in step 6.
The matching private keys never leave the badge. The gpg --card-status you
just ran also recorded them as on-card stubs, which you can see with:
$ gpg --list-secret-keyssec> ed25519 ... [SCA] A88FA2BBB450CB1E3A20A170ABC015BA827C44E0 Card serial no. = 4344 BA755010uid Your Name <you@example.com>ssb> nistp256 ... [E] E487CB0BB44C6708857A2CCF38F14AB49DCEF583 Card serial no. = 4344 BA755010The > after sec / ssb and the Card serial no. line mean GnuPG holds only
a reference: the actual secret keys stay on the badge. Every signature (step 5)
and decryption (step 7) runs on the badge and asks for the User PIN (PW1).
4. Share and import public keys
Section titled “4. Share and import public keys”Your own mykey.asc is safe to hand out: give it to anyone who wants to send you
encrypted files or verify your signatures, or publish it wherever you like. It
contains only public material.
To encrypt a file to someone (step 6), you first need their public key in GnuPG. There are two ways to get it:
-
From a file they gave you:
Terminal window $ gpg --import their-key.asc -
From your badge, if they sent you their key over Bluetooth: it now lives under GPG ▸ Received Keys. Pull it onto the computer over the serial console as shown in Getting an exchanged key onto a computer below, then
gpg --importthe saved block.
Either way, gpg --list-keys then lists their key with an [E] subkey, ready to
encrypt to.
5. Sign a file with the badge
Section titled “5. Sign a file with the badge”Signing runs on the badge: GnuPG hands the data to the card, the badge signs it with the on-card signature key, and asks for the User PIN (PW1). The private key never leaves the device.
$ gpg --detach-sign -u <YOUR_FINGERPRINT> report.pdf$ gpg --verify report.pdf.sig report.pdfUse --clearsign for text you want to keep readable.
6. Encrypt a file for someone else
Section titled “6. Encrypt a file for someone else”Encrypting to a recipient uses their public key, not the badge, so this step needs no PIN:
$ gpg --encrypt --recipient friend@example.com document.txtTo sign with the badge and encrypt in one step, combine both. The signature runs on the badge and asks for the User PIN (PW1); the encryption uses the recipient’s public key:
$ gpg --sign --encrypt -r friend@example.com -u <YOUR_FINGERPRINT> document.txt7. Decrypt a file sent to you
Section titled “7. Decrypt a file sent to you”When someone encrypts a file to your key, the badge does the decryption with its decryption key, so it asks for the User PIN (PW1):
$ gpg --decrypt secret.gpgGnuPG talks to the badge over the smartcard interface; the private key never leaves the device.
Badge-to-badge key exchange and cross-signing
Section titled “Badge-to-badge key exchange and cross-signing”Two badges can exchange and cross-sign each other’s keys over Bluetooth, without a computer. The full round trip:
- Send your key. On the first badge open GPG ▸ Send Key, pick the other badge, and confirm the matching number on both. The other badge stores it under GPG ▸ Received Keys.
- Cross-sign. On the receiving badge open GPG ▸ Received Keys, select the entry and choose Cross-Sign. The badge certifies that key with its own signature key.
- Send the signature back. Choose Send Signature to return the certification to the key’s owner over Bluetooth.
- Collect it. On the original badge the returned certification appears under GPG ▸ My Certifications.
A certification only lands under My Certifications if it actually targets that badge’s own key; one sent to the wrong badge is discarded.
Getting an exchanged key onto a computer
Section titled “Getting an exchanged key onto a computer”A key you received over Bluetooth lives in Received Keys. To use it in GnuPG, read it over the serial console (115200 baud) by its list index:
GPG RECV_LISTOK: 1 received keys[0] Alice Example <alice@example.com> FP: F832D01E... Signed: No
GPG RECV_EXPORT 0-----BEGIN PGP PUBLIC KEY BLOCK-----...-----END PGP PUBLIC KEY BLOCK-----GPG RECV_EXPORT prints the peer’s key with its encryption subkey. You do not
need to cross-sign it first; cross-signing only adds your own certification (the
web-of-trust step above). Save the block to their-key.asc and import it:
$ gpg --import their-key.asc$ gpg --list-keys alice@example.compub ed25519 ... [SCA] F832D01E763213413BA9ABFEFCC74F9458C137BEuid Alice Example <alice@example.com>sub nistp256 ... [E]The [E] subkey means you can now encrypt to that peer (step 6). If you have
cross-signed the key, GPG RECV_EXPORT additionally carries your certification.
When you export your own key (GPG ▸ Export Public or GPG EXPORT), every
certification collected under My Certifications is attached automatically, so
a single gpg --import rebuilds your web of trust.
Stuck?
Section titled “Stuck?”- Card not found:
gpgconf --kill scdaemon, thengpg --card-statusagain. Only one program can hold the smartcard at a time. gpghangs on a PIN prompt in scripts: add--pinentry-mode loopback --passphrase <PW1>.No encryption subkey: re-import withGPG EXPORT(step 3); the imported key must show the[E]subkey.- PIN attempts: the User PIN allows 3 tries, then it blocks. Reset a blocked
User PIN from the host with the Admin PIN (
gpg --admin▸unblock). Never guess PINs.