The GNU Privacy Guard is a complete and free implementation of the OpenPGP standard as defined by RFC4880 (also known as **PGP**). GnuPG allows to encrypt and sign your data and communication, features a versatile key management system as well as access modules for all kind of public key directories.
> In the following content, we will use GPG to refer to GnuPG tool, and PGP to refer to various concepts defined in the OepnPGP standard(e.g. PGP key, PGP key server).
Key functions of GnuPG:
1. Keypair(keyring) management
2. Sign and Verify your data
3. Encrypt and Decrypt your data
Main usage scenarios of GnuPG:
1. Sign or encrypt your email
1. Verify or decrypt the email you received
2. Sign your git commit
3. Manage your ssh key
4. Encrypt your data and store it somewhere.
GnuPG/OpenPGP is complex, so while using it, I have been looking forward to finding an encryption tool that is simple enough, functional enough, and widely adopted.
Currently I use both age & GnuPG:
1. Age for secrets encryption(ssh key & other secret files), it's simple and easy to use.
2. GnuPG for password-store and email encryption.
> At present, the safe and efficient use of GPG is probably combined with hardware keys such as yubikey. but I don't have one, so I won't talk about it here.
## Practical Cryptography for Developers
To use GnuGP without seamlessly, Some Practical Cryptography knowledge is required, here is dome tutorials:
- English version: <https://github.com/nakov/Practical-Cryptography-for-Developers-Book>
- Chinese version: <https://thiscute.world/tags/cryptography/>
## Overview of GnuPG
> GnuPG's Official User Guides: <https://www.gnupg.org/documentation/guides.html>
Key management is the core of OpenPGP standard / GnuPG.
GnuPG uses public-key cryptography so that users may communicate securely. In a public-key system, each user has a pair of keys consisting of a private key and a public key. **A user's private key is kept secret; it need **never be revealed. The public key may be given to anyone with whom the user wants to communicate**. GnuPG uses a somewhat more sophisticated scheme in which a user has a primary keypair and then zero or more additional subordinate keypairs. The primary and subordinate keypairs are bundled to facilitate key management and the bundle can often be considered simply as one keypair, or a keyring/keychain(which contains multiple sub key-pairs).
Let's generate a keypair interactively:
> Now in 2024, GnuPG 2.4.1 defaults to ECC algorithm (9) and Curve 25519 for ECC, which is morden and safe, I would recommend to use these defaults directly.
```bash
gpg --full-gen-key
```
This command will ask you for some algorithm related settings(ECC & Curve 25519), your personal info, and a strong passphrase to protect your PGP key. e.g.
The functions of most files are quite clear at a glance, but the `trustdb.gpg` in them is a bit difficult to understand. Here are the details: <https://www.gnupg.org/gph/en/manual/x334.html>
Home Manager will manage all the things in `~/.gnupg/` EXCEPT `~/.gnupg/openpgp-revocs.d/` and `~/.gnupg/private-keys-v1.d/`, which is expected.
### 3. Sub Key Generation & Best Practice
In PGP, every keys has a **usage flag** to indicate its usage:
- `C` means this key can be used to **Certify** other keys, which means this key can be used to **create/delete/revoke/modify** other keys.
- `S` means this key can be used to **Sign** data.
- `E` means this key can be used to **Encrypt** data.
- `A` means this key can be used to **Authenticate** data with various non-GnuPG programs. The key can be used as e.g. an **SSH key**.
The **best practice** is:
1. Generate a primary key with strong cryptography arguments(such as ECC + Curve 25519).
2. Then generate 3 sub keys with `E`, `S` and `A` usage flag respectively.
3. **The Primary Key is extremely important**, Backup the primary key to somewhere absolutely safe(such as two encryptd USB drivers, keep them in different places), and then **delte it from your computer immediately**.
4. The sub key is also important, but you can generate a new one and replace it easily. You can backup it to somewhere else, and import it to another machine to use your keypair.
5. Backup your Primary key's revocation certificate to somewhere safe, it's the last way to rescure your safety if your primary key is compromised!
1. It's a big problem if your revocation certificate is compromised, but not the bigest one. because it's only used to revoke your keypair, your data is still safe. But you should generate a new keypair and revoke the old one immediately.
1. It will be a big problem if your primary key is compromised, and you don't have a revocation certificate to revoke it. But since OpenPGP do not have a good way to distribute revocation certificate, even you have a revocation certificate, it's still hard to distribute it to others...
To keep your keypair safe, you should backup your keypair according to the following steps.
Now let's add the sub keys to the keypair we generated above:
> `E` sub key is already generated by default, so we only need to generate `S` and `A` sub keys.
> GnuPG will ask you to input your passphrase to unlock your primary key.
Export Sub Keys one by one(The exported key is still encrypted by your passphrase):
```bash
gpg --armor --export-secret-subkeys
```
Your can import the exported Private Key via `gpg --import <keyfile>` to restore it.
As for Public Keys, please import your publicKeys via Home Manager's `programs.gpg.publicKeys` option, DO NOT import it manually(via `gpg --import <keyfile>`).
### 5. Signing & Verification
```bash
# Make a cleartext signature.
gpg --clearsign <file>
# Make a detached signature, with text output.
gpg --armor --detach-sign <file>
# verify the file contains a valid signature.
gpg --verify <file>
# verify the file with a detached signature.
gpg --verify <file> <signature-file>
```
### 6. Encryption & Decryption
```bash
# Encrypt a file via recipient's public key, sign it via your private key for signing, and output cleartext.
# so that the reciiptent can decrypt it via his/her private key.
In the case of many users, it is very difficult to exchange public keys securely and reliably with each other.
In the Web world, There is a **Chain of Trust**** to resolve this problem:
- A Certificate Authority(CA) is responsible to verify & sign all the certificate signing request.
- Web Server can safely transmit its Web Certificate to the client via TLS protocol.
- Client can verify the recevied Web Certificate via the CA's root certificate(which is built in Browser/OS).
But in OpenPGP:
- There is key servers to distribute(exchange) public keys, but it **do not verify the identity of the key owner**, and any uploaded data is **not allowed to be deleted**. Which make it **insecure and dangerous**.
- Why key server is dangerous?
- Many PGP novices follow various tutorials to upload various key with personal privacy (such as real names) to the public key server, and then find that they can't delete them, which is very embarrassing.
- Anyone can upload a key to the key server, and claim that it is the key of a certain person(such as Linus), which is very insecure.
- **key server** is not recommend to use.
- GnuPG will generate revocation certificate when generating keypair(`~/.gnupg/private-keys-v1.d/<Key-ID.rev>`), anyone can import this certificate to revoke the keypair. But OpenPGP standard **DO NOT provide a way to distribute this certificate to others**.
- Not to mention some key status query protocol like OCSP in Web PKI.
- Users has to pulish their revocation certificate to their blog, github profile or somewhere else, and others has to check it and run `gpg --import <revocation-certificate>` to revoke the keypair manually.
In summary, **there is no good way to distribute public keys and revoke them in OpenPGP**, which is a big problem.
Currently, You have to distribute your public key or revocation certificate via your blog, github profile, or somewhere else, and others has to check it and run `gpg --import` to import your public key or revocation certificate manually.
@@ -10,12 +10,6 @@ In addition, we further improve the security of secrets files by storing them in
This directory contains this README.md, and a `nixos.nix`/`darwin.nix` that used to decrypt all my secrets via agenix, and then I can use them in this flake.
> All the operations in this section should be performed in my private repository: `nix-secrets`.
Reference in New Issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.