◆ TV録画予約用アプリ「EpgDataCap_Bon+EpgTimer_Bon」(EDCB)の"人柱版10.43"以降には、"EpgTimerSrv.exe"をWebサーバーとして動作させて、これにWebブラウザを用いてアクセスし録画予約などの操作ができる機能が追加された。
◆ この機能は、あくまでローカルのネットワーク環境(LAN・イントラネット内)で用いる事が前提の機能だが、これに、サーバー認証と通信暗号化の機能ならびにユーザ認証などのセキュリティ機能を備えた環境を別途に構築してそこを経由して接続するようにすることで、外出先などからノートPCやスマートフォンなどを使って、インターネット経由で自宅のTV録画サーバーに安全にアクセス・操作することができるようになる。本資料はその環境構築の手順を記したものである。
緊急 … "OpenSSL"で深刻な脆弱性問題「Heartbleed Bug」が発覚。(2014.4.8追記)
これは「秘密鍵が漏洩する可能性がある」という非常に深刻なもので、その為、本来ならSSL/TLSによって暗号化・保護されている筈の情報が、特殊な環境下でなくても容易に盗聴されてしまう可能性がある。
現在、世界中のサイト管理者がこの脆弱性の対策に追われているが、仮にこの脆弱性が悪用されてMITM攻撃をしかけられたとしても攻撃された痕跡は残らないとの事。(詳しくは本稿内の「81.補足事項(1) … "OpenSSL"の脆弱性問題「Heartbleed Bug」の詳細」の項を参照)
但し、この脆弱性を有するのは、"OpenSSL"の「Ver.1.0.1」〜「Ver.1.0.1f」と、ベータ版の「Ver.1.0.2-beta」〜「Ver.1.0.2-beta1」で、「Ver.1.0.0」系や「Ver.0.9.8」系といった古いバージョンについては影響はないとの事。
本稿でも紹介している"Apache"のオフィシャルサイト(*1)にてリリースされているWin32版のバイナリパッケージの現時点での最新版に同梱される"OpenSSL"のバージョンは、「Ver.0.9.8y」となっているので、本稿のようにバイナリパッケージを用いてシステムを構築したような場合(*2)(*3)はおそらく影響は無いと思われる。
*2 ソースコードからモジュールをビルドして環境を構築しているような場合で、"OpenSSL"の「Ver.1.0.1」〜「Ver.1.0.1f」もしくはベータ版の「Ver.1.0.2-beta」〜「Ver.1.0.2-beta1」を用いて環境構築している場合は、至急に"OpenSSL"の「Ver.1.0.1g」以降を入手してシステムをビルドし直したうえで、さらに「秘密鍵」や「証明書」なども再生成しなおす作業が必要となる。
*3 別途"mod_spdy"を用いて「SPDY」プロトコルによるサービスを公開しているような場合は、"OpenSSL"が「Ver.0.9.8」系などの古いディストリビューションであってもこの脆弱性の影響を受ける可能性があるとのことで、その場合は、"mod-spdy-beta"パッケージの最新版(2014.4.9リリースの「0.9.4.2-r413」以降)に更新する必要があるとの事。
注意 … EDCBシステムの構築手順に関する情報について。
なお、本資料はEDCBシステムの構築が完了してる事を前提とした内容となっており、よって同システムの構築手順などについては特には解説されていない。本資料で解説するセキュリティシステムは、基本的にはEDCBシステムとは別途に独立しており、よって、本資料はあくまで、そのセキュリティシステムの部分について、それを構築する手順と、それをEDCBシステムと連携させる手順とを解説した資料となっている。多くの方々がEDCBシステムの構築手順に関する情報を求めて本サイトを訪れて来られるケースが多い様だが、しかし、それらの情報については、既に多くの優秀な先人の方々によって大変解かり易く解説されたサイトが多数存在しているので、それらを参照されることをお奨めしたい。(2013.7.31追記)
< 免責事項・その他 >
この資料の作成者は、利用者がこの資料の情報を用いて行う一切の行為について、何ら責任を負うものではない事とする。
また、この資料は、あくまでその作成者の個人的な作業の覚書きとして作成されたものであり、不特定・任意の環境での作業を前提としたものではない。よって、これを利用する場合は、環境に依存する部分については、適宜各自の環境に合わせて読み替えて頂きたい。参考までに、本資料の作成者がこの資料を元に構築したシステムの構成を記しておく。
[Operating System]
Microsoft Windows XP-Professional SP3 (32bit)
[Web Server]
Apache ver.2.2.22 (including OpenSSL 0.9.8t)
[EDCB System]
EpgDataCap_Bon+EpgTimer_Bon 人柱版10.66
TVTest ver.0.7.23
BonDriver_PT-ST 人柱版3
[Runtime]
Microsoft .NET Framework 3.5 SP1
Microsoft .NET Framework 3.5 SP1 日本語 Language Pack
Microsoft .NET Framework 4
Microsoft Visual C++ 2005 SP1
Microsoft Visual C++ 2008 SP1
Microsoft Visual C++ 2010
◆ 構成の概要としては、フリーのWebサーバーアプリとして有名な"Apache"ならびに"OpenSSL"を導入し、それにまず、以下に示すセキュリティ機能を実装させる。
@ 独自のサーバー証明書を生成して、それを用いて接続先サーバーの検証を行い、接続先の"すり替わり"や"なりすまし"を排除して、確実に自分のサーバーに接続している確証が得られるようにする。
A 通信を暗号化(https通信)して通信内容の漏洩を防ぐ。
B ユーザーID&パスワード入力によるユーザー認証機能を設定してサーバーへの不正アクセスを防止する。
次に、このセキュリティを強化したWebサーバーに、更に「リバースプロクシ」の機能を設定して、これをフロントエンドのリバースプロキシサーバーとして動作させ、これによって、バックエンドのEDCBサーバー(EpgTimerSrv.exe)への外部からの接続要求を全て一旦、このフロントエンドのリバースプロキシサーバーを通すようにする(*1)。
*1 ルータのポートフォワード先は、EDCBサーバーではなく、このフロントエンドのリバースプロキシサーバーに設定する。
以上の構成によって、クライアントに対してはサーバー証明書を用いて接続先を保証する機能を提供し、EDCBサーバーに対してはユーザー認証を用いて未知の不特定ユーザーからの不正アクセスから保護する機能を提供するとともに、その双方に対して通信を暗号化することによってユーザー認証時に入力されたユーザーID&パスワード等も含めた全ての通信内容の漏洩を防止する機能を提供する。
┏━━━━━━━TV録画サーバーPC━━━━━━━┓
┌ Internet ┐ ┃ ┌──Apache──┐┌────EDCB────┐┃
│ │ ┃ │┌─────┐││┌────────┐│┃
┏ クライアントPC ┓ │ │ ┃┌→│SSL暗号化 ││││ EpgTimer.exe ││┃
┃┌──────┐┃ │暗号化通信│ ┃││├──↓──┤││└────────┘│┃
┃│Webブラウザ │----------------------┘││ユーザー認証 │││ │┃
┃└──────┘┃ │ │ ┃ │├──↓──┤││┌────────┐│┃
┗━━━━━━━━┛ │ │ ┃ ││リバースプロキシ│─→│EpgTimerSrv.exe ││┃
│ │ ┃ │└─────┘││└────────┘│┃
└─────┘ ┃ └───────┘└──────────┘┃
┗━━━━━━━━━━━━━━━━━━━━━━┛
◆ ユーザー認証には「Basic認証」を用いるが、これをそのままの状態で用いてしまうと、ユーザーID&パスワードがMIMEエンコードされただけの状態でネットに流れてしまう為に、第三者にユーザーID&パスワードが盗聴される危険がある。
そこで、そのBasic認証のセッションも含めた通信セッションの全体を、別途"SSL"(Secure Socket Layer)を用いて暗号化してやることで、ユーザ認証時のユーザーID&パスワードの送・受信も含めた全ての通信が暗号化された状態で行われる様にする。
参考 … 「Digest認証」について。
ユーザーID&パスワードをMD5で暗号化(ハッシュ化)して送ることで「Basic認証」より高い安全性が確保できるとされている「Digest認証」については、実状としては、対応ブラウザが最近のものに限られていたり、古い物であっても"IE6"のようにバグの為に正常動作しなかったり、また、そもそも「Basic認証」ほどには普及していなかったり、と色々問題が多いので利用は断念した。
◆ 「サーバー証明書」は、自分で認証・署名を行って最上位の「ルート証明書」(自己署名証明書)を作成し、それをサーバーとクライアント(Webブラウザ)の双方に設定することで、接続先の検証を行う。
補足 … 「自己署名証明書」のインターネットでの使用の是非について。
個人が私的に作成した「自己署名証明書」(ルート証明書)をインターネットで利用することについては、最近では「オレオレ証明書」などと揶揄されるなど「自己署名証明書の使用」を全て「悪」とするような風評が蔓延してしまっている。
まず最初にハッキリさせておくべき点は、ここで言う「証明書」とは、「何が出来る/出来ない」といったような、いわゆる「資格」や「能力」や「権利」といった要件を証明する為のものではなく、あくまで「身元」 … 即ち、「その人」が確実に「その人」本人であるという「識別」を行う為の証明書だという点だ。
この証明書の問題は、「鍵」と「家」に例えることが出来る。「インターネット」を「住宅街」に、「Webサイト」をその「住宅街」に立ち並ぶ「家」に例えるとして、その「住宅街」に立ち並ぶ「家」は皆どれも外見が似ている為に、それがたとえ自分の家であっても見分けがつかず、「家」を特定する唯一の条件は、手元にある「鍵」で、その「家」のドアを開けることができるかどうかでしか判断できないと仮定する。
自分で家を建てて、ドアの鍵穴も自分で取り付けて、それを開ける鍵も自分で管理しているAさんが自分の家に入る場合に、自分が管理しているその「鍵」でドアを開ける事が出来た「家」は「確実にAさんの家」と断定できる。
では、AさんがBさんの「家」を訪問する場合はどうすべきか。まず、Bさん本人から直接手渡しでBさんの家の「鍵」を受け取る事ができれば、その「鍵」でドアを開ける事ができた「家」は「確実にBさんの家」と判断することができる。しかし、仮にBさんの家への訪問客がAさんだけでなく非常に大勢の不特定多数の訪問客がある場合だと、その全ての訪問客に対して、Bさん本人が「鍵」を直接手渡しすることは現実的に不可能であり、その場合、Bさんは、鍵の配布を何がしかの第三者に委託する必要が生じてくる。ただし、その場合は、訪問客はBさん本人から鍵を受け取れない以上、受け取った「鍵」が果たして本当にBさんの家の鍵であるかどうか … もしかすると、Bさんに成りすまそうと企んだZさんが自分の家の鍵を「Bさんの家の鍵」と偽って渡したものかもしれない … といったような疑いが生じることとなり、訪問客が安心してBさんの家に訪問することができなくなってしまう。
そこでBさんは、有名な鍵メーカー「X社」に、自宅のドアの鍵穴の交換と、それを開けるための新たな鍵の管理ならびにその配布を依頼することにする。Bさんの家を訪れようとする訪問客は、この「X社」からBさんの家の鍵を受け取るようにするとともに、その鍵が確実にBさんの家の鍵であることを「X社が保証する」ようにすれば、不特定多数の訪問客を確実にBさんの家へ導くことができるようになる。
しかし、この「X社」のサービスは有料であるので、Bさん同様に訪問客の多いCさんは、その費用負担を渋った挙句に、とある暴挙にでる。安全をアピールするためにAさんを真似て自分でドアに「鍵穴」は取り付けてはみたものの、しかし … 「ドアの鍵は一応閉まっています。けれどもその鍵は配布しません。でも、そのドアはムリにこじ開ければ開けられるので、最初はそうやって入ってきてください。で、ドアの鍵は一応家の中に置いておくので、欲しい人は、ドアをこじ開けて家の中に入ってからそれを自分で取って、次回からはその鍵でドアを開けて入ってきてください」 … といった具合だ。
これでは「鍵」の意味が全く無いばかりか、そもそも訪問者は最初の訪問時に一体どうやってCさんの家を特定すればいいのかもわからない。ドアをむりやりこじ開けて入った家がCさんの家でなく、悪意をもったZさんの家だった場合は、それで訪問客が何らか危険な目に合う可能性もある。家の中に置いてあるという「鍵」にしても、そもそもその家が本当にCさんの家かどうかも判らない以上、その鍵についてもそれが本当にCさんの家の鍵かどうかも判らない。故に、それを手に入れたところで全く何の意味も無いどころか、その「鍵」がCさんの家のものではなく実は悪意をもったZさんの家のものだったような場合であっても、訪問者は「鍵」を手に入れることが出来た事によって安心してしまい、なんの疑いも無く「Zさんの家をCさんの家と思い込んで」その中に入り、そして、自分が話している相手が「実はCさんではなくZさんである」とも知らずに、自分の秘密を明かすようなことをしてしまうかもしれない …
それでもCさんは、「我が家のドアには"鍵"が付いているので"安全"です … みなさん"安心"して遊びに来てください」と声高に喧伝することをやめようとはしない …
「オレオレ証明書」で槍玉にあげられたのは、この「Cさん」の運用をそのままマネた「銀行」や「役所」や「大学」だ。「インターネット」という「広大な海」の中から自分達のWebサイトを確実に「識別」してもらえるようにする目的の為に「身元証明書」を作成するという所までは正しい。しかし、その証明書を配布する相手は、「銀行」や「役所」や「大学」といった組織が運営するWebサイトの場合、それは「"不特定"でなおかつ"多数"の"未知のユーザー"」であるはずだ。この場合に作成すべき証明書は、先の「Bさん」の例を見ても明らかなように、公的な立場の第三者に認証・発行を依頼するしかないことは明白である。なぜなら、彼らが独自に証明書を作ったとしても、それをユーザーに対して直接手渡すことが出来ない以上、その「"不特定"でなおかつ"多数"の"未知のユーザー"」の立場からすれば「それを信用するに足るだけの根拠や理由が全く無い」(*2)からだ。しかし、彼らは、その「単純」にして「明白」な事実を無視し、「ブラウザに表示される警告など無視してこの"身元証明書"を盲目的に正しいと信じて接続しろ」などと無責任な要求をした挙句に、「ブラウザの警告表示など無意味であり無視しても問題ない」などというような「ウソ」まで平然とついて、それが間違いである事を指摘されても一向に改めようとしないその態度こそが問題とされているのである。
*2 「外見」からそのWebサイトが「本物」なのか「偽物」なのかを判断する事は事実上不可能だ。「人間」の場合と違って「Webサイト」の「外見」は、そのソースコードをWebブラウザで表示させてコピーするなどの方法で簡単に、しかも、「本物と全く見分けがつかないようなレベル」で真似ることが出来てしまうからだ。
ましてや、その「"不特定"でなおかつ"多数"の"未知のユーザー"の立場からすれば信用するに足るだけの根拠や理由が全く無い」といった「素性の知れない証明書」を、自分のPCに「ルート証明書」(*3)としてインストールすることを強要するなど言語道断な話だ。
*3 ルート証明書 … 証明書の階層構造においてその"頂点"に君臨する絶対的効力を持つ"根幹"( = "root")的な証明書のこと。
対して「Aさん」の行為は果たして問題といえるのか。AさんもCさんも「鍵穴は自分で取り付けた」と言う点では同じだが、それを開ける「鍵」の使用や管理の点において、その健全性や安全性が全く異なることは、既に上記の例を見ても明らかなはずだ。Aさんは「自分の家には自分しか入らない」という前提のもとに、自分の家に自分で「鍵穴」をつけて、「それとペアであることが自分で確実に判っている鍵」を、これまた「自分しか使わない」という条件のもとで自分で管理している。逆に言えば、その鍵を不特定多数の未知の訪問客に配布するような事をしない限り、わざわざ費用を払ってまで「X社」のような第三者機関のサービス(「自分」の鍵を「自分」に配布してもらい、その「自分」の鍵が確実に「自分」の家の鍵であることを「自分」に対して保証してもらう …)を利用する必要もなければ、「利用しなければならない理由」も全く無いわけで、Aさんのこの「X社を利用しない運用形態」もまた「全く正しい運用形態」だと言える。
つまり、インターネット経由で自宅の「自分のサーバー」に「自分でアクセスする」という場合に、その接続先が確実に「自分のサーバー」であるという「識別」を行う目的の為に作成する証明書については、独自に作成されたものであっても、それは公的な立場の第三者にその「素性」と「効力」とを証明してもらうまでも無く「自分自身が十分にその<素性>と<効力>とを把握している」という点において「正しい証明書」と言える。なぜなら、それは得体の知れないサーバーで、得体の知れない第三者がそれを勝手に操作して作ったわけなどではなく、「自分で作った事が確実に判っている自分のサーバー」においてそれを「自分自身で操作する」ことによって「自分で作った事が確実に判っている証明書」であるからだ。
ちなみに、証明書はそれを作成する元となる「秘密鍵・公開鍵」の鍵ペアの生成に乱数が用いられるので、既存の証明書と同じものが作成される確率は殆ど"0"(ゼロ)であり、よって独自に作られた証明書であっても、それが既に出回っている証明書に悪影響を与えるような心配は殆ど無い。
そして、その証明書を、顔見知りでもない不特定多数のユーザーに対して、ネット越しで姿も見えないような相手から盲目的にダウンロードさせてインストールさせるといったような運用ではなく、「自分だけのPCに確実に自分自身の手で証明書を運んでインストールする」という条件下で運用するのであれば、その運用は「正しい運用」と言える。
逆に言えば、槍玉にあげられた「某銀行」や「某役所」や「某大学」などが、彼らがあくまで自分達で作成した「オレオレ証明書」での運用を望むというのであれば、その「オレオレ証明書」に「これは自分達が作った物に相違ない」といった趣旨の社印付きの紙の証明書を添えるなどした上で、それを、自分達の抱える全ての顧客やその他の一般ユーザーの手に確実に渡るよう、直接手渡しするとか、CDに焼いて郵送するなどすればいいのである。しかし、彼らの抱えるユーザーの数は100や200といった程度の数では済まないはずだ … それでもその「全員に証明書を手渡ししたりCDに焼いて郵送したりするコスト」は、「公的CAで正式な証明書発行と認証を受けるコスト」よりも安いと言えるのか? … 多少なりともマトモなスキルのあるベンダなりシステム管理者ならば考えるまでも無く判る話だ。
但し、「自分で作った証明書」を運用する場合に重要なのは、クライアントPCにもキチンとその自分で作成した証明書をインストールして「ブラウザに警告画面が一切表示されない状態」にする事が重要になる。そして、もしも万が一ブラウザに警告画面が表示された場合は、何らかの"MITM"攻撃(*4)をうけていると判断して接続を絶対にしないようにするといった運用を徹底・厳守する必要がある。
*4 "MITM"("Man in the Middle") 攻撃="中間者攻撃" … クライアントとサーバーの中間に悪意を持った第三者が割り込んで通信内容を盗聴したり改竄したりする攻撃。
また、証明書を後からインストールすることができない携帯電話のフルブラウザなどから警告を無視して接続するといったような運用も絶対に止めるべきだ。この場合、通信の暗号化がされるだけで、接続先の保証が得られない。「暗号化」の技術は、あくまで通信内容を符号化するだけの技術であり、通信相手が「なりすまし」によって別の第三者にすり替わる事までは防止してくれない。そもそも「暗号化」する目的とは「第三者の介入による盗聴や改ざんを防止すること」である筈なのに、その肝心の「接続相手の素性」に拘らなければ、いくら「暗号化」だけに拘ってみてもそれは全く意味がない行為だ。例えて言うなら、「ある人」に話の内容を聞かれまいと、話し相手の耳元でいくら小声で囁く努力をしてみたところで、その肝心の「話し相手」が「ある人」だったら、その「相手の耳元で小声で囁く」という行為自体が全く意味が無いというのと同じである。
通信における「安全性」は以下の3つの要素の"掛け算"で成り立っている。
@ 通信の機密性が保たれていること … 暗号化
A 相手の身元が明らかなこと … 証明書
B 通信内容の改竄が行われていないこと … デジタル署名等のハッシュ値の検証
これらの内のどれか一つでも"0"(ゼロ)になれば、"掛け算"の結果である「安全性」もまた"0"(ゼロ)になってしまうという事を肝に銘じておくべきだ。