chore(All Markdown Files): auto wrap text, fix typos

This commit is contained in:
Ryan Yin
2024-03-16 19:45:36 +08:00
parent 1e38f7bb09
commit 0eb83b22f0
79 changed files with 2477 additions and 2896 deletions

View File

@@ -1,10 +1,14 @@
# GNU Privacy Guard(GnuPG)
> Offical Website: https://www.gnupg.org/
> Official Website: https://www.gnupg.org/
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.
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).
> 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:
@@ -20,18 +24,21 @@ Main usage scenarios of GnuPG:
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.
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.
> 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:
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/>
@@ -50,12 +57,14 @@ Related Docs:
- [Predictable, Passphrase-Derived PGP Keys][Predictable, Passphrase-Derived PGP Keys]
- [OpenPGP - The almost perfect key pair][OpenPGP - The almost perfect key pair]
GnuPG generate every secret key separately, and encrypt them with a symmetric key derived from your
passphrase. OpenPGP standard defines
[String-to-Key (S2K)](https://datatracker.ietf.org/doc/html/rfc4880#section-3.7) algorithm to derive
a symmetric key from your passphrase.
GnuPG generate every secret key separately, and encrypt them with a symmetric key derived from your passphrase.
OpenPGP standard defines [String-to-Key (S2K)](https://datatracker.ietf.org/doc/html/rfc4880#section-3.7)
algorithm to derive a symmetric key from your passphrase.
GnuPG's [OpenPGP protocol specific options](https://gnupg.org/documentation/manuals/gnupg/OpenPGP-Options.html#OpenPGP-Options) shows that:
GnuPG's
[OpenPGP protocol specific options](https://gnupg.org/documentation/manuals/gnupg/OpenPGP-Options.html#OpenPGP-Options)
shows that:
```
--s2k-cipher-algo name
@@ -81,24 +90,31 @@ gpg --s2k-mode 3 --s2k-count 65011712 --s2k-digest-algo SHA512 --s2k-cipher-algo
To use the strongest options globally, you can specify these options in your `~/.gnupg/gpg.conf`.
I've added them to my Home Manager's `programs.gpg.settings` option.
### 1. PGP Key(Primary Key) generation
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).
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.
> 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.
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.
``` bash
```bash
gpg --full-gen-key
gpg (GnuPG) 2.4.1; Copyright (C) 2023 g10 Code GmbH
This is free software: you are free to change and redistribute it.
@@ -131,9 +147,9 @@ Is this correct? (y/N) y
GnuPG needs to construct a user ID to identify your key.
Real name:
Email address:
Comment:
Real name:
Email address:
Comment:
You selected this USER-ID:
"Ryan Yin (For pass For Work ssh only) <ryan4yin@linux.com>"
@@ -163,7 +179,7 @@ sub cv25519 2024-01-09 [E] [expires: 2034-01-04]
The generated keys are stored in `~/.gnupg` by default, the functions of each file are as follows:
``` bash
```bash
tree ~/.gnupg/
/Users/ryan/.gnupg/
|-- S.gpg-agent # socket file
@@ -185,28 +201,41 @@ The generated keys are stored in `~/.gnupg` by default, the functions of each fi
4 directories, 12 files
```
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>
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.
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.
- `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**.
- `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 **delete 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...
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 **delete 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!
6. 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.
7. 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.
@@ -216,7 +245,7 @@ Now let's add the sub keys to the keypair we generated above:
> GnuPG will ask you to input your passphrase to unlock your primary key.
``` bash
```bash
gpg --expert --edit-key ryan4yin@linux.com
gpg (GnuPG) 2.4.1; Copyright (C) 2023 g10 Code GmbH
This is free software: you are free to change and redistribute it.
@@ -380,7 +409,7 @@ ssb ed25519 2024-01-09 [A] [expires: 2034-01-04]
gpg --list-public-keys
...
```
### 4. Backup & Restore
Export Public Keys(Both Primary Key & Sub Keys):
@@ -393,10 +422,12 @@ nix run nixpkgs#pgpdump ryan4yin-gpg-keys.pub
Export Primary Key(The exported key is still encrypted by your passphrase):
> the `!` at the end of the key ID is to force GnuPG to export only the specified key, not the subkeys.
> the `!` at the end of the key ID is to force GnuPG to export only the specified key, not the
> subkeys.
> GnuPG will ask you to input your passphrase to unlock your keypair,
> because GnuPG need to convert the secret key's format from its internal protection format to the one specified by the OpenPGP protocol.
> GnuPG will ask you to input your passphrase to unlock your keypair, because GnuPG need to convert
> the secret key's format from its internal protection format to the one specified by the OpenPGP
> protocol.
```bash
# replace the key ID with your own sec key's ID
@@ -416,16 +447,20 @@ Old: Secret Key Packet(tag 5)(134 bytes)
Hash alg - SHA1(hash 2)
Salt - 8c 78 58 c0 87 83 8c 2c
Count - 65011712(coded count 255)
IV - xx xx xx xx xx xx xx xx xx xx xx xx xx xx xx
IV - xx xx xx xx xx xx xx xx xx xx xx xx xx xx xx
Encrypted EdDSA x
Encrypted SHA1 hash
...
```
As [Predictable, Passphrase-Derived PGP Keys][Predictable, Passphrase-Derived PGP Keys] says, we'll find that gpg ignored the `--s2k-count` option we specified when generating the keypair, and the `--s2k` related options we specified in `~/.gnupg/gpg.conf`,
the exported primary key is protectd by `SHA1` and `AES128`, which is not secure enough!
As [Predictable, Passphrase-Derived PGP Keys][Predictable, Passphrase-Derived PGP Keys] says, we'll
find that gpg ignored the `--s2k-count` option we specified when generating the keypair, and the
`--s2k` related options we specified in `~/.gnupg/gpg.conf`, the exported primary key is protectd by
`SHA1` and `AES128`, which is not secure enough!
So to increase the security of the exported primary key, we need to encrypt it again with a stronger algorithm, I choose `age` here(which use `scrypt` to encrypt the file key with a provided passphrase):
So to increase the security of the exported primary key, we need to encrypt it again with a stronger
algorithm, I choose `age` here(which use `scrypt` to encrypt the file key with a provided
passphrase):
```bash
# for simplicity, use the same passphrase as your gpg keypair here
@@ -446,11 +481,14 @@ age --passphrase -o ryan4yin-gpg-subkeys.priv.age ryan4yin-gpg-subkeys.priv
rm ryan4yin-gpg-subkeys.priv
```
Your can import the exported Private Key via `gpg --import <keyfile>` to restore it, but you need to decrypt it via age first.
Your can import the exported Private Key via `gpg --import <keyfile>` to restore it, but you need to
decrypt it via age first.
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>`).
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>`).
To ensure security, delete the master key and revoke the certificate immediately after the backup is completed:
To ensure security, delete the master key and revoke the certificate immediately after the backup is
completed:
```bash
# delete the primary key and all its sub keys
@@ -522,7 +560,8 @@ gpg --decrypt <file>
gpg -d <file>
```
If you just want to encrypt/decrypt a file quickly, you can use `age` with a passphrase, `gpg` can also do this, but it's not recommended(as age(scrypt)'s more secure):
If you just want to encrypt/decrypt a file quickly, you can use `age` with a passphrase, `gpg` can
also do this, but it's not recommended(as age(scrypt)'s more secure):
```bash
# Encrypt a file via symmetric encryption(AES256), and output cleartext.
@@ -538,27 +577,41 @@ gpg -d <file>
### 7. Public Key Exchange & Revocation
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:
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).
- Client can verify the received 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**.
- 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.
- 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**.
- 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.
- 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.
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.
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.
Anyway, let's try to revoke a keypair:
@@ -615,7 +668,8 @@ STuJCp+gru6OtbTCu8Y2LugQeDh7UicM7Ak=
-----END PGP PUBLIC KEY BLOCK-----
```
As the revocation certificate says, we need to remove the first colon(`:`) before the 5 dashes(`-----BEGIN PGP PUBLIC KEY BLOCK-----`), then import it:
As the revocation certificate says, we need to remove the first colon(`:`) before the 5
dashes(`-----BEGIN PGP PUBLIC KEY BLOCK-----`), then import it:
```bash
gpg --import gpg-test-revoke.rev
@@ -646,7 +700,8 @@ gpg: 9E78E897B6490D6B: skipped: Unusable public key
gpg: README.md: encryption failed: Unusable public key
```
But if you delete the `trustdb.gpg` and `pubring.kbx`, then import the revoked public key again, it will be valid and usable again... which is very dangerous.
But if you delete the `trustdb.gpg` and `pubring.kbx`, then import the revoked public key again, it
will be valid and usable again... which is very dangerous.
## References
@@ -654,7 +709,8 @@ But if you delete the `trustdb.gpg` and `pubring.kbx`, then import the revoked p
- [Predictable, Passphrase-Derived PGP Keys][Predictable, Passphrase-Derived PGP Keys]
- [OpenPGP - The almost perfect key pair][OpenPGP - The almost perfect key pair]
[2021年用更现代的方法使用PGP]: https://ulyc.github.io/2021/01/13/2021%E5%B9%B4-%E7%94%A8%E6%9B%B4%E7%8E%B0%E4%BB%A3%E7%9A%84%E6%96%B9%E6%B3%95%E4%BD%BF%E7%94%A8PGP-%E4%B8%8A/
[2021年用更现代的方法使用PGP]:
https://ulyc.github.io/2021/01/13/2021%E5%B9%B4-%E7%94%A8%E6%9B%B4%E7%8E%B0%E4%BB%A3%E7%9A%84%E6%96%B9%E6%B3%95%E4%BD%BF%E7%94%A8PGP-%E4%B8%8A/
[Predictable, Passphrase-Derived PGP Keys]: https://nullprogram.com/blog/2019/07/10/
[OpenPGP - The almost perfect key pair]: https://blog.eleven-labs.com/en/openpgp-almost-perfect-key-pair-part-1/
[OpenPGP - The almost perfect key pair]:
https://blog.eleven-labs.com/en/openpgp-almost-perfect-key-pair-part-1/