【実験】電話線を使ってQUICで通信してみた

# はじめに
タイトルだけ読んでもピンとこない人のほうが大半だと思われるので、まずは今回行った実験の簡単な構成図を見せる。

構成図![quic-ppp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/2229f0e0-5843-119d-d637-fac26058c924.png)

上の図では、クライアント側が電話線を経由して、サーバー上にあるWebコンテンツを受け取るという仕組みになっている。
例えば一般のご家庭（~~逸般の誤家庭~~）にて、LAN内で一台Webサーバーを構築して、それをLAN内の端末と接続しようと考えた際に、通常であればLANケーブルを用いて接続する。
しかし今回の研究ではLANケーブルを使わずに、電話線で接続するという手法を用いて接続した。

# なぜ電話線で接続できるのか？
結論から述べると、ネットワークインターフェイス層にPPPを用いれば電話線でエンドツーエンド通信ができ、さらにTCP/IPの階層モデルにてそれぞれのレイヤーが独立しているという特徴があるので、PPPを採用しながらアプリケーション層でQUICが使えるからである。

まずは復習も兼ねて、TCP/IPの階層モデルを見ていこう。

```
第1層：ネットワークインターフェイス層（Ethernet、PPPなど）
第2層：インターネット層（IP、ARP、ICMPなど）
第3層：トランスポート層（QUIC、TCP、UDPなど）
第4層：アプリケーション層（HTTP、SSH、SMTPなど）
```

以上4層がTCP/IPの階層モデルを構成するレイヤーである。
これらのレイヤーはそれぞれ独立して構成されているので、それぞれのレイヤーごとにプロトコルを定めることができる。
例えばトランスポート層にQUICを使った際に、現代では第1層にはほぼEthernetが選ばれる。Ethernetでは主にツイストペアケーブル（LANケーブルが代表例）が採用されている。しかし、それぞれのレイヤーがそれぞれ独立して構成しているという特徴から、第1層でPPPという別のプロトコルを用いても、トランスポート層では変わらずQUICを採用することができるのだ。

ところでインターネットネイティブ世代（かくいう筆者も）にとってPPPというプロトコルはあまり馴染みがないだろう。
PPPとは簡単に説明すると以下の通りである。
- 1対1でコンピュータを接続するプロトコル
- 主に[ダイヤルアップ接続](https://qiita.com/Juice/items/708599f9f1528099f77d#%E3%83%80%E3%82%A4%E3%83%A4%E3%83%AB%E3%82%A2%E3%83%83%E3%83%97%E6%8E%A5%E7%B6%9A%E3%81%AB%E3%81%A4%E3%81%84%E3%81%A6)などで用いられていた
    - 電話回線レベルのコネクションを確立させたあとに、PPPのコネクション確立
- 物理層で使うものは定められていない
    - 電話回線、ISDN、ATM回線、専用線など

以上の説明のうち、今回の実験で注目してほしいのが、最後の物理層で使うものについてである。PPPでは物理層で使うものは特段定められていないが、一般的に用いられているものはいくつか存在している。その中の一つとして「電話線」が挙げられる。つまりPPPを採用すれば、電話線でエンドツーエンド通信をすることができるのである。

以上の特徴から、ネットワークインターフェイス層でPPPを採用することで、物理層で電話線を採用しつつ、アプリケーション層でQUICを採用できるがゆえに、電話線を使ってQUICで通信できるのである。

# 実装

構成図1
![quic-ppp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/89e2f1d0-cd66-a260-0597-fab8644731c7.png)

今回は[USB接続型のモデム](https://qiita.com/Juice/items/708599f9f1528099f77d#usb%E5%9E%8B%E3%83%A2%E3%83%87%E3%83%A0)を使用することで、デジタルデータをアナログデータに変換をして、電話線でデータのやり取りができるようにした。

構成図2
![quic-ppp2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/d3aa9e75-590d-d2bd-b3ca-543bae0aa302.png)

クライアント、サーバーそれぞれにIPv6を割り当て、ルーターにはそれぞれ電話の内線番号である\*1と\*2を割り当てた。

## PPP接続の設定
### mgettyの設定
アナログモデムを接続したデバイスを常時監視
着信があった際にpppd（PPPを管理するデーモン）を起動

mgettyの起動設定（/etc/systemd/system/mgetty.service）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/362d803d-55d7-4124-6f18-a6e9223f89a1.png)


mgettyの設定（/etc/mgetty/mgetty.config）
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/25892734-7ddc-0c74-7e69-52e67d4cc431.png" width="50%">


PPPPの自動設定スクリプト（/etc/mgetty/mgetty.login）
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/502369e6-670f-acbe-2dd5-8ebc409bc3a9.png" width="70%">

### pppdの設定
PPPを管理するデーモン

設定オプション（/etc/ppp/options）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/51292ec1-5bfe-0d50-8712-3f4b6d56e2ff.png)

PAP認証設定（/etc/ppp/pap-secrets）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/be089dc2-7531-0fd9-5dda-2682f4f8ade4.png)

Linuxのユーザー認証（/etc/pam.d/ppp）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/62e32aa7-4c9a-1221-dfb3-acceaceb3249.png)

なおPAP認証を用いた際、パスワードが平文で渡されてしまうセキュリティ上のリスクが存在するが、今回はLAN内での通信であること、実験で受け渡すWebコンテンツに機密情報が含まれないこと、今回の実験でのみ用いるシステムであることなどといった理由から、特段考慮するリスクではないと判断したため、PAP認証を採用した。

## Nginxの構築
QUICに対応した1.25.0以上のものをインストールした。

Nginxの設定（/etc/nginx/conf.d/default.conf）
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/ea13ff4e-83ed-bd63-b34d-7a0f26d4b0a1.png" width="60%">

# 実行手順
- Systemdに新しいサービスとしてmgetty、Nginxを追加して起動
- Windows側からPAPで設定したユーザー名とパスワード、内線番号を使ってPPP接続を確立させる
- クライアント側からサーバー側にブラウザを使ってHTTP接続をする
    - Hostsを使って”myserver.com”でアクセスできるようにした
    - 自己署名証明書を発行したうえでTLS接続を行った

PAPで設定したユーザー名とパスワード、内線番号を使ってPPP接続
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/8661d101-e3a9-ccda-b028-fb64dba9401a.png" width="60%">

# 実行結果

サーバーから返されたWebコンテンツ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/a7f703b6-5175-6b1d-9831-1a21e8495533.png)

通信情報1
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/86fb74e5-d42e-f17a-d3b1-a2309a7d524d.png" width="60%">

通信情報2
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3642100/dc13efca-6e03-ffbb-bce2-d2d27e7764cb.png" width="60%">

実行結果より、通信においてアプリケーション層でHTTP/3、TLSv1.3が使われていることから、QUICでの通信に成功していることがわかる。

# おわりに
いかがだっただろうか。
インターネット黎明期に普及していたPPPと、令和以降に普及し始めたQUICを組み合わせた通信というなんとも奇妙なものであったが、TCP/IPプロトコルにおいて、レイヤーごとの機能が独立している恩恵を肌身で感じることができる、良い経験になったと思った。
ただPPPに関して説明しているサイトがかなり限られていたことから、PPPの設定には一番労力を費やした（ダメ元でChatGPTにもPPPの設定について聞いてみたところ、想像以上に精度の高い回答を得ることができ、構築するうえではかなりの助けになった）。
またNginxを用いてQUICサーバーを構築する知見を得ることができたのも、個人的にはかなり大きな学びであった。