旅とプログラミングを少々

趣味に関する記録などをします。おそらくプログラミング入門に関しての内容を連ねていきます。

家庭内トラストレス化へ向けての認証局

域内だけに公開しているhttpサービスを網全体を信用するのではなく、クライアント毎にアクセスを認可したい。ユーザ管理があるわけでもないのでIdPを使うのは難しいと判断し、クライアント認証を行う。

略語・専門用語

CA

Certificate authority.

証明書が信頼できると検証できる形で認証してくれるもの。CAが信頼できると言ってるなら自分も信頼できるな、と言えるような権威。

実態としてはbasicContrtaintsCA:Trueを持つ証明書の秘密鍵で、あなたが信頼できる手段で公開鍵を入手しているもの。「CAが信頼できると言ってる奴が信頼できると言ってる奴が信頼できると言ってるなら自分も信頼できるな」という具合で最大でPathLenの回数だけ多段に認証を信用できる。

csr

Certificate Signing Request (Certification Req.).

自分が何者であるかと保持する鍵をまとめて署名してもらう要求。csrと公開鍵を渡して証明書(crtファイル)を返してもらう。

現代のWeb業界だと多分PKCS#10(RFC2986)形式以外見る機会がないが必要な項目を適切に書いてあればcsrではあるので他でも用語としては使う。HTMLのタグ関連で歴史的文書の中ではweb業界でも別の形式のcsrが見られるかもしれない。

crl

Certificate Revocation List

期限内だけれど信頼しちゃ駄目な証明書のリスト。なんかの事故とかで信頼性を担保できないのに署名しちゃった証明書が生まれた時にそれを排除するためにある仕組みだが、ブラウザくらい目が届いているもの以外実態としてクライアント側がきちんとチェックしきれていないと思う。家庭内トラストレス化でも事故が起きたらAuthorityを変えて再配布でこと足りるため、無視される。

crt

Certificate.

証明書に一般的に使われる拡張子。web業界だとX.509形式以外見ないと思われる。この証明書を持っている者が何であり、その事をどのAuthorityが署名したかが書いてあり、署名を検証する事で信頼性を保証する。署名済み公開鍵。 エンコードとしてはpemが多いが、windowsだとバイナリのder形式も一般的らしい。

key

一般的には秘密鍵の拡張子によく用いられるが、多分定められた標準はない。

pem

base64フォーマットされた証明書関連のあれこれのコンテナフォーマット。RFC1421,1422,1423,1424あたりで定義されたPrivacy Enhanced Mail用に作られた。PEMのメールは使われていないがコンテナとして便利なのでこれだけは現在でも使われている。 X.509形式の証明書、あるいは証明書の署名を検証していってルート証明書まで検証した結果、あるいはPKCS#10形式もPEM形式に変換できるのでCSRかもしれない。コンテナなのでこれだけでは中身が何かはわからない。

pkcs#12

RFC7292形式。拡張子としては.pfx .p12あたりが使われる。

証明書や、公開鍵と秘密鍵のセットといった複数の鍵をまとめて暗号化するフォーマット。

家庭内では物理的手段で信頼できる通信路が確保できる事が多く、必要性よりもブラウザ等で手軽に読み込むための利便性のために使う。

認証局作成手順

実態はちょっと珍しい制約を持つ秘密鍵と公開鍵である。有効なCAは公開鍵を信頼できる手段で多くの環境に配布済みであるが、オレオレ認証局はなんらかの方法で公開鍵を渡さない限り検証できない。 家庭内での使用ということでスクラップアンドビルドや再配布が容易であり、ルートとイシュアー認証局を分けずに使う。 環境はUbuntu 18.04(多分)。家庭用なので。

# apt install openssl
# cd /usr/local/share
# mkdir -p pki/CA
# cd pki
# cp /usr/lib/ssl/misc/CA.pl ./
# cp /etc/ssl/openssl.cnf ./

コピーしてきたCA.plを修正する。

$CATOP="./CA";

コピーしてきたopenssl.cnfを修正する。

[ CA_default ]
dir             = ./CA
# これで続く行がCA.plが適当に作るディレクトリ類を適切に指しているはず。
[ req_distinguished_name ]
countryName_default = JA
# その他distinguished_nameのデフォルトも適当に書いておくと便利。
[ v3_ca ]
# CA.pl --newcaが読む部分。`-extensions v3_ca`と書いてあるはず。CA自体の証明書の設定。
basicConstraints = critical,CA:true
keyUsage         = critical, cRLSign, keyCertSign, digitalSignature
# extendedKeyUsage はルートCAなので指定しない。中間CAを複数分ける時などには指定するだろうが、大規模システムのみ。
# nsCertType は古いシステムでは参照するかもしれないが、新たなものでは指定しない。(extended)keyUsageとbasicConstraintsで管理されるべきである。

CAを作る。CA.plがopensslコマンドの面倒なところをやってくれる。

# SSLEAY_CONFIG="-config ./openssl.cnf" ./CA.pl -newca
CA certificate filename (or enter to create) # 既存の証明書で作る場合は指定するが、今回は空でEnter
(中略)
# CA.plが勝手に新しい秘密鍵と公開鍵を作ってくれるので、その鍵のパスフレーズを入力する
writing new private key to './CA/private/cakey.pem'
Enter PEM pass phrase:
Verifying - Enter PEM pass phrase:
# 次に自己署名するためのCSRの情報を聞かれる。defaultを書いていたらEnterだけで良い。どうせ家庭内用なので適当に入力しても良いが、commonNameやemail等は存在するかどうかのチェックがあるため空欄は不可。
Country Name (2 letter code) [JA]:
State or Province Name (full name) [Tokyo]:
(中略)
# 最初に作ってもらった鍵で署名するため、ついさきほどのパスフレーズを要求される
Enter pass phrase for ./CA/private/cakey.pem:
(後略)

これで自己署名済みのCAができた。