暗号化されたすべてのクライアントストリームで、ピア検証がデフォルトで有効になりました。 デフォルトでは、OpenSSL のデフォルト CA バンドルを使ってピア証明書を検証します。 たいていの場合は、正しい SSL 証明書を持つサーバーと通信するならこれを変更する必要はありません。 OpenSSL が、よく知られた CA バンドルを使うように設定されているからです。
デフォルトの CA バンドルを上書きすることもできます。
openssl.cafile あるいは openssl.capath を設定すればグローバルに変更でき、コンテキストオプション
cafile あるいは
capath
を使えばリクエスト単位で変更できます。
一般的にはおすすめできませんが、
コンテキストオプション
verify_peer
を false にしてリクエストでのピア証明書の検証を無効化することもできます。
また同じく、ピア名の検証も、コンテキストオプション
verify_peer_name
を false にすれば無効化できます。
証明書のフィンガープリントの抽出と、その検証に対応しました。
新たに追加された openssl_x509_fingerprint() 関数が、
X.509 証明書からフィンガープリントを抽出します。また、
SSL ストリームコンテキスト
に二つのオプションが追加されました。
capture_peer_cert はピアの X.509 証明書を取り込み、
peer_fingerprint はピアの証明書が指定したフィンガープリントにマッチすることを確かめます。
PHP がデフォルトで使う暗号が更新され、 » Mozilla cipher recommendations に基づいた、よりセキュアなリストになりました。 リストにない例外は、anonymous Diffie-Hellman ciphers と RC4 です。
新しい定数
OPENSSL_DEFAULT_STREAM_CIPHERS で、この一覧にアクセスできます。
また、(過去のバージョンの PHP のように) 上書きもできます。上書きをするには、コンテキストオプション
ciphers
を設定します。
SSL/TLS の圧縮が、デフォルトで無効になりました。これは、CRIME 攻撃への対応です。
PHP 5.4.13 で新たにコンテキストオプション
disable_compression
が加わり、圧縮を無効にできるようになりました。そのデフォルト値が true (つまり圧縮が無効になっている)
に変わったのです。
SSL コンテキストオプション honor_cipher_order
が追加されました。これによって、暗号化されたストリームサーバーでの BEAST
脆弱性を除去するために、サーバーの暗号をクライアントよりも優先させられるようになります。
暗号化ストリームでネゴシエート済みのプロトコルと暗号へのアクセスが、
stream_get_meta_data() あるいは
stream_context_get_options() でできるようになりました。
これは、SSL コンテキストオプション
capture_session_meta が true になっている場合に有効です。
<?php
$ctx = stream_context_create(['ssl' => [
'capture_session_meta' => TRUE
]]);
$html = file_get_contents('https://google.com/', FALSE, $ctx);
$meta = stream_context_get_options($ctx)['ssl']['session_meta'];
var_dump($meta);
?>上の例の出力は以下となります。
array(4) {
["protocol"]=>
string(5) "TLSv1"
["cipher_name"]=>
string(20) "ECDHE-RSA-AES128-SHA"
["cipher_bits"]=>
int(128)
["cipher_version"]=>
string(11) "TLSv1/SSLv3"
}
暗号化クライアントストリームはすでに前方秘匿性に対応しています。 というのも、一般に前方秘匿性は、サーバーが制御するものだからです。 PHP の暗号化サーバーストリームが使っている証明書は前方秘匿性に対応しており、 何もしなくても有効になっています。 しかし、前方秘匿性に関してより決め細やかな制御をしたり、 互換性に関する問題に対応したりするために、 新たな SSL コンテキストオプションがいくつか追加されました。
ecdh_curve
このオプションで、ECDH 暗号で使う曲線を選択できるようになります。
省略した場合は prime256v1 を使います。
dh_paramDiffie-Hellman 鍵交換用のパラメータを含むファイルへのパス。 このファイルは、たとえば以下のようなコマンドで生成したものです。
openssl dhparam -out /path/to/my/certs/dh-2048.pem 2048
single_dh_use
true にすると、Diffie-Hellman パラメータを使うときに、
新たな鍵ペアを作成します。これにより、前方秘匿性が向上します。
single_ecdh_use
true にすると、ECDH 暗号スイートでのネゴシエート時に
新たな鍵ペアを作成します。これにより、前方秘匿性が向上します。
SSL や TLS の、特定のバージョンを指定できるようになりました。SSL コンテキストオプション
crypto_method を利用するか、
あるいはストリームラッパーの作成時に
(stream_socket_client() あるいは
stream_socket_server() を呼んで)
トランスポートを指定します。
SSL コンテキストオプション crypto_method には、
stream_socket_enable_crypto() 関数の
crypto_type と同様に、
許可するプロトコルをビットマスクで指定します。
| プロトコル | クライアントのフラグ | サーバーのフラグ | トランスポート |
|---|---|---|---|
| 任意のバージョンの TLS あるいは SSL | STREAM_CRYPTO_METHOD_ANY_CLIENT |
STREAM_CRYPTO_METHOD_ANY_SERVER |
ssl:// |
| 任意のバージョンの TLS | STREAM_CRYPTO_METHOD_TLS_CLIENT |
STREAM_CRYPTO_METHOD_TLS_SERVER |
tls:// |
| TLS 1.0 | STREAM_CRYPTO_METHOD_TLSv1_0_CLIENT |
STREAM_CRYPTO_METHOD_TLSv1_0_SERVER |
tlsv1.0:// |
| TLS 1.1 | STREAM_CRYPTO_METHOD_TLSv1_1_CLIENT |
STREAM_CRYPTO_METHOD_TLSv1_1_SERVER |
tlsv1.1:// |
| TLS 1.2 | STREAM_CRYPTO_METHOD_TLSv1_2_CLIENT |
STREAM_CRYPTO_METHOD_TLSv1_2_SERVER |
tlsv1.2:// |
| SSL 3 | STREAM_CRYPTO_METHOD_SSLv3_CLIENT |
STREAM_CRYPTO_METHOD_SSLv3_SERVER |
sslv3:// |
<?php
// file_get_contents() を使うには TLS 1.0 以降が必要です
$ctx = stream_context_create([
'ssl' => [
'crypto_method' => STREAM_CRYPTO_METHOD_TLS_CLIENT,
],
]);
$html = file_get_contents('https://google.com/', false, $ctx);
// TLS 1.1 あるいは 1.2 が必要です
$ctx = stream_context_create([
'ssl' => [
'crypto_method' => STREAM_CRYPTO_METHOD_TLSv1_1_CLIENT |
STREAM_CRYPTO_METHOD_TLSv1_2_CLIENT,
],
]);
$html = file_get_contents('https://google.com/', false, $ctx);
// 接続時に tlsv1.2:// ストリームソケットトランスポートを利用します
$sock = stream_socket_client('tlsv1.2://google.com:443/');
?>openssl_get_cert_locations() 関数が追加されました。 この関数は、PHP が CA バンドルを探す際のデフォルトの場所を返します。
<?php
var_dump(openssl_get_cert_locations());
?>上の例の出力は以下となります。
array(8) {
["default_cert_file"]=>
string(21) "/etc/pki/tls/cert.pem"
["default_cert_file_env"]=>
string(13) "SSL_CERT_FILE"
["default_cert_dir"]=>
string(18) "/etc/pki/tls/certs"
["default_cert_dir_env"]=>
string(12) "SSL_CERT_DIR"
["default_private_dir"]=>
string(20) "/etc/pki/tls/private"
["default_default_cert_area"]=>
string(12) "/etc/pki/tls"
["ini_cafile"]=>
string(0) ""
["ini_capath"]=>
string(0) ""
}
署名された公開鍵およびチャレンジ (SPKAC) の生成や抽出、そして検証のサポートが追加されました。
新たに追加された関数 openssl_spki_new()、
openssl_spki_verify()、
openssl_spki_export_challenge() そして
openssl_spki_export() で、
SPKAC が HTML5 の KeyGen 要素から生成した
PEM 公開鍵とチャレンジの作成、検証、エクスポートを行います。
openssl_spki_new秘密鍵とチャレンジ文字列、そしてハッシュアルゴリズムを指定して、 新しい SPKAC を生成します。
<?php
$pkey = openssl_pkey_new();
openssl_pkey_export($pkey, 'secret passphrase');
$spkac = openssl_spki_new($pkey, 'challenge string');
?>上の例の出力は以下となります。
SPKAC=MIIBXjCByDCBnzANBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEA3L0IfUijj7+A8CPC8EmhcdNoe5fUAog7OrBdhn7EkxFButUp40P7+LiYiygYG1TmoI/a5EgsLU3s9twEz3hmgY9mYIqb/rb+SF8qlD/K6KVyUORC7Wlz1Df4L8O3DuRGzx6/+3jIW6cPBpfgH1sVuYS1vDBsP/gMMIxwTsKJ4P0CAwEAARYkYjViMzYxMTktNjY5YS00ZDljLWEyYzctMGZjNGFhMjVlMmE2MA0GCSqGSIb3DQEBAwUAA4GBAF7hu0ifzmjonhAak2FhhBRsKFDzXdKIkrWxVNe8e0bZzMrWOxFM/rqBgeH3/gtOUDRS5Fnzyq425UsTYbjfiKzxGeCYCQJb1KJ2V5Ij/mIJHZr53WYEXHQTNMGR8RPm7IxwVXVSHIgAfXsXZ9IXNbFbcaLRiSTr9/N4U+MXUWL7
openssl_spki_verify指定した SPKAC を検証します。
<?php
$pkey = openssl_pkey_new();
openssl_pkey_export($pkey, 'secret passphrase');
$spkac = openssl_spki_new($pkey, 'challenge string');
var_dump(openssl_spki_verify($spkac));
?>openssl_spki_export_challenge指定した SPKAC から、関連付けられたチャレンジをエクスポートします。
<?php
$pkey = openssl_pkey_new();
openssl_pkey_export($pkey, 'secret passphrase');
$spkac = openssl_spki_new($pkey, 'challenge string');
$challenge = openssl_spki_export_challenge($spkac);
echo $challenge;
?>上の例の出力は以下となります。
challenge string
openssl_spki_exportPEM フォーマットされた RSA 公開鍵を、SPKAC からエクスポートします。
<?php
$pkey = openssl_pkey_new();
openssl_pkey_export($pkey, 'secret passphrase');
$spkac = openssl_spki_new($pkey, 'challenge string');
echo openssl_spki_export($spkac);
?>上の例の出力は以下となります。
-----BEGIN PUBLIC KEY----- MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDcvQh9SKOPv4DwI8LwSaFx02h7 l9QCiDs6sF2GfsSTEUG61SnjQ/v4uJiLKBgbVOagj9rkSCwtTez23ATPeGaBj2Zg ipv+tv5IXyqUP8ropXJQ5ELtbXPUN/gvw7cO5EbPHr/7eMhbpw8Gl+AfWxW5hLW8 MGw/+AwwjHBOwong/QIDAQAB -----END PUBLIC KEY-----