Gpg4winとGit for Windowsでgithubを使う②：gpg鍵生成と登録

## はじめに
構築したGpg4winとGit for Windowsの環境で、鍵を生成してgithubにssh/gpg鍵を登録します。

## gpgでの鍵の生成
メールアドレスは，github の Settings > Email で確認できます。「Keep my email private」有効の時は，github が生成したメールアドレスを使います。

### gpg鍵生成
gpg鍵を生成します。速度やセキュリティ面からECC鍵，Curve 25519が良いです。
```
C:\Users\xxx>gpg --expert --full-generate-key
gpg (GnuPG) 2.4.3; Copyright (C) 2023 g10 Code GmbH
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Please select what kind of key you want:
   (1) RSA and RSA
   (2) DSA and Elgamal
   (3) DSA (sign only)
   (4) RSA (sign only)
   (7) DSA (set your own capabilities)
   (8) RSA (set your own capabilities)
   (9) ECC (sign and encrypt) *default*
  (10) ECC (sign only)
  (11) ECC (set your own capabilities)
  (13) Existing key
  (14) Existing key from card
Your selection? 9
Please select which elliptic curve you want:
   (1) Curve 25519 *default*
   (2) Curve 448
   (3) NIST P-256
   (4) NIST P-384
   (5) NIST P-521
   (6) Brainpool P-256
   (7) Brainpool P-384
   (8) Brainpool P-512
   (9) secp256k1
Your selection? 1
Please specify how long the key should be valid.
         0 = key does not expire
      <n>  = key expires in n days
      <n>w = key expires in n weeks
      <n>m = key expires in n months
      <n>y = key expires in n years
Key is valid for? (0)
Key does not expire at all
Is this correct? (y/N) y

GnuPG needs to construct a user ID to identify your key.

Real name: [githubアカウント名]
Email address: [メールアドレス]
Comment:
You selected this USER-ID:
    "[githubアカウント名] <[メールアドレス]>"

Change (N)ame, (C)omment, (E)mail or (O)kay/(Q)uit? O
We need to generate a lot of random bytes. It is a good idea to perform
some other action (type on the keyboard, move the mouse, utilize the
disks) during the prime generation; this gives the random number
generator a better chance to gain enough entropy.
We need to generate a lot of random bytes. It is a good idea to perform
some other action (type on the keyboard, move the mouse, utilize the
disks) during the prime generation; this gives the random number
generator a better chance to gain enough entropy.
gpg: revocation certificate stored as 'C:\\Users\\xxx\\AppData\\Roaming\\gnupg\\openpgp-revocs.d\\[鍵ID].rev'
public and secret key created and signed.

pub   ed25519 2024-03-21 [SC]
      [鍵ID]
uid                      [githubアカウント名] <[メールアドレス]>
sub   cv25519 2024-03-21 [E]
```

### ssh用の鍵を追加
キーの役割としてA(Authenticate)を指定したサブキーを追加します。
速度やセキュリティ面からECC鍵，Curve 25519が良いです。
```
C:\Users\xxx>gpg --expert --edit-key [鍵ID]
gpg (GnuPG) 2.4.3; Copyright (C) 2023 g10 Code GmbH
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  ed25519/[サブ鍵ID1]
     created: 2024-03-21  expires: never       usage: SC
     trust: ultimate      validity: ultimate
ssb  cv25519/[サブ鍵ID2]
     created: 2024-03-21  expires: never       usage: E
[ultimate] (1). [githubアカウント名] <[メールアドレス]>

gpg> addkey
Please select what kind of key you want:
   (3) DSA (sign only)
   (4) RSA (sign only)
   (5) Elgamal (encrypt only)
   (6) RSA (encrypt only)
   (7) DSA (set your own capabilities)
   (8) RSA (set your own capabilities)
  (10) ECC (sign only)
  (11) ECC (set your own capabilities)
  (12) ECC (encrypt only)
  (13) Existing key
  (14) Existing key from card
Your selection? 11

Possible actions for this ECC key: Sign Authenticate
Current allowed actions: Sign

   (S) Toggle the sign capability
   (A) Toggle the authenticate capability
   (Q) Finished

Your selection? S

Possible actions for this ECC key: Sign Authenticate
Current allowed actions:

   (S) Toggle the sign capability
   (A) Toggle the authenticate capability
   (Q) Finished

Your selection? A

Possible actions for this ECC key: Sign Authenticate
Current allowed actions: Authenticate

   (S) Toggle the sign capability
   (A) Toggle the authenticate capability
   (Q) Finished

Your selection? Q
Please select which elliptic curve you want:
   (1) Curve 25519 *default*
   (2) Curve 448
   (3) NIST P-256
   (4) NIST P-384
   (5) NIST P-521
   (6) Brainpool P-256
   (7) Brainpool P-384
   (8) Brainpool P-512
   (9) secp256k1
Your selection? 1
Please specify how long the key should be valid.
         0 = key does not expire
      <n>  = key expires in n days
      <n>w = key expires in n weeks
      <n>m = key expires in n months
      <n>y = key expires in n years
Key is valid for? (0)
Key does not expire at all
Is this correct? (y/N) y
Really create? (y/N) y
We need to generate a lot of random bytes. It is a good idea to perform
some other action (type on the keyboard, move the mouse, utilize the
disks) during the prime generation; this gives the random number
generator a better chance to gain enough entropy.

sec  ed25519/[サブ鍵ID1]
     created: 2024-03-21  expires: never       usage: SC
     trust: ultimate      validity: ultimate
ssb  cv25519/[サブ鍵ID2]
     created: 2024-03-21  expires: never       usage: E
ssb  ed25519/[サブ鍵ID3]
     created: 2024-03-21  expires: never       usage: A
[ultimate] (1). [githubアカウント名] <[メールアドレス]>

gpg> save
```

用途が[A]になっているサブ鍵ID3のkeygripを表示します。
```
C:\Users\xxx>gpg --with-keygrip --keyid-format LONG --list-key [鍵ID]
pub   ed25519/[サブ鍵ID1] 2024-03-21 [SC]
      [鍵ID]
      Keygrip = [キーグリップ1]
uid                 [ultimate] [githubアカウント名] <[メールアドレス]>
sub   cv25519/[サブ鍵ID2] 2024-03-21 [E]
      Keygrip = [キーグリップ2]
sub   ed25519/[サブ鍵ID3] 2024-03-21 [A]
      Keygrip = [キーグリップ3]
```

keygripは`2C2689B1DC6635E575C254ABBADBEEFF7051DAE6`のような16進数の文字列です。
このkeygripを、プロファイルフォルダの`AppData\Roaming\gnupg\sshcontrol`に書きます。
用途が[A]ではない鍵のものは不要です。
ssh認証に使いたい鍵が複数ある時は、一行に一つずつkeygripを書きます。
```
[キーグリップ3]
```

以下のコマンドで、ssh認証に使うことのできる鍵の一覧が出ます。
githubに登録するキー（後の手順の`gpg --export-ssh-key`で出力）と同じものが表示されるはずです。
```
C:\Users\taniz>ssh-add -L
ssh-ed25519 AAAABADzaC1lZDI1NTE5AAAAIEOjOUYmG1fGbGyqhaxMAgTJGcwgVIY8lESNoi4vDBAD (none)
```

## github への鍵登録
コミットへの署名のためgpg鍵を、sshアクセスのためにssh鍵を追加します。

### gpg鍵
以下の手順でエクスポートし、githubの Settings > SSH and GPG keys のGPG keysに登録します。
```
C:\Users\xxx>gpg --armor --export [鍵ID]
-----BEGIN PGP PUBLIC KEY BLOCK-----

mDMEZfxIiBYJKwYBBAHaRw8BAQdAmLtT3hMigGrMWiF0gqXgQGhhSP7nqRWZCEIc
... [snip] ...
PVsKXDwQnMVXpFcA/ifnP1FdBqdsmwI8SyyVoWk/lfl3OviIS4np2+Or4IYG
=3KQa
-----END PGP PUBLIC KEY BLOCK-----

C:\Users\taniz>
```

### ssh鍵
以下の手順でエクスポートし、githubの Settings > SSH and GPG keys のSSH keysに登録します。キーの種類はAuthentication key です。
```
C:\Users\xxx>gpg --export-ssh-key [鍵ID]
ssh-ed25519 AAAABADzaC1lZDI1NTE5AAAAIEOjOUYmG1fGbGyqhaxMAgTJGcwgVIY8lESNoi4vDBAD openpgp:0xEFEE6BAD
```

## 動作確認
以下のコマンドでgithubにアクセスします。githubアカウント名が表示されるはずです。
```
C:\Users\xxx>ssh -T git@github.com
Hi [githubアカウント名]! You've successfully authenticated, but GitHub does not provide shell access.
```