第II部: Java SE Security APIを使用したセキュアな通信
ここでは、セキュアな通信を実行するアプリケーションを構築する方法について説明します。Java SE プラットフォームは、アプリケーションがセキュアな通信を実行できるようにする3つの標準API(Java Generic Security Service (GSS)、Java SASL APIおよびJava Secure Socket Extension (JSSE))を提供します。アプリケーションを構築する場合、これらのAPIのうちのどれを使用すべきでしょうか。その答えは、プロトコルまたはサービスの要件、配備インフラストラクチャ、他のセキュリティ・サービスとの統合など、数多くの要因によって異なります。たとえば、LDAPクライアント・ライブラリを構築する場合は、Java SASL APIを使用する必要があります。SASLの使用は、LDAPのプロトコル定義の一部であるためです。別の例として、サービスがSSLをサポートする場合、サービスにアクセスしようとするクライアント・アプリケーションはJSSEを使用する必要があります。
課題3: Java Generic Security Service (GSS) APIの使用
この課題の目標
この課題の目標は、Java GSS APIを使用してセキュアな認証および通信を実行する方法について学習することです。
この課題の内容
Generic Security Service APIは、認証、メッセージの整合性、メッセージの機密性などのさまざまなセキュリティ・サービスにアクセスするための、統一されたC言語インタフェースを提供します。Java GSS APIは、対応するインタフェースをJavaアプリケーションに提供します。これを使用すると、アプリケーションは認証を実行してピアとのセキュアな通信を確立できます。GSS-APIおよびJava GSS-APIによってアクセスされるもっとも一般的なセキュリティ・サービスの1つは、Kerberosです。
この課題のリソース
- JAASおよびJava GSS-APIチュートリアルの紹介
- 「Generic Security Service API Version 2: Java Bindings」(RFC 2853)
- Java GSS JavaDoc APIドキュメント: org.ietf.jgss。
この課題の概要
この課題では、Java GSS APIを使用してセキュアに通信する方法を示すクライアント・サーバー・アプリケーションを扱います。クライアント部分とサーバー部分は、課題1: JAAS APIの使用に示されているように、最初にKerberosに対して認証します。これにより、資格がサブジェクトに格納されます。アプリケーションは、サブジェクトを使用してSubject.doAsの内部で、(基盤となるGSSメカニズムとしてKerberosを使用して) Java GSS操作を実行するアクションを実行します。Java GSS KerberosメカニズムはdoAsの内部で実行されるため、Kerberos資格をサブジェクトから取得し、それらを使用してピアとの認証およびメッセージのセキュアな交換を行います。
実行ステップ
-
GssServer.java
コードを参照してください。このコード・フラグメントは、サービス・プリンシパルがKDCに対して認証した後に実行するアクションを定義します。これによって、課題1: JAAS APIの使用の
MyAction
が置き換えられます。このコードは、最初にGSSManagerのインスタンスを作成し、それを使用して独自のクレデンシャルを取得してGSSContextのインスタンスを作成します。このコンテキストを使用して認証を実行します。認証が完了すると、暗号化された入力をクライアントから受け入れ、確立されたセキュリティ・コンテキストを使用してデータを復号化します。次に、セキュリティ・コンテキストを使用して元の入力と日付を含む応答を暗号化し、クライアントに返信します。 -
サンプル・コードをコンパイルします。
-
GssClient.java
コードを参照してください。このコードは、クライアント・プリンシパルがKDCに対して認証したあとに実行するアクションを定義します。これによって、課題1: JAAS APIの使用の
MyAction
が置き換えられます。このコードは、最初にGSSManagerのインスタンスを作成し、それを使用して通信対象のサービスのプリンシパル名を取得します。次に、GSSContextのインスタンスを作成し、サービスとの認証を実行します。認証が完了すると、確立されたセキュリティ・コンテキストを使用してメッセージを暗号化し、サーバーに送信します。次に、暗号化されたメッセージをサーバーから読み取り、確立されたセキュリティ・コンテキストを使用して復号化します。 -
サンプル・コードをコンパイルします。
-
新規のウィンドウを起動してサーバーを起動します。
% java -Djava.security.auth.login.config=jaas-krb5.conf GssServer
-
クライアント・アプリケーションを実行します。GssClientは、サービス名とそのサービスが実行されているサーバーの名前の2つのパラメータを取ります。たとえば、サービスがマシンj1hol-001上で実行されているhostの場合は、次のように入力します。
% java -Djava.security.auth.login.config=jaas-krb5.conf GssClient host j1hol-001
パスワードの入力を求められた場合は、
change_it
を入力します。 -
クライアントおよびサーバー・アプリケーションのウィンドウにそれぞれ次の出力が表示されます。
GssServerを実行した出力の例:
Authenticated principal: [host/j1hol-001@J1LABS.EXAMPLE.COM] Waiting for incoming connections.. Got connection from client /192.0.2.102 Context Established! Client principal is test@J1LABS.EXAMPLE.COM Server principal is host/j1hol-001@J1LABS.EXAMPLE.COM Mutual authentication took place! Received data "Hello There!" of length 12 Confidentiality applied: true Sending: Hello There! Thu May 06 12:11:15 PDT 2005
GssClientを実行した出力の例:
Kerberos password for test: change_it Authenticated principal: [test@J1LABS.EXAMPLE.COM] Connected to address j1hol-001/192.0.2.102 Context Established! Client principal is test@J1LABS.EXAMPLE.COM Server principal is host@j1hol-001 Mutual authentication took place! Sending message: Hello There! Will read token of size 93 Received message: Hello There! Thu May 06 12:11:15 PDT 2005
サマリー
この課題では、Java GSS APIを使用してお互いセキュアに認証および通信を行うクライアント/サーバー・アプリケーションを記述する方法について学習しました。
次のステップ
-
課題4: Java SASL APIの使用に進み、Java SASL APIを使用してお互いセキュアに認証および通信を行うクライアント/サーバー・アプリケーションを記述する方法について学習します。
-
課題5: KerberosでのJava Secure Socket Extensionの使用に進み、JSSEを使用してお互いセキュアに認証および通信を行うクライアント/サーバー・アプリケーションを記述する方法について学習します。
-
課題6: シングル・サインオンの配備に進み、Kerberos環境でシングル・サインオンを行う場合に使用したサンプル・プログラムを構成する方法について学習します。
課題4: Java SASL APIの使用
この課題の目標
この課題の目標は、Java SASL APIを使用してセキュアな認証および通信を実行する方法について学習することです。
この課題の内容
SASL (Simple Authentication and Security Layer)は、チャレンジ・レスポンス・プロトコルを指定します。このプロトコルでは、1つには認証目的、もう1つには認証後通信を続行するセキュリティ・レイヤーを確立する目的(オプション)で、クライアントとサーバーがデータを交換します。SASLでは異なるメカニズムを使用できます。このようなメカニズムはそれぞれ、交換されるデータと名前を定義するプロファイルによって識別されます。SASLは、LDAPv3やIMAPv4などの接続ベースのプロトコルで使用されます。SASLは、RFC 4422で説明されています。
Java SASL APIは、メカニズムに依存しない方法でSASLを使用するアプリケーション用のAPIを定義します。たとえば、SASLを使用するネットワーク・プロトコルのライブラリを記述する場合、Java SASL APIを使用して、ピアと交換するデータを生成できます。ライブラリが配備されるときに、ライブラリで使用するメカニズムを動的に構成できます。
認証以外に、SASLを使用して認証後に使用されるセキュリティ層とのネゴシエーションを行うことができます。ただし、GSS-APIとは異なり、セキュリティ層のプロパティ(整合性を求めるか機密性を求めるかなど)はネゴシエーション時に決定されます(GSS-APIでは、メッセージごとに機密性をオンまたはオフにできます)。
この課題のリソース
この課題の概要
この課題では、Java SASL APIを使用してセキュアに通信する方法を示すクライアント・サーバー・アプリケーションを扱います。クライアント部分とサーバー部分は、課題1: JAAS APIの使用を使用して最初にKerberosに対して認証します。これにより、資格がサブジェクトに格納されます。アプリケーションは、サブジェクトを使用してSubject.doAsの内部で、(基盤となるSASLメカニズムとしてKerberosを使用して) Java SASL API操作を実行するアクションを実行します。SASL/Kerberosメカニズムは、doAsの内部で実行されるため、Kerberos資格をサブジェクトから取得し、それらを使用してピアとの認証およびメッセージのセキュアな交換を行います。
この例は、AppConnection
クラスによって実装される単純なプロトコルを使用します。このプロトコルは、認証コマンドおよびデータ・コマンドを交換します。各コマンドは、タイプ(AppConnection.AUTH_CMD
など)、後続のデータの長さおよびデータ自体で構成されています。データが認証または暗号化された/整合性が保護されたアプリケーション・データ用の場合、そのデータはSASLバッファです。それ以外の場合は、プレーンなアプリケーション・データです。
実行ステップ
-
SaslTestServer.java
サンプル・コードを参照してください。このコード・フラグメントは、サービス・プリンシパルがKDCに対して認証した後に実行するアクションを定義します。これによって、課題1: JAAS APIの使用の
MyAction
が置き換えられます。サーバーは、サポートする保護の品質(QOP)を指定し、SaslServerのインスタンスを作成して認証を実行します。SASLのチャレンジ応答プロトコルは、whileループの中で実行されています。そこでサーバーは、チャレンジをクライアントに送信しクライアントからの応答を処理します。認証後、認証されたクライアントのアイデンティティをgetAuthorizedID()メソッドの呼出しによって取得できます。セキュリティ層がネゴシエーションされた場合、サーバーはクライアントとセキュアにデータを交換できます。 -
サンプル・コードをコンパイルします。
-
SaslTestClient.java
サンプル・コードを参照してください。このコードは、クライアント・プリンシパルがKDCに対して認証したあとに実行するアクションを定義します。これによって、課題1: JAAS APIの使用のMyActionが置き換えられます。プログラムは、必要な保護の品質(この場合は、機密性)を最初に指定し、次に認証に使用する
SaslClient
のインスタンスを作成します。次に、メカニズムに初期応答があるかどうかをチェックし、ある場合は、空のバイト配列でevaluateChallenge()
メソッドを呼び出すことによって応答を取得します。次に、応答をサーバーに送信して認証を開始します。SASLのチャレンジ応答プロトコルは、whileループの中で実行されています。そこでクライアントは、サーバーから取得したチャレンジを評価してチャレンジに対応する応答をサーバーに送信します。認証後、クライアントは、ネゴシエーションされたセキュリティ層を使用してサーバーとの通信に進むことができます。 -
サンプル・コードをコンパイルします。
-
新規のウィンドウを起動してサーバーを起動します。
SaslTestServer
は、サービス名とそのサービスが実行されているサーバーの名前の2つのパラメータを取ります。たとえば、サービスがマシンj1hol-001上で実行されているhostの場合は、次のように入力します。% java -Djava.security.auth.login.config=jaas-krb5.conf SaslTestServer host j1hol-001
-
クライアント・アプリケーションを実行します。
SaslTestClient
は、サービス名とそのサービスが実行されているサーバーの名前の2つのパラメータを取ります。たとえば、サービスがマシンj1hol-001上で実行されているhostの場合は、次のように入力します。% java -Djava.security.auth.login.config=jaas-krb5.conf SaslTestClient host j1hol-001
セキュアなパスワードを指定します。
-
クライアントおよびサーバー・アプリケーションのウィンドウにそれぞれ次の出力が表示されます。
SaslTestServer
を実行した出力の例:Authenticated principal: [host/j1hol-001@J1LABS.EXAMPLE.COM] Waiting for incoming connections... Got connection from client /192.0.2.102 Client authenticated; authorized client is: test@J1LABS.EXAMPLE.COM Negotiated QOP: auth-conf Received: Hello There! Sending: Hello There! Fri May 07 15:32:37 PDT 2005 Received data "Hello There!" of length 12
SaslTestClient
を実行した出力の例(passwordは、指定したパスワードに置き換えられます):Kerberos password for test: password Authenticated principal: [test@J1LABS.EXAMPLE.COM] Connected to address j1hol-001/192.0.2.102 Client authenticated. Negotiated QOP: auth-conf Sending: Hello There! Received: Hello There! Fri May 07 15:32:37 PDT 2005
サマリー
この課題では、Java SASL APIを使用してお互いセキュアに認証および通信を行うクライアント/サーバー・アプリケーションを記述する方法について学習しました。
次のステップ
-
課題5: KerberosでのJava Secure Socket Extensionの使用に進み、JSSEを使用してお互いセキュアに認証および通信を行うクライアント/サーバー・アプリケーションを記述する方法について学習します。
-
課題6: シングル・サインオンの配備に進み、Kerberos環境でシングル・サインオンを行う場合に使用したサンプル・プログラムを構成する方法について学習します。
課題5: KerberosでのJava Secure Socket Extensionの使用
この課題の目標
この課題の目標は、JSSE APIを使用して、Kerberos暗号化方式群を使用したセキュアな認証および通信を実行する方法について学習することです。
この課題の内容
Secure Socket Layer (SSL)とTransport Layer Security (TLS)は、インターネットで暗号化を実装する場合にもっともよく使用されるプロトコルです。TLSは、SSLから発展したインターネット標準です。SSL/TLSは、アプリケーション・レベルのプロトコル(HTTPやLDAPなど)にセキュアな認証と通信を提供します。たとえば、HTTPSはSSL/TLSを介してHTTPを使用した結果のプロトコルです。SSL/TLSは、HTTPなどの標準プロトコルに対して使用されるだけでなく、セキュアに通信する必要がある、カスタム・プロトコルを使用するカスタム・アプリケーションを構築する場合にも広く使用されます。
SSL/TLSは、従来は証明書ベースの認証を使用しており、一般にサーバー認証に使用されます。たとえば、ブラウザなどのWebクライアントがユーザーに代わってセキュアなWebサイト(サーバー)にアクセスすると、サーバーは、ブラウザがサーバーのアイデンティティを検証できるようにサーバーの証明書をブラウザに送信します。これにより、ユーザーが機密情報(クレジット・カード情報など)を偽のサーバーに公開することはありません。最近、新しい標準によって、TLSでKerberosを使用できるようになりました。つまり、証明書ベースの認証を使用する代わりに、アプリケーションはKerberos資格を使用して、配備環境でKerberosインフラストラクチャを利用できます。Kerberos暗号化方式群を使用すると、サーバーだけでなくクライアントも認証される相互認証が自動的にサポートされます。
特定のアプリケーションでJava GSS、Java SASLまたはJSSEを使用するかどうかの決定は、アプリケーションが相互に作用するサービス(によって使用されているプロトコル)、配備環境(PKIまたはKerberosベース)、アプリケーションのセキュリティ要件など、複数の要因に依存する場合がよくあります。JSSEは、I/Oおよびトランスポートを処理するセキュアなエンドツーエンドのチャネルを提供します。一方、Java GSSおよびJava SASLは、データの暗号化および整合性保護を提供しますが、セキュリティ保護されたデータをピアにトランスポートするのはアプリケーションの担当です。JSSEとJava GSSを使用するタイミングを決定する要因の詳細は、ドキュメントJava GSS-APIおよびJSSEをいつ使用するかで説明しています。
この課題のリソース
この課題の概要
この課題では、JSSEおよびKerberos暗号化方式群を使用してセキュアに通信する方法を示すクライアント・サーバー・アプリケーションを扱います。クライアント部分とサーバー部分は、課題1: JAAS APIの使用を使用して最初にKerberosに対して認証します。これにより、資格がサブジェクトに格納されます。アプリケーションは、サブジェクトを使用してSubject.doAsの内部で、(Kerberos暗号化方式群を使用して) JSSE操作を実行するアクションを実行します。Kerberos暗号化方式群の実装はdoAsの内部で実行されるため、Kerberos資格をサブジェクトから取得し、それらを使用してピアとの認証およびメッセージのセキュアな交換を行います。この例では、改行で終了されるメッセージ(ネゴシエーションが行われた暗号化方式群を使用して暗号化され、整合性が保護される)を、クライアントとサーバー間で送受信します。
標準(RFC 2712)に従って、すべてのKerberos対応TLSアプリケーションは、同じサービス名(host)を使用します。このため、この課題では、Kerberosサービス名を明示的に指定する必要はありません。
実行ステップ
-
JsseServer.java
サンプル・コードを参照してください。このコード・フラグメントは、サービス・プリンシパルがKDCに対して認証した後に実行するアクションを定義します。これによって、課題1: JAAS APIの使用の
MyAction
が置き換えられます。サーバーは最初に、SSLServerSocketを作成します。これは、SSLServerSocketが必要に応じて自動的な認証、暗号化および復号化を提供する点を除いて、プレーンなServerSocketを作成するアプリケーションと似ています。次に、サーバーは使用する暗号化方式群を設定します。さらに、サーバーはループで実行され、SSLクライアントからの接続を受け入れ、SSLソケットから読み書きします。サーバーは、getLocalPrincipal()およびgetPeerPrincipal()メソッドを呼び出すことによって、ソケットの所有者のアイデンティティを調べることができます。 -
サンプル・コードをコンパイルします。
-
JsseClient.java
サンプル・コードを参照してください。このコードは、クライアント・プリンシパルがKDCに対して認証したあとに実行するアクションを定義します。これによって、課題1: JAAS APIの使用の
MyAction
が置き換えられます。クライアントは最初に、SSLSocketを作成します。次に、クライアントは使用する暗号化方式群を設定します。次に、クライアントは、SSLSocketを使用してソケットの入力/出力ストリームを読み書きすることによって、サーバーとメッセージを交換します。クライアントは、getLocalPrincipal()およびgetPeerPrincipal()メソッドを呼び出すことによって、ソケットの所有者のアイデンティティを調べることができます。 -
サンプル・コードをコンパイルします。
-
新規のウィンドウを起動してサーバーを起動します。
JsseServer
は、JSSEサービスが実行されているサーバーの名前の1つのパラメータを取ります。たとえば、マシンj1hol-001上で実行されている場合は、次のように入力します。% xterm & % java -Djava.security.auth.login.config=jaas-krb5.conf JsseServer j1hol-001
-
クライアント・アプリケーションを実行します。
JsseClient
は、JSSEサービスが実行されているサーバーの名前の1つのパラメータを取ります。たとえば、サービスがマシンj1hol-001上で実行されている場合は、次のように入力します。% java -Djava.security.auth.login.config=jaas-krb5.conf JsseClient j1hol-001
セキュアなパスワードを指定します。
-
クライアントおよびサーバー・アプリケーションのウィンドウにそれぞれ次の出力が表示されます。
JsseServer
を実行した出力の例:Authenticated principal: [host/j1hol-001@J1LABS.EXAMPLE.COM] Waiting for incoming connections... Got connection from client /192.0.2.102 Received: Hello There! Sending: Hello There! Fri May 07 15:32:37 PDT 2005 Cipher suite in use: TLS_KRB5_WITH_3DES_EDE_CBC_SHA I am: host/j1hol-001@J1LABS.EXAMPLE.COM Client is: test@J1LABS.EXAMPLE.COM
JsseClient
を実行した出力の例(passwordは、指定したパスワードに置き換えられます):Kerberos password for test: password Authenticated principal: [test@J1LABS.EXAMPLE.COM] Sending: Hello There! Received: Hello There! Fri May 07 15:32:37 PDT 2005 Cipher suite in use: TLS_KRB5_WITH_3DES_EDE_CBC_SHA I am: test@J1LABS.EXAMPLE.COM Server is: host/j1hol-001@J1LABS.EXAMPLE.COM
サマリー
この課題では、基盤となる認証システムとしてKerberosを使用し、JSSEを使用してお互いセキュアに認証および通信を行うクライアント/サーバー・アプリケーションを記述する方法について学習しました。
次のステップ
課題6: シングル・サインオンの配備に進み、課題3、4、および5のサンプル・プログラムを構成してKerberos環境でシングル・サインオンを行う方法について学習します。