|
| 1 | +--TEST-- |
| 2 | +SNI 001 |
| 3 | +--SKIPIF-- |
| 4 | +<?php |
| 5 | + if (!extension_loaded('openssl')) die("skip openssl extension not available"); |
| 6 | + if (!getenv('SNI_TESTS')) die("skip Set SNI_TESTS to enable this test (uses remote resources)"); |
| 7 | +?> |
| 8 | +--FILE-- |
| 9 | +<?php |
| 10 | +/* Server Name Indication (SNI) tests |
| 11 | + * |
| 12 | + * This test relies on https://sni.velox.ch/ and thus is disabled by default. |
| 13 | + * |
| 14 | + * sni.velox.ch uses 3 certificates : |
| 15 | + * - CN=alice.sni.velox.ch (sent in response to server_name = alice.sni.velox.ch or not set) |
| 16 | + * - CN=bob.sni.velox.ch (sent in response to server_name = bob.sni.velox.ch) |
| 17 | + * - CN=*.sni.velox.ch (sent in response to server_name = mallory.sni.velox.ch or *.sni.velox.ch or sni.velox.ch) |
| 18 | + * |
| 19 | + * The test sends requests to the server, sending different names, and checks which certificate |
| 20 | + * the server returned. |
| 21 | + */ |
| 22 | + |
| 23 | +function context() { |
| 24 | + return stream_context_create(array( |
| 25 | + 'ssl' => array( |
| 26 | + 'capture_peer_cert' => true, |
| 27 | + ), |
| 28 | + )); |
| 29 | +} |
| 30 | + |
| 31 | +function get_CN($context) { |
| 32 | + |
| 33 | + $ary = stream_context_get_options($context); |
| 34 | + assert($ary); |
| 35 | + |
| 36 | + $cert = $ary['ssl']['peer_certificate']; |
| 37 | + assert($cert); |
| 38 | + |
| 39 | + $cert_ary = openssl_x509_parse($cert); |
| 40 | + return $cert_ary['subject']['CN']; |
| 41 | +} |
| 42 | + |
| 43 | +function do_http_test($url, $context) { |
| 44 | + |
| 45 | + $fh = fopen($url, 'r', false, $context); |
| 46 | + assert($fh); |
| 47 | + |
| 48 | + var_dump(get_CN($context)); |
| 49 | +} |
| 50 | + |
| 51 | +function do_ssl_test($url, $context) { |
| 52 | + |
| 53 | + $fh = stream_socket_client($url, $errno, $errstr, |
| 54 | + ini_get("default_socket_timeout"), STREAM_CLIENT_CONNECT, $context); |
| 55 | + assert($fh); |
| 56 | + |
| 57 | + var_dump(get_CN($context)); |
| 58 | +} |
| 59 | + |
| 60 | +function do_enable_crypto_test($url, $context) { |
| 61 | + |
| 62 | + $fh = stream_socket_client($url, $errno, $errstr, |
| 63 | + ini_get("default_socket_timeout"), STREAM_CLIENT_CONNECT, $context); |
| 64 | + assert($fh); |
| 65 | + |
| 66 | + $r = stream_socket_enable_crypto($fh, true, STREAM_CRYPTO_METHOD_TLS_CLIENT); |
| 67 | + assert($r); |
| 68 | + |
| 69 | + var_dump(get_CN($context)); |
| 70 | +} |
| 71 | + |
| 72 | +/* Test https:// streams */ |
| 73 | + |
| 74 | +echo "-- auto host name (1) --\n"; |
| 75 | +do_http_test('https://alice.sni.velox.ch/', context()); |
| 76 | + |
| 77 | +echo "-- auto host name (2) --\n"; |
| 78 | +do_http_test('https://bob.sni.velox.ch/', context()); |
| 79 | + |
| 80 | +echo "-- auto host name (3) --\n"; |
| 81 | +do_http_test('https://bob.sni.velox.ch./', context()); |
| 82 | + |
| 83 | +echo "-- user supplied server name --\n"; |
| 84 | + |
| 85 | +$context = context(); |
| 86 | +stream_context_set_option($context, 'ssl', 'SNI_server_name', 'bob.sni.velox.ch'); |
| 87 | +stream_context_set_option($context, 'http', 'header', b'Host: bob.sni.velox.ch'); |
| 88 | +do_http_test('https://alice.sni.velox.ch/', $context); |
| 89 | + |
| 90 | +echo "-- sni disabled --\n"; |
| 91 | + |
| 92 | +$context = context(); |
| 93 | +stream_context_set_option($context, 'ssl', 'SNI_enabled', false); |
| 94 | +do_http_test('https://bob.sni.velox.ch/', $context); |
| 95 | + |
| 96 | +/* Test ssl:// socket streams */ |
| 97 | + |
| 98 | +echo "-- raw SSL stream (1) --\n"; |
| 99 | +do_ssl_test('ssl://bob.sni.velox.ch:443', context()); |
| 100 | + |
| 101 | +echo "-- raw SSL stream (2) --\n"; |
| 102 | +do_ssl_test('ssl://mallory.sni.velox.ch:443', context()); |
| 103 | + |
| 104 | +echo "-- raw SSL stream with user supplied sni --\n"; |
| 105 | + |
| 106 | +$context = context(); |
| 107 | +stream_context_set_option($context, 'ssl', 'SNI_server_name', 'bob.sni.velox.ch'); |
| 108 | + |
| 109 | +do_ssl_test('ssl://mallory.sni.velox.ch:443', $context); |
| 110 | + |
| 111 | +echo "-- raw SSL stream with sni disabled --\n"; |
| 112 | + |
| 113 | +$context = context(); |
| 114 | +stream_context_set_option($context, 'ssl', 'SNI_enabled', false); |
| 115 | + |
| 116 | +do_ssl_test('ssl://mallory.sni.velox.ch:443', $context); |
| 117 | + |
| 118 | +/* Test tcp:// socket streams with SSL enabled */ |
| 119 | + |
| 120 | +echo "-- stream_socket_enable_crypto (1) --\n"; |
| 121 | + |
| 122 | +do_enable_crypto_test('tcp://bob.sni.velox.ch:443', context()); |
| 123 | + |
| 124 | +echo "-- stream_socket_enable_crypto (2) --\n"; |
| 125 | + |
| 126 | +do_enable_crypto_test('tcp://mallory.sni.velox.ch:443', context()); |
| 127 | + |
| 128 | +echo "-- stream_socket_enable_crypto with user supplied sni --\n"; |
| 129 | + |
| 130 | +$context = context(); |
| 131 | +stream_context_set_option($context, 'ssl', 'SNI_server_name', 'bob.sni.velox.ch'); |
| 132 | + |
| 133 | +do_enable_crypto_test('tcp://mallory.sni.velox.ch:443', $context); |
| 134 | + |
| 135 | +echo "-- stream_socket_enable_crypto with sni disabled --\n"; |
| 136 | + |
| 137 | +$context = context(); |
| 138 | +stream_context_set_option($context, 'ssl', 'SNI_enabled', false); |
| 139 | + |
| 140 | +do_enable_crypto_test('tcp://mallory.sni.velox.ch:443', $context); |
| 141 | + |
| 142 | +echo "-- stream_socket_enable_crypto with long name --\n"; |
| 143 | + |
| 144 | +$context = context(); |
| 145 | +stream_context_set_option($context, 'ssl', 'SNI_server_name', str_repeat('a.', 500) . '.sni.velox.ch'); |
| 146 | + |
| 147 | +do_enable_crypto_test('tcp://mallory.sni.velox.ch:443', $context); |
| 148 | + |
| 149 | +?> |
| 150 | +--EXPECTF-- |
| 151 | +-- auto host name (1) -- |
| 152 | +%unicode|string%(18) "alice.sni.velox.ch" |
| 153 | +-- auto host name (2) -- |
| 154 | +%unicode|string%(16) "bob.sni.velox.ch" |
| 155 | +-- auto host name (3) -- |
| 156 | +%unicode|string%(16) "bob.sni.velox.ch" |
| 157 | +-- user supplied server name -- |
| 158 | +%unicode|string%(16) "bob.sni.velox.ch" |
| 159 | +-- sni disabled -- |
| 160 | +%unicode|string%(18) "alice.sni.velox.ch" |
| 161 | +-- raw SSL stream (1) -- |
| 162 | +%unicode|string%(16) "bob.sni.velox.ch" |
| 163 | +-- raw SSL stream (2) -- |
| 164 | +%unicode|string%(14) "*.sni.velox.ch" |
| 165 | +-- raw SSL stream with user supplied sni -- |
| 166 | +%unicode|string%(16) "bob.sni.velox.ch" |
| 167 | +-- raw SSL stream with sni disabled -- |
| 168 | +%unicode|string%(18) "alice.sni.velox.ch" |
| 169 | +-- stream_socket_enable_crypto (1) -- |
| 170 | +%unicode|string%(16) "bob.sni.velox.ch" |
| 171 | +-- stream_socket_enable_crypto (2) -- |
| 172 | +%unicode|string%(14) "*.sni.velox.ch" |
| 173 | +-- stream_socket_enable_crypto with user supplied sni -- |
| 174 | +%unicode|string%(16) "bob.sni.velox.ch" |
| 175 | +-- stream_socket_enable_crypto with sni disabled -- |
| 176 | +%unicode|string%(18) "alice.sni.velox.ch" |
| 177 | +-- stream_socket_enable_crypto with long name -- |
| 178 | +%unicode|string%(18) "alice.sni.velox.ch" |
0 commit comments