サーバー証明書なお話

たまに Windows Azure Platform (WAP)での証明書の取り扱いに関する話が挙がるので、簡単におさらいしてみました。
※すでに証明書の基本なんて知ってるよ!Azure に関するところだけ知りたい!という方は こちらこちら が詳しいですので、そちらへGo!

 

最初に、このエントリは自分の備忘録も兼ねてるのでだいぶ端折っている部分もあります。より正確な情報はちゃんとした文献やらRFCを参照くださいませ。
※その割にはやたら長くなってしまった…

HTTPS

よくWebでログイン処理や決済処理等で利用される HTTPS ですが、こちらは HTTP over SSL/TLS の略です。
つまるところ、 SSL/TLS を使ってメッセージを暗号化した HTTP な通信ということになります。

※ HTTPS では SSL/TLS を使って通信内容の暗号化はしてくれますが、通信相手が想定している正しい相手かどうか(信頼できるかどうか)は気にしません。(盗聴は防止できますが、なりすまし等は保護されません)
普段ブラウザ等で HTTPS なサイトに接続した際に警告が表示されたりする場合、それは HTTPS の機能というよりは SSL/TLS の機能に基づいてブラウザが判断しています。
(なのでフィッシング対策等ではブラウザ側でどのように警告するか、確認するか、利用者に知らせるかなどが重要になります)

SSL/TLS

SSL は Secure Sockets Layer の略称。TLS は Transport Layer Security の略称です。
TLS は SSL の後継のような位置づけになっています。SSL は3.0、TLSは1.2が最新です。(TLS 1.0 のネゴシエーションにおけるバージョン番号は SSL3.0 より新しいということで 3.1)

SSL/TLS では暗号化認証改ざん検出の機能が提供されています。それぞれでどのようなアルゴリズムが利用できるかは提供するバージョンで異なり、サーバー・クライアント双方で利用できるアルゴリズムから選択することになります。

※通信のやり取りについては、こちらのWikipediaの図(直リンク)がわかりやすいです。
※SSL/TLS そのものは暗号化通信そのものの話なので、アプリケーション層のプロトコルには依存しません。なので、 HTTPS だけでなく SSH など幅広く使われています。

暗号化

SSL/TLS では、暗号化の方式として共通鍵方式を使用して通信内容を暗号化します。
暗号化に使用するアルゴリズムとしては、DES や 3DES、AES 等が利用されます。

さて共通鍵方式を使用するということは、事前に双方で共通鍵を持っておかないと暗号化も復号もできません。
SSL/TLS では、クライアント/サーバーそれぞれのから提供される乱数を基に組み合わせて共通鍵を4種類生成し、双方で保持します。(共通鍵の生成は、生成後の鍵のやり取りを考えるとクライアントで生成されることになります)

…で、共通鍵を生成したのはいいけど、その鍵はサーバーにもクライアントにもないといけません。なんせ共通なので。
あれ、でもクライアントで鍵を生成しましたよね?ということで、生成後は共通鍵を今度は公開鍵/秘密鍵方式で鍵そのものを暗号化して、サーバーに送信します。
※共通鍵方式は性質上、共通鍵をいかに安全に受け渡しするかというところが重要なポイントになります。SSL/TLS では、この共通鍵方式の問題を公開鍵/秘密鍵方式を利用することでクリアしています。

…ということで、サーバー/クライアント双方に共通鍵ができた状態で初めて暗号化通信が開始されます。(暗号化・復号は共通鍵を利用します)

…さぁだんだん本題に近づいてきました。(長いな~)

認証

SSL/TLS では、通常サーバーだけがサーバー証明書を提示し、クライアントが正当性を検証することで、接続先が信頼するに足るかどうかを判断します。
※ちなみに逆でも同じようにサーバーも、クライアントが正当かどうか検証し相互に認証する方式もあります。相互TLSとかがそうですね。(IIS の SSL の設定のところでもちゃんとオプションがあります)

この時に利用するのが、サーバー証明書になります。
サーバー証明書では、なりすましを防ぐために認証局から署名されており、クライアントは接続先とサーバー証明書に記載されているサーバー名や、署名した認証局が信頼できるかどうかを検証することができます。(CA証明書の確認)
※同じように期限切れで発行された証明書が失効していないかどうかも確認することで、より厳密に検証できます。(ブラウザの設定で変えたりできますね)

さてこのサーバー証明書には公開鍵が含まれており、公開鍵を抽出することで、サーバーに対して送信するデータを暗号化することができます。
SSL/TLS 通信では、まず最初にサーバー証明書をサーバーより取得し、接続先の検証を行い公開鍵を抽出します。その後は共通鍵を生成して~といった通信の流れになります。

改ざん検出

SSL/TLS では、データ送信する際にハッシュ値を付加し、改ざんされていないかどうかを検出できるようにする機能があります。
レコードのシーケンス番号なども含まれているので、途中で改ざんされても検出することが可能です。
アルゴリズム的には MD-5、SHA-1 や SHA-256 が利用できます。

公開鍵/秘密鍵方式

さて SSL/TLS の暗号や認証でも出てきた公開鍵/秘密鍵方式ですが、この仕組みは公開鍵で暗号化し、秘密鍵で復号する方式です。
なので、公開鍵と秘密鍵は鍵として別物ですが、関連のある一対のものなっています。
※PGPなどもこの方式を利用していますね。
公開鍵は名前の通り公開されていますが、秘密鍵は復号する本人だけが所有することになります。

使い方的には広く公開されてる受信者の公開鍵を用いて送信者が暗号化し、受信者へ暗号文を送付します。
暗号文を受け取った受信者は、秘密鍵を使って平文に復号します。めでたしめでたし。

さてこの方式にも問題点があります。Aさんと名乗って公開鍵を公開してるが実はBさんでした!というような、なりすましですね。
で、こういった問題に対応するために信頼できる第三者機関が認証局(CA)というものを運営し、Aさんが正しくAさんであることを証明する仕組みを利用することになります。
先ほどのAさんは、Aさん自身が秘密鍵を持ち、対応する公開鍵を認証局に署名付きで発行してもらうことで、正しくAさんであることを保証します。

サーバー証明書

さて、サーバー証明書の説明までやっときました。
つまるところサーバー証明書というのは、認証局によって署名された、サーバーの公開鍵です。
Windowsだと、このサーバー証明書は拡張子が .cer ファイルになりますね。
こちらに、そのサーバーがどんな名前で、どこの認証局によって署名されたかが改ざんされてない形でわかり、かつ公開鍵として機能します。
※公開鍵だけなので、暗号化することはできても、復号することはできません。

また認証局そのものも、別の認証局から証明されるようになっています。で、たどっていくと一番上の最初の認証局になるわけですが、それをルート認証局(ルートCA)と呼んでます。
※WindowsであればルートCAの証明書はあらかじめインストールされていたりしますね。(是非証明書管理コンソールで見てみてください。管理コンソールは certmgr.msc で表示できます。※Windows 7の場合)

サーバー証明書と秘密鍵

さてサーバー証明書を発行してもらって、暗号通信を行うには公開鍵だけでなく秘密鍵が必要ですね。
Windows、特にIIS等では認証局に発行してもらうためにリクエストを作成し、インポートする機能がありますがここで何をしているかというと、

  • 対象となるサーバーの秘密鍵を作成する
  • 秘密鍵に対応した公開鍵と署名をもらう為に認証局に提示するリクエストを作成する

の2つを最初に処理しています。
Openssl 等のコマンドを利用すると秘密鍵も .pem ファイル等で管理できるのですが、Windows上で標準機能を使うと秘密鍵の管理は完全にOS任せ/IIS任せで触ることができません。
また、サーバー証明書の要求は .csr ファイルになります。

認証局側では要求を受け取り、署名をして .cer (サーバー証明書)を返します。

要求を作成したサーバーでは、 .cer をインポートして初めて秘密鍵と公開鍵が対になり、クライアントから送信された暗号文を復号することができるようになります。(つまり SSL/TLS で通信できるようになる)

一連のステップで要求を取り消したり、要求を作成したサーバーと異なるサーバーに .cer をインポートしたりすると、秘密鍵と公開鍵がペアになりませんので SSL/TLS で使うことはできません。
※うまくできないのはここで引っかかっているケースが一番多いんじゃないでしょうか。
※全部自分で制御したければ Openssl 等を使うほうがいいですね。。。

ちなみに要求を作成する際にサーバー名等を指定しますが、要求を作成しているサーバー名じゃなくて、証明してほしいサーバー名になります。(ここで間違うと、証明書と実際にアクセスしてるURLのサーバー名が違うとかでブラウザが警告だしたりします)
※また認証局は Active Directory で提供されるCAや、自分自身で署名する自己署名などでもOKです。(単にブラウザが認証局を認識できなかったりして警告がでるだけで、通信の暗号化そのもには影響ありません。ただし発行元が信頼できないということですので、テストではよくても公開時はいろいろ問題になるので注意が必要です)

Windows Azure で クライアントと HTTPS 通信するには

さぁ、やっと本題ですよ。
Windows Azure 上で、サービスとして Web Role 等を HTTPS で暗号化する場合、今まで説明してきたような理屈によってサーバー上に秘密鍵があり、対応する公開鍵が公開されないといけません。

ということで、公開用のサーバー証明書を手元で要求・発行してもらい、いったんインポートした後、秘密鍵と公開鍵(サーバー証明書)を含めた PKCS#12 形式でエクスポートしたものを Windows Azure 上に保管する必要がある、という理屈がなんとなくおわかり頂けたでしょうか。
※おそらく Azure Portal サイト等でアップロードした後、各 Windows Azure 上に展開・設定しているのだと思います。

おわりに

このエントリで、なんとなく使われている証明書や HTTPS に関する理解が深まったり、興味を持っていただけると幸いです。

サーバー証明書に基づく暗号化通信は、いまや HTTPS だけに限らず SSH やPKI、 Federation 認証等に必須な技術になっています。
たぶんこのエントリのような事を知らなくてもこのあたりの技術を活用することで多数の恩恵は受けられると思いますが、知ってると何かあった際のトラブルシュートや、別の技術ができてきた際の理解の助けになるんじゃないかな~と思います。

え?言いたいことはわかったけど、余計にわからなくなったって?それは私の不徳ですね…申し訳ないですw

もし、間違い等見つけられた方は連絡頂けるとすごいうれしいです。

※Azure のサービス管理用の証明書が秘密鍵無しでいい理由はもうちょっと調べないといけないなぁ~。。。 x.509 v3ってところなんだとは思うんですが…だれか教えてください。
2010.10.12 update:理屈がわかったので追記しました。 (→ こちら

参考

広告

サーバー証明書なお話」への1件のフィードバック

  1. ピンバック: Windows Azure Platform (WAP)での証明書の取り扱いに関するおさらい | fullvirtueの世界

コメントを残す

以下に詳細を記入するか、アイコンをクリックしてログインしてください。

WordPress.com ロゴ

WordPress.com アカウントを使ってコメントしています。 ログアウト / 変更 )

Twitter 画像

Twitter アカウントを使ってコメントしています。 ログアウト / 変更 )

Facebook の写真

Facebook アカウントを使ってコメントしています。 ログアウト / 変更 )

Google+ フォト

Google+ アカウントを使ってコメントしています。 ログアウト / 変更 )

%s と連携中