Encrypted Client Hello(ECH)
TLSで唯一平文だったSNIを暗号化し、閲覧先ドメインの盗聴・検閲ブロックを防ぐ仕組みが、鍵配布からGREASEまで筋道立てて分かる。
- 1.TLS1.3でも拡張SNIだけは平文で残り、経路上の観察者に接続先ドメインが漏れていた。ECHはClientHello全体を暗号化してこれを塞ぐ。
- 2.outerとinnerの二重ClientHello構造を使い、outerはダミー値、innerが本物のSNI等を含む暗号化ペイロードとして運ばれる。
- 3.ECH鍵はDNSのHTTPSリソースレコードで配布され、対応サーバーが同一IPに同居する前提が必要。非対応時はGREASEでフォールバックを見分けにくくする。
TLS 1.3 でもなお残った平文
TLS 1.3 はハンドシェイクの大半を暗号化し、Certificate すらハンドシェイク鍵で保護します。しかし最初の ClientHello そのものは暗号化できません。クライアントとサーバーはまだ共有秘密を持たず、鍵を導出する材料(key_share など)を運ぶメッセージ自体を暗号化する手段がないからです。
この ClientHello には拡張 server_name(SNI)が乗っており、クライアントが接続したいホスト名を平文で運びます。理由は単純です。1台のサーバーが多数のドメインを同一 IP でホストする場合(バーチャルホスティング、多くの CDN や共有ロードバランサ)、サーバーはどの証明書を提示すべきかを ClientHello の時点で知る必要があるからです。結果として、経路上の誰でも「どの IP に繋いだか」だけでなく「どのドメイン名を要求したか」まで観測できてしまいます。DNS クエリを DoH/DoT で隠しても、直後の TLS ハンドシェイクで同じ情報が SNI として漏れれば意味がありません。
アプリ本体の通信は TLS で守られていても、SNI が平文であれば「誰がどのサービスにアクセスしたか」というメタデータは検閲・ブロック・プロファイリングに十分使えます。国や組織単位でのドメイン別遮断の多くは、この SNI 平文を根拠にしています。
outer と inner:二重の ClientHello
ECH(Encrypted Client Hello)の核心は、ClientHello をそのまま暗号化して別の ClientHello の中に埋め込むという二段構造です。
- inner ClientHello:本物の
server_name(例mail.example.com)や実際のハンドシェイクパラメータを含む、クライアントが本来送りたい ClientHello。 - outer ClientHello:実際にワイヤ上へ平文で流れるメッセージ。
server_nameにはダミーの公開名(public name、例cloudflare-ech.comのような ECH を代理提供するドメイン)を入れ、拡張encrypted_client_helloに HPKE で暗号化した inner ClientHello を封入する。
outer ClientHello(ワイヤ上の平文)
server_name = "public-name.example" ← ダミー、露出してよい値
key_share, supported_versions ... ← ECDHE用の値(outer独自)
extension: encrypted_client_hello
├ HPKE鍵カプセル化情報(enc)
└ payload = HPKEで暗号化されたinner ClientHello
└ server_name = "mail.example.com"(本物、暗号化済み)
サーバー側はまず outer を受け取り、encrypted_client_hello 拡張を見つけると、対応する **ECH 鍵ペア(秘密鍵)**で payload を復号して inner ClientHello を取り出します。そこから先のハンドシェイクは inner の内容(本物の SNI・パラメータ)で進行し、証明書もそのドメインに対応するものが提示されます。outer 用に用意した鍵共有値や乱数はハンドシェイク鍵導出には使われず、あくまで inner を運ぶための「封筒」としての役割に限定されます。
ECH の暗号化には HPKE(RFC 9180)を使います。KEM(鍵カプセル化、例 X25519)で一時鍵から共有秘密を導出し、AEAD で inner ClientHello を暗号化する構成です。DNS で配布された ECH 設定に含まれる公開鍵に対して、クライアントが接続のたびに新しい一時鍵を使うため、outer 側からは毎回異なる暗号文に見えます。
「同居」が成立条件になる理由
ECH が機能するには、同一 IP・同一 TLS 終端点に、outer の公開名で応答できるサーバーと、inner の本物ドメインを処理できるサーバーが共存していることが前提です。中間者や検閲装置は outer だけを見て public-name.example への接続だと判断しますが、実際にコネクションを受けた終端サーバー(多くは大規模 CDN のエッジ)は inner を復号して本当の宛先へルーティングします。これは「隠れ蓑ドメイン(cover domain)」の背後に無数の実サイトを隠す発想で、多数のドメインを収容する CDN・ロードバランサ のような環境と特に相性が良い一方、単独運用の小規模サーバーでは outer 役を用意しにくいという制約があります。
ECH 鍵配布:DNS の HTTPS リソースレコード
クライアントは接続前に、ECH 用の公開鍵と対応パラメータを知る必要があります。これを運ぶのが DNS の **HTTPS リソースレコード(type 65、SVCB のサブタイプ)**です。権威サーバーはこのレコードに ech パラメータとして ECHConfig(バージョン、HPKE 公開鍵、対応する KEM/KDF/AEAD の組、公開名など)を含めて応答します。
example.com. IN HTTPS 1 . (
alpn="h2,h3"
ech="<base64エンコードされたECHConfigList>"
)
クライアントはこのレコードを引いてから ECH 鍵で inner を暗号化した ClientHello を組み立てます。したがって ECH の秘匿性は「DNS 応答自体をどれだけ信頼できるか」に依存します。ここで DNSSEC による応答の真正性検証や、DoH/DoT による問い合わせ自体の秘匿化と組み合わせることで、ECH 鍵の取得経路そのものが改ざん・盗聴される余地を減らせます。DNS 応答が偽装されれば、クライアントは攻撃者の鍵で inner を暗号化してしまい、ECH の保護は成立しません。
| 観点 | 従来のSNI | ECH |
|---|---|---|
| 宛先ドメインの可視性 | 平文でワイヤに露出 | outerはダミー、inner(本物)は暗号化 |
| 必要な事前情報 | なし | DNSのHTTPSレコードからECH鍵を取得 |
| サーバー側の前提 | 証明書選択にSNI平文が必要 | outer/inner兼用の終端点(多くはCDN)が必要 |
| 失敗時の挙動 | 該当なし | 鍵不一致時はouterの公開名でリトライ/フォールバック |
GREASE:フォールバックを見分けにくくする
ECH 非対応のサーバーや中間装置が「この拡張は知らない」と一意に反応すると、その反応パターン自体が ECH 使用の有無を推測する手がかりになります。これを防ぐのが GREASE(Generate Random Extensions And Sustain Extensibility) の ECH への応用です。ECH をまだ使わない、あるいは使えない接続でも、クライアントはダミーの encrypted_client_hello 拡張(ランダムな内容の GREASE ECH)を ClientHello に含めておきます。
狙いは二つです。第一に、サーバーや中間装置が未知の拡張を許容せず接続を落とすような硬直した実装を早期に検出し、相互運用性の劣化を防ぐこと。第二に、実際に ECH を使っている接続とダミーだけの接続を、外形(拡張の有無や長さ)だけから区別しにくくすることです。GREASE 自体は IETF が TLS 拡張全般の硬直化対策として先に導入した仕組みで、ECH はその応用形にあたります。
- TLS1.3でも ClientHello の
server_name(SNI)は平文のまま残り、接続先ドメインが経路上に露出する。 - ECH は inner(本物のSNI等)を HPKE で暗号化し、outer(ダミーのpublic name)に封入して送る二重構造。
- ECH鍵は DNS の HTTPS リソースレコードで配布され、DNS応答の真正性(DNSSEC等)に安全性が依存する。
- 同一終端点に outer/inner 双方を捌けるサーバーの同居が必須で、大規模CDN環境と親和性が高い。
- GREASE ECHはダミー拡張を混ぜ、ECH利用の有無を外形から区別しにくくして硬直実装も検出する。
一段で言うと
ECH は「ClientHello をもう一枚の ClientHello で包んで暗号化し、本物の SNI を隠す」仕組みです。outer に無害なダミー名を、inner に本物のホスト名を入れて HPKE で封をし、鍵は DNS の HTTPS レコードから事前に取得します。この設計は ESNI(Encrypted SNI)と呼ばれた初期草案から発展したもので、SNI 一箇所だけを暗号化する素朴な方式では ClientHello 全体の構造からハンドシェイクの実質的な内容を推測されうるという弱点があり、ClientHello 全体を封筒に入れる現行の ECH 方式に置き換わりました。DNS 側の信頼性と、outer/inner を同居させられるサーバー基盤が普及の前提条件であり、検証には openssl s_client の ECH 対応ビルドや、対応ブラウザの開発者ツールでハンドシェイクの拡張一覧を確認するとよいでしょう。
ネットワーク Article
Encrypted Client Hello(ECH)を実務で読む
TL;DRは入口です。実際に選ぶ・使う段階では、何を解決するか、何と比較するか、導入後にどこで詰まるかまで見る必要があります。
解決すること
TLS
比較で見る軸
難易度: advanced / カテゴリ: ネットワーク / タグ数: 6
導入後に効く点
outerとinnerの二重ClientHello構造を使い、outerはダミー値、innerが本物のSNI等を含む暗号化ペイロードとして運ばれる。
先に潰すリスク
用語だけ覚えても、設計・実装・運用でどこに効くかを確認しないと判断を誤る。
- 難易度
- advanced
- カテゴリ
- ネットワーク
- タグ数
- 6
判断チェックリスト
- 自社の用途が「TLS / ECH」に近いか確認する。
- 強みである「TLS1.3でも拡張SNIだけは平文で残り、経路上の観察者に接続先ドメインが漏れていた。ECHはClientHello全体を暗号化してこれを塞ぐ。」が本当に評価軸になるか確認する。
- 注意点の「用語だけ覚えても、設計・実装・運用でどこに効くかを確認しないと判断を誤る。」を運用で吸収できるか確認する。
- 公開値や仕様値は、対象プラン・対象機種・対象リージョンまで確認する。
- 既存システム、ID、ネットワーク、監視、バックアップとの接続方法を先に洗い出す。
- 小さく試してから、本番移行、権限設計、障害時手順、コスト監視を決める。