オレオレCA証明書とサーバ証明書を作り、OpenSSLライブラリでその証明書を使うサーバを作り、chromeで信頼してもらう設定をする実験（Hands On）

#これから実施する実験のあらすじ
##はじめに
　実験は前半と後半の２つのパートで構成されます。前半でopensslコマンドで２つの証明書を作成します。ひとつはCAの自己署名証明書で、ふたつめがサーバの証明書でオレオレCAに署名してもらいます。
　後半ではopensslライブラリを使ったHTTPSサーバのソースコードをダウンロードしてビルドします。そして前半で作ったサーバ証明書でHTTPSサーバを起動します。そのままだとHTTPSサーバにアクセスするとブラウザ側でエラーになるのですが、CAの自己署名証明書をブラウザ側PCにインストールするとエラーが消えてコンテンツが表示されます。
　どのようなコマンドを使うと証明書を作成できるのか、opensslのライブラリを使ったソフトウェアをビルドするには、どのような作業が必要なのか、そしてブラウザの信頼を得るにはどのような作業が必要なのかをハンズオンで体験します。WindowsでもMacOSのどちらでも実施できます。ただし、WindowsではWSL2でのUbuntuを利用して、Windows側のブラウザでUbuntuのHTTPSサーバにアクセスします。このために、事前にWSL2でUbuntuをインストールしておいてください。UbuntuでもMacOSでのopensslコマンドが実行可能な状態から作業が開始されます。

##(前半)オレオレCAを作り、オレオレCAに署名してもらったサーバ証明書を作る
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/722db4b5-6a81-cc39-a477-5138cd492e03.png)

##(後半)TLSサーバを作ってchromeブラウザでアクセスしてみる
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/5a3d4ebd-c8d6-7cce-f8de-4361be11fc02.png)

#証明書の作成
##オレオレCAの証明書を作る
###オレオレCAのキーペアを作る
RSAキーペアを生成します。このキーはAESで暗号化します。デフォルトでRSAの秘密鍵は2048ビット長となります。出力ファイルca.keyには秘密鍵と公開鍵のキーペアが含まれています。
コマンド：openssl genrsa  -aes256 -out ca.key

```
hata@DESKTOP-KQLV5KG:~/cert/CA$openssl genrsa  -aes256 -out ca.key
Generating RSA private key, 2048 bit long modulus (2 primes)
................+++++
................+++++
e is 65537 (0x010001)
Enter pass phrase:ここでパスワード(CAパスワード)を決める
Verifying - Enter pass phrase:パスワード確認
```

###署名要求書を作る
　証明書は公開鍵にCAの秘密鍵で署名したモノですが、直接公開鍵に署名するのではなくまず公開鍵の埋め込まれた署名要求書を作成し，それに署名します
。署名要求書には句会鍵の他に、この公開鍵の所有者に関する情報も含まれます。これらの情報は署名要求書を作成するときに対話型で入力されます。
コマンド：openssl req  -key ca.key -new -out ca.req

```
hata@DESKTOP-KQLV5KG:~/cert/CA$ openssl req  -key ca.key -new -out ca.req
Enter pass phrase for ca.key:
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [AU]:JP
State or Province Name (full name) [Some-State]:Fukui
Locality Name (eg, city) []:Sabae
Organization Name (eg, company) [Internet Widgits Pty Ltd]:myCA
Organizational Unit Name (eg, section) []:HQ
Common Name (e.g. server FQDN or YOUR name) []:www.myca.com
Email Address []:myca@myca.com

Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:(省略)
An optional company name []:(省略)
hata@DESKTOP-KQLV5KG:~/cert/CA$ ls
ca.key  ca.req
```
###証明書を作成する
　CAの秘密鍵でCAの公開鍵を含んだ署名要求書に署名する。この証明書は公開鍵の所有者(Subject)と署名者（発行者；Issuer)が同じです。このようなSとIが同じ証明書をオレオレ証明書といいます。
コマンド：openssl x509 -req -in ca.req -signkey ca.key -out ca.crt

```
hata@DESKTOP-KQLV5KG:~/cert/CA$ openssl x509 -req -in ca.req -signkey ca.key -out ca.crt
Signature ok
subject=C = JP, ST = Fukui, L = Sabae, O = myCA, OU = HQ, CN = www.myca.com, emailAddress = myca@myca.com
Getting Private key
Enter pass phrase for ca.key:
hata@DESKTOP-KQLV5KG:~/cert/CA$ ls
ca.crt  ca.key  ca.req
```

##サーバ証明書を作る
###サーバのキーペアと署名要求書を一気に作る
　CAはキーペアを生成してから、署名要求書を作成しました。この２つの作業は一つのコマンドで一気に実行できます。作業ディレクトリを変更して作業します。
コマンド：openssl req -newkey rsa -keyout server.key -out server.req

```
hata@DESKTOP-KQLV5KG:~/cert/SERVER$ openssl req -newkey rsa -keyout server.key -out server.req
Generating a RSA private key
.......................................................................................................................................................................................................................+++++
...................................................+++++
writing new private key to 'server.key'
Enter PEM pass phrase:
Verifying - Enter PEM pass phrase:
-----
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [AU]:JP
State or Province Name (full name) [Some-State]:Tokyo
Locality Name (eg, city) []:Shibuya
Organization Name (eg, company) [Internet Widgits Pty Ltd]:example inc.
Organizational Unit Name (eg, section) []:Sales
Common Name (e.g. server FQDN or YOUR name) []:www.example.com
Email Address []:sales@example.com

Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:
An optional company name []:

hata@DESKTOP-KQLV5KG:~/cert/SERVER$ ls
server.key  server.req
```
###サーバの証明書作るためCAにより署名してもらう
　実際のシーンではサーバ管理者は署名要求書をCAに送って証明書を送り返してもらいます。ここではオレオレCAによって署名します。証明書にはバージョンがあります。CAのオレオレ証明書はV1でしたが、ここでは実験後半に必要なV3で作成します。V3の大きな特徴はSAN（subjectAltName）を含めることができる点です。サーバ証明書の動作するサーバは、DNSでCommonName(CN)が設定されている必要があります。しかしCNだけでなく複数の名前を付けたい場合があります。そのときCNに変わるサーバ名をSANに設定できます。ここではSANに幾つかのサーバ名(Ubuntuとlocalhost,www.example.com ）を設定します。SANは署名要求書には含まれていません。外部の設定ファイルを作成して、そこに書き込んでおきます。
 下記の例ではエディタを使わずにmy.cnfを作成していますが、catコマンド応答を参考にvimなどが使えれば[v3]で改行してsubjectAltNameで始まる2行からなるテキストファイルを作成してください。

```
hata@DESKTOP-KQLV5KG:~/cert/SERVER$ echo "[v3]" >my.cnf
hata@DESKTOP-KQLV5KG:~/cert/SERVER$ echo subjectAltName=DNS:ubuntu,DNS:localhost,DNS:www.example.com >>my.cnf
hata@DESKTOP-KQLV5KG:~/cert/SERVER$ cat my.cnf
[v3]
subjectAltName=DNS:ubuntu,DNS:localhost,DNS:www.example.com
```
　このmy.cnfのv3セクションを使ってサーバの署名要求書にCAの秘密鍵で署名するには、CAの秘密鍵に加えてCAの証明書が必要です。サーバ証明書には、署名要求書に書かれている公開鍵所有者がSubjectに、CAの証明書に書かれているSubjectをIssuerに設定されます。
　CAのオレオレ（自己署名）証明書を作成したときには署名のハッシュアルゴリズムを指定しませんでしたので、opensslコマンドのバージョンによってはデフォルトのSHA-1が使われることがあります。後述しますが、CAの自己署名証明書は利用者の操作によりPCにインストールされます。この場合には多少セキュリティレベルの低いアルゴリズムでも操作者がそれを許容したとみなされエラーとはなりません。しかしサーバ証明書はネットワーク経由でサーバからダウンロードされます。よってセキュリティレベルの低いアルゴリズムで署名された証明書ではPC側でサーバとの接続を切断してしまいます。よってサーバ証明書では署名にはSHA-256を明示的に指定します。

コマンド：openssl x509 -req -in server.req -out server.crt -CA ../CA/ca.crt -CAkey ../CA/ca.key -CAcreateserial -sha256 -extfile my.cnf -extensions v3
ここでパスワードを尋ねられます。署名はCAの秘密鍵でサーバの公開鍵を暗号化するので、CAの秘密鍵のパスワードを入力します。誤ってサーバの秘密鍵のパスワードを入力しないように注意します。

```
hata@DESKTOP-KQLV5KG:~/src/tls_lib/cert$ openssl x509 -req -in server.req -out server.crt -CA ../CA/ca.crt -CAkey ../CA/ca.key -CAcreateserial -sha256 -extfile my.cnf -extensions v3
Signature ok
subject=C = JP, ST = Tokyo, L = Shibuya, O = example inc., OU = Sales, CN = www.example.com, emailAddress = sales@example.com
Getting CA Private Key
Enter pass phrase for ../CA/ca.key:（CAの秘密鍵のパスワード）
hata@DESKTOP-KQLV5KG:~/cert/SERVER$ ls
my.cnf  server.crt  server.key  server.req
```
###証明書の確認と検証
証明書や鍵ファイルは、PEM形式といって、プリント可能な文字で構成されています。五つのハイフン記号のBEGIN行とEND行で挟まれた領域がデータになっています。

```
-----BEGIN CERTIFICATE-----
MIIDsTCCApmgAwIBAgIUL8RBH1LSmP0+LCHYRlA4KFahGgUwDQYJKoZIhvcNAQEL
BQAwfjELMAkGA1UEBhMCSlAxDjAMBgNVBAgMBUZ1a3VpMQ4wDAYDVQQHDAVTYWJh
ZTENMAsGA1UECgwEbXlDQTELMAkGA1UECwwCSFExFTATBgNVBAMMDHd3dy5teWNh
LmNvbTEcMBoGCSqGSIb3DQEJARYNbXljYUBteWNhLmNvbTAeFw0yMTA3MDgwMzAx
MjdaFw0yMTA4MDcwMzAxMjdaMH4xCzAJBgNVBAYTAkpQMQ4wDAYDVQQIDAVUb2t5
bzEQMA4GA1UEBwwHQ2hpeW9kYTEOMAwGA1UECgwFTXlDb20xCzAJBgNVBAsMAkhR
MRMwEQYDVQQDDAp3d3cubXkuY29tMRswGQYJKoZIhvcNAQkBFgxteWNvbUBteS5j
b20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDGvOHAvHeCkKSMeuHG
b1T+98/XqsC3auvVozLMoMDNY8hauf/mY/Ue3CXL9mFKVNULtmWhGAXDLC248cFi
9izvCPEwfNFtpYhf+/4mnqdmhnzJUcB9bW9uXHgM/W/HaCHA9M2GSYDpVt+iR4oZ
MydKkcLvSqyo4E+UBZzQGWvtRxpR+xOp6+DBsHX7TxN66FJ7cwt8vZSLr3a7EEro
U0BB18R/SVFQtgqo6IXB/8NypoEBe75bqSpr7KEqsZRyNvbehndx1lD0Nr3XxfGc
Eq2iOmqeybkQ89BcFLDlobBfzLt5Ndnn5mtGwQQdmaTwuuZIa7Q+fQ2hl8ZIiA95
1g2zAgMBAAGjJzAlMCMGA1UdEQQcMBqCBTE3Mi4qggZ1YnVudHWCCWxvY2FsaG9z
dDANBgkqhkiG9w0BAQsFAAOCAQEAtkpz+uLOrYJgKypIfMNXkBkFbVmmz3MvAWXp
rGeVuGMcQzuDxpo2TgcWa48Yis4XnWG2kygiKqTLMpqQYJY8+sNwOVf0s4JTDQHc
RiD5SeK4VNMpcRPDcWMJ6iMxWWwl15fiH6/5GTo2Y8xrJV5A81xJRi6+hW2xw+Y0
syGC6Epb/F8q10RoPno1LcPChyPWGWkTdBOAS/sncxc5AI/X4z8CbZQo1juhSViD
Ty+4t4GExgX46M2TCuZz21l7z3Q/hJ7BbGzxV690qLVo38OrIXSl2hJ+Pt5Ggico
DpVZhVmXNcgniJmH1WGtCPOakRVOj/GnC7cZfDBUOqCL15KxqA==
-----END CERTIFICATE-----
```
　このBEGINとENDの外はいわゆるコメント行としてメモのようなものを記録してもかまいません。データはBase64でエンコードされており、証明書の内容である公開鍵や、Subject,Issuer,有効期限、SANなどの情報が構造化されて格納されています。これを人間の目にもわかるように出力するには、opensslコマンドでオプション-textを付与して-inで読みたいファイルを指定します。
例えば
openssl req -in server.req -text　や
openssl x509 -in server.crt -text
このままopenssl x509 -in server.crt -text > server2.crtとして新たな証明書ファイルを作成してもBEGIN行とEND行の間には変更がありませんので、このまま解釈文字列付きで証明書としてサーバで読み込み可能です。
　ただし、openssl rsa -in server.key -text コマンドの利用には細心の注意を払いましょう。本来パスワードで暗号化されている秘密鍵ですが、-text付で表示すると画面などに秘密鍵の本体が表示されます。漏洩の可能性がありますので、表示履歴を消したり、ファイルにセーブしないようにしましょう。
サーバ証明書の検証はCAの照明書を指定してopensslのverifyコマンドで行えます。

```
hata@DESKTOP-KQLV5KG:openssl verify -CAfile ~/cert/CA/ca.crt server.crt 
server.crt: OK
```

#TLSサーバを作る
##ソースコードをダウンロードする
　作成したサーバ証明書を使ってみるためにopensslライブラリを使って作成したHTTPSサーバを作ってブラウザからアクセスしてみます。このプログラムはWebサーバではnginxやapacheが有名で、サーバ証明書はほとんどがこれらのサーバで使われます。ここでは、ソフトウェアとしてサーバ証明書と秘密鍵がどのように読み込まれるのかをソースコードレベルで確認することを目的とした簡易的なTLSサーバプログラムを使ってHTTPSサーバを立てることとします。このソフトウェアは図のようにopensslライブラリの上に、TLSラッパライブラリとTLSアプリケーションを乗せた構成になっています。まずグレーの部分のHTTPSサーバのソースコードをgithubよりダウンロードして、その後opensslライブラリをインストールします。

![図1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/a0d9b5b2-03f2-403c-2bc5-7a61f48df89d.png)
　UbuntuでもMacOSでも作業は共通です。Gitコマンドが動作しない場合は、gitをインストールするかブラウザで直接レポジトリにアクセスして必要なファイルをダウンロードしてください。レポジトリのURLは次の通りです。https://github.com/h-hata/tls_lib 

```
hata@DESKTOP-KQLV5KG:~/src$ git clone https://www.github.com/h-hata/tls_lib
Cloning into 'tls_lib'...
warning: redirecting to https://github.com/h-hata/tls_lib.git/
remote: Enumerating objects: 14, done.
remote: Counting objects: 100% (14/14), done.
remote: Compressing objects: 100% (12/12), done.
remote: Total 14 (delta 1), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (14/14), 10.14 KiB | 3.38 MiB/s, done.
hata@DESKTOP-KQLV5KG:~/src$ cd  tls_lib
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ ls
Makefile  README.md  dump.c  my.cnf  tls.c  tls.h  tls_tls.h  tlsrv.c
```
このtls_libディレクトリでTLSサーバを動作させますので、サーバ証明書のあるディレクトリのシンボリックリンクを、ここに生成しておきます。

```
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ ln -s ~/cert/SERVER/ ./cert
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ ls ./cert
my.cnf  server.crt  server.key  server.req
```
##opensslライブラリのインストール
###ubuntuにopensslライブラリをインストールする
　追加インストールするのはlibssl-devパッケージです。このパッケージがインストールされると、/usr/include/opensslにヘッダファイルが、/usrlib/x86_64-linux-gnu/にlibssh.aがコピーされてHTTPSサーバがビルド可能になります。
コマンド:sudo apt install libssl-dev

```
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ sudo apt install libssl-dev
Reading package lists... Done
Building dependency tree
Reading state information... Done
Suggested packages:
  libssl-doc
The following NEW packages will be installed:
  libssl-dev
0 upgraded, 1 newly installed, 0 to remove and 0 not upgraded.
Need to get 1583 kB of archives.
After this operation, 8006 kB of additional disk space will be used.
Get:1 http://archive.ubuntu.com/ubuntu focal-updates/main amd64 libssl-dev amd64 1.1.1f-1ubuntu2.4 [1583 kB]
Fetched 1583 kB in 4s (409 kB/s)
Selecting previously unselected package libssl-dev:amd64.
(Reading database ... 38949 files and directories currently installed.)
Preparing to unpack .../libssl-dev_1.1.1f-1ubuntu2.4_amd64.deb ...
Unpacking libssl-dev:amd64 (1.1.1f-1ubuntu2.4) ...
Setting up libssl-dev:amd64 (1.1.1f-1ubuntu2.4) ...
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ make
gcc -o dump.o -Wall -DDEBUG -c dump.c
gcc -o tls.o -Wall -DDEBUG -c tls.c
gcc -o tlsrv dump.o tls.o  tlsrv.c -lpthread -lssl -lcrypto
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ ls
Makefile   cert    dump.o  tls.c  tls.o      tlsrv
README.md  dump.c  my.cnf  tls.h  tls_tls.h  tlsrv.c
```
上図のようにmakeコマンドでtlsrvという実行ファイルが生成できました。
###MacOSにopensslライブラリをインストールする
　これまでMacOSでもopensslコマンドを使ってきましたが、厳密にはMacOSでのopensslコマンドはlibreSSLというopenSSLから派生した別種類のソフトウェアです。TLS機能を使ったソースコードをMacOSでビルドするために、opensslをMacOSに追加します。
コマンド: brew install openssl
これで、opensslコマンドと開発用パッケージがインストールされます。開発者用パッケージのヘッダファイルとライブラリがインストールされている場所を探して、Makefileの-Iオプションと-Lオプションに適切な位置を設定します。
ライブラリのインストールされている場所の見つけ方は、/usr配下でlibssl.aやopenssl/bio.hが存在している場所をfindコマンドで見つけ出します。例えば以下では、`./local/Cellar/openssl@1.1/1.1.1k/lib/libssl.a`や`./local/include/node/openssl/bio.h`そして
`./local/Cellar/openssl@1.1/1.1.1k/include/openssl/bio.h`が発見されました。

```
hata@claire /usr % find .|grep libssl.a$
find: ./sbin/authserver: Permission denied
find: ./local/Quarantine: Permission denied
./local/Cellar/openssl@1.1/1.1.1k/lib/libssl.a
hata@claire /usr % find .|grep bio.h$   
find: ./sbin/authserver: Permission denied
find: ./local/Quarantine: Permission denied
./local/include/node/openssl/bio.h
./local/Cellar/openssl@1.1/1.1.1k/include/openssl/bio.h
```

node/opensslはnode.jsのディレクトリなので、今回の場所ではありません。Makefileの-Iと-Lオプションを以下のように見つけたディレクトリ名で上書きしてください。

```
OBJ=dump.o tls.o 
OPT=-I /usr/local/Cellar/openssl@1.1/1.1.1k/include
LOPT=-L /usr/local/Cellar/openssl@1.1/1.1.1k/lib
all: tlsrv
tlsrv: $(OBJ) tlsrv.c
  gcc $(OPT) -o tlsrv $(OBJ) tlsrv.c $(LOPT) -lpthread -lssl -lcrypto
.c.o:
  gcc -o $*.o -Wall -DDEBUG -c $(OPT) $<
# gcc -Wall  -c $<
clean:
  rm -f $(OBJ) tlsrv  a.out tags
```

この後makeコマンドでtlsrvコマンドがビルドできます。

##サーバの起動とブラウザによるアクセス
　先ほどビルドしたtlsrvコマンドを起動します。単に無パラメータで起動できます。終了はCtlr+Cです。起動時にサーバ証明書に加えてサーバ鍵ファイルも読み込まれます。このため起動時にはサーバの秘密鍵のパスワードが聞かれます。CAの鍵ではありません。サーバの鍵のパスワードを入力してください。

```
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ ./tlsrv
Setup  Server
Enter PEM pass phrase:（サーバの秘密鍵のパスワード）
New Main Server Thread
```
よくある起動失敗原因は、証明書ファイルと鍵ファイルが見つからない場合です。この場合Enter PEM pass phrase:というサーバパスワードプロンプトが出ずに終了します。tlsrvの置かれているディレクトリにcertというディレクトリがあり、そこにserver.crtとserver.keyがおかれている必要があります。これらのファイルの場所や名前を変更したい場合には、tlsrv.cの18行目と19行目を環境に合わせて適切に変更したのち、再度コンパイルリンクしてください。

```
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ ./tlsrv
Setup  Server
TLS_ServerSetup returned -20
```
 入力したサーバ鍵のパスワードが間違っている場合には、opensslライブラリの出すエラーメッセージが出力されます。CAの秘密鍵のパスワードを誤って入力すると、以下のようにエラー終了します。

```
hata@DESKTOP-KQLV5KG:~/src/tls_lib$ ./tlsrv
Setup  Server
Enter PEM pass phrase:
139870990009088:error:06065064:digital envelope routines:EVP_DecryptFinal_ex:bad decrypt:../crypto/evp/evp_enc.c:610:
139870990009088:error:23077074:PKCS12 routines:PKCS12_pbe_crypt:pkcs12 cipherfinal error:../crypto/pkcs12/p12_decr.c:62:
139870990009088:error:2306A075:PKCS12 routines:PKCS12_item_decrypt_d2i:pkcs12 pbe crypt error:../crypto/pkcs12/p12_decr.c:93:
139870990009088:error:0907B00D:PEM routines:PEM_read_bio_PrivateKey:ASN1 lib:../crypto/pem/pem_pkey.c:88:
139870990009088:error:140B3009:SSL routines:SSL_CTX_use_RSAPrivateKey_file:PEM lib:../ssl/ssl_rsa.c:489:
** tls.c:269 setup_server_ctx RSA Keyfile invalid
TLS_ServerSetup returned -20
```

##サーバの起動とブラウザによるアクセス
 HTTPSサーバはポート番号4444でTCPポートがオープンしています。セキュリティソフトウェアやファイアウォールを起動している場合に、このポート番号がブロックされている可能性がありますので、必要に応じて実験の間は4444番ポートへのアクセスを許容してください。
 MacOSやUbuntuの動作しているのと同じ(VM)マシンでブラウザが利用できる場合にはhttps://127.0.0.1:4444 へアクセスしてください。WindowsのWSL2でUbuntuを動作させて、このUbuntu上でtlsrvを起動しWindowsのブラウザからtlsrvにアクセスする場合には、まずUbuntuのIPアドレスを調べます。いったんtlsrvを終了して ip a コマンドでインタフェースeth0のIPv4アドレスを調べてください。例えば、下図の例では172.31.181.241がubuntuのIPアドレスです。WSLでは起動するたびにubuntuのIPアドレスが変化します。昨日とは異なっているかもしれませんので注意してください。

```
4: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP group default qlen 1000
    link/ether 00:15:5d:57:5c:f6 brd ff:ff:ff:ff:ff:ff
    inet 172.31.181.241/20 brd 172.31.191.255 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::215:5dff:fe57:5cf6/64 scope link
       valid_lft forever preferred_lft forever
```
再度tlsrvを起動してブラウザでそのIPアドレスのURLにアクセスします。この例ではhttps://172.31.181.241:4444 です。
すると「この接続ではプライバシーが保護されません」というメッセージでWebサーバからのコンテンツが表示されません。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/04310940-44a9-fe19-7fef-f733b8ac6ade.png)
この原因は2つあります。ひとつはアクセス先のIPアドレスもしくはホスト名が証明書のSubjectのCNもしくはSANに記載されていないことです。ふたつめは、サーバ証明書のIssuerの証明書がなくて、サーバ証明書の検証に失敗したためです。上図のエラーメッセージERR＿CERT_COMMON_NAME_INVALIDはひとつ目のエラーを表示しています。この２つ問題を取り除きます。

##ホストファイルにSANに記述したホスト名を登録する
サーバ証明書のSANにはubuntu,localhost,www.example の３つのホスト名を登録していました。ここではwww.example.comを登録してみます。ブラウザの動作しているホストPCでホストファイルを特権モードで起動したエディタでオープンします。MacOSやUbuntuではsudo vim /etc/hostsです。 WSL2でのUbuntuをWindows側のブラウザで見ている場合には、Windowsのhostsを開きます。開き方はまず「メモ帳」を「管理者として実行」します。そして、c:\Windows\System32\drivers\etc\hostsを開きます。このファイルには拡張子がありませんので、ファイル名のテキストボックスにアスタリスクを入れて開くボタンを押さなければファイル名ペインにファイル名が現れませんので注意してください。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/c15b13f5-2cd2-1aff-b7b3-c559e89e708a.png)
そしてIPアドレスとホスト名を空白で区切って登録してセーブします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/d9d89844-45dc-e847-6765-d61927d708c5.png)
 上記の例では同じIPアドレスでUbuntuでもwww.example.comでもアクセス可能なように設定しました。この設定済のホスト名のURLであるhttp://www.example.com:4444にアクセスしてみます。すると、やはりエラーになりのですが、エラーメッセージがERR_CERT_AUTHORITY_INVALIDに変わりました。これは上述の２つの原因のひとつめが解消されふたつめの原因が顕在化したことになります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/bf2bbd19-cd69-2a81-51b9-8c22f18e715e.png)


##CA証明書をPCにインストールする
##Chromeブラウザからルート証明書登録への入り口
ブラウザでERR_CERT_AUTHORITY_INVALIDが表示されたのはサーバ証明書のIssuerの証明書がブラウザの動作するコンピュータにインストールされていなかったからです。ここではCAの証明書であるca.crtをブラウザの動作するPCにインストールしてみます。証明書のインストーラ起動の方法はいくつかありますが、Chromeブラウザの右上のメニューから設定＞セキュリティ＞証明書の管理で、システムの証明書管理アプリケーションが起動されます。

##CA証明書をWindowsにインストールする
Windowsでは証明書ウィザードから信頼されたルート証明機関のタブを選択します。最初からインストールされているCAの自己署名証明書の一覧が表示されます。インポートボタンを押すと新たな証明書を読み込めます。WSL2では\\wsl$でUbuntuのフォルダが見えますので、ca.crtを探して選択してください。インストールが完了すると該当のエントリをダブルクリックすると、SubjectもIssuerもwww.myca.comとなったオレオレ証明書が表示されるはずです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/83ca45b5-209c-e0ef-f81b-31b6fec2e4c6.png)


##CA証明書をMacOSにインストールする
MacOSではキーチェーンアクセスアプリが起動します。メニュ＞ファイル＞読み込むからca.crtを選択します。すると左ペインのログインのところを選ぶとwww.oreore.comが登録されていることが分かります。
![図2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/3e2994e1-d2d7-05e6-2d59-9c90bea8febe.png)
MacOSの場合には、単に登録しただけでは検証がなされていないものとして利用はできません。この証明書のエントリをダブルクリックして下図のようなダイヤログボックスを出します。そして信頼の項目（ここは通常未展開で内容が消えていますので、左横の矢印をクリックして内容を表示する）からSSLとX.509基本ポリシーの項目を「常に信頼」と変更します。このダイヤログボックスを閉じるときにログインアカウントのパスワードが求められますので、適切に入力してください。

![図3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/caf21e7b-a1e7-37bd-cba8-eaf632d6f0c9.png)
元の画面に戻ると、www.oreore.comの証明書がアカウントにとって信頼されているという表示に変わり利用が可能になったことが分かります。

![図4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/48bfd4b7-b99d-3a59-2b5f-8dc3c88a10f3.png)
##動作確認
 CAの証明書のインストールが完了したらいったんchromeを終了して再起動します。そして改めてhttps://www.example.com:4444 にアクセスしてみますと、tlsrv.cから送られたHTMLがエラーなくコンテンツとして表示されていることが分かります。これで実験は終了です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/a9942743-69fe-4df9-d0cd-410d458952c0.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/135512/a513be47-6a07-a82a-dad6-d2772882069c.png)

#実験の終わりの注意
（注意１）PCにインストールしたオレオレCA自己書名証明書は、実験が終わったら削除しておきましょう。
（注意２）実際の運用では秘密鍵と公開鍵の入っている鍵ファイルが非常に重要です。証明書の期限が過ぎれば、再び同じ鍵ファイルから署名要求書を作成して、CAに署名してもらいます。すなわち、鍵ファイル(.key)はずっと使いますが署名要求書(.req)や証明書(.crt）は有効期限が過ぎると作り直しされます。有効期限を長く設定すると、鍵ファイルは残っているもののパスワードを失念してしまう危険があります。年に１回程度しか使わないパスワードですので、大切に保管しておいてください。