]> git.saurik.com Git - apple/security.git/blob - OSX/libsecurity_ssl/regressions/ssl-39-echo.c
Security-57336.1.9.tar.gz
[apple/security.git] / OSX / libsecurity_ssl / regressions / ssl-39-echo.c
1
2 #if TARGET_OS_IPHONE
3 // Currently only supported for iOS
4
5 #include <stdbool.h>
6 #include <pthread.h>
7 #include <fcntl.h>
8 #include <sys/mman.h>
9 #include <unistd.h>
10
11 #include <CoreFoundation/CoreFoundation.h>
12
13 #include <AssertMacros.h>
14 #include <Security/SecureTransportPriv.h> /* SSLSetOption */
15 #include <Security/SecureTransport.h>
16 #include <Security/SecPolicy.h>
17 #include <Security/SecTrust.h>
18 #include <Security/SecIdentity.h>
19 #include <Security/SecIdentityPriv.h>
20 #include <Security/SecCertificatePriv.h>
21 #include <Security/SecKeyPriv.h>
22 #include <Security/SecItem.h>
23 #include <Security/SecRandom.h>
24
25 #include <string.h>
26 #include <sys/types.h>
27 #include <sys/socket.h>
28 #include <errno.h>
29 #include <stdlib.h>
30 #include <mach/mach_time.h>
31
32 #include <Security/SecRSAKey.h>
33
34 #include "testlist.h"
35
36 /*
37 SSL CipherSuite tests
38
39 Below are all the ciphers that are individually tested. The first element
40 is the SecureTransport/RFC name; the second is what openssl calls it, which
41 can be looked up in ciphers(1).
42
43 All SSL_DH_* and TLS_DH_* are disabled because neither openssl nor
44 securetransport support them:
45 SSL_DH_DSS_EXPORT_WITH_DES40_CBC_SHA, SSL_DH_DSS_WITH_DES_CBC_SHA,
46 SSL_DH_DSS_WITH_3DES_EDE_CBC_SHA, SSL_DH_RSA_EXPORT_WITH_DES40_CBC_SHA,
47 SSL_DH_RSA_WITH_DES_CBC_SHA, SSL_DH_RSA_WITH_3DES_EDE_CBC_SHA,
48 TLS_DH_DSS_WITH_AES_128_CBC_SHA, TLS_DH_RSA_WITH_AES_128_CBC_SHA,
49 TLS_DH_DSS_WITH_AES_256_CBC_SHA, TLS_DH_RSA_WITH_AES_256_CBC_SHA,
50
51 DSS is unimplemented by securetransport on the phone:
52 SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA, SSL_DHE_DSS_WITH_DES_CBC_SHA,
53 SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA, TLS_DHE_DSS_WITH_AES_128_CBC_SHA,
54 TLS_DHE_DSS_WITH_AES_256_CBC_SHA,
55
56 SSLv2 ciphersuites disabled by securetransport on phone:
57 SSL_RSA_WITH_RC2_CBC_MD5, SSL_RSA_WITH_IDEA_CBC_MD5,
58 SSL_RSA_WITH_DES_CBC_MD5, SSL_RSA_WITH_3DES_EDE_CBC_MD5,
59
60 SSLv3 ciphersuites disabled by securetransport on phone:
61 SSL_RSA_WITH_IDEA_CBC_SHA, SSL_RSA_EXPORT_WITH_RC2_CBC_40_MD5
62
63 */
64
65 typedef struct _CipherSuiteName {
66 SSLCipherSuite cipher;
67 const char *name;
68 bool dh_anonymous;
69 } CipherSuiteName;
70
71 #define CIPHER(cipher, dh_anonymous) { cipher, #cipher, dh_anonymous }
72
73 static const CipherSuiteName ciphers[] = {
74 #if 0
75 /* TODO: Generate an ecdsa private key and certificate for the tests. */
76 CIPHER(TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384, false),
77 CIPHER(TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, false),
78 CIPHER(TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384, false),
79 CIPHER(TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, false),
80 CIPHER(TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA, false),
81 CIPHER(TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, false),
82 CIPHER(TLS_ECDHE_ECDSA_WITH_RC4_128_SHA, false),
83 CIPHER(TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA, false),
84 CIPHER(TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384, false),
85 CIPHER(TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, false),
86 CIPHER(TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384, false),
87 CIPHER(TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, false),
88 CIPHER(TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, false),
89 CIPHER(TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, false),
90 CIPHER(TLS_ECDHE_RSA_WITH_RC4_128_SHA, false),
91 CIPHER(TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA, false),
92 CIPHER(TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384, false),
93 CIPHER(TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256, false),
94 CIPHER(TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384, false),
95 CIPHER(TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256, false),
96 CIPHER(TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384, false),
97 CIPHER(TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256, false),
98 CIPHER(TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384, false),
99 CIPHER(TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256, false),
100 CIPHER(TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA, false),
101 CIPHER(TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA, false),
102 CIPHER(TLS_ECDH_ECDSA_WITH_RC4_128_SHA, false),
103 CIPHER(TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA, false),
104 CIPHER(TLS_ECDH_RSA_WITH_AES_128_CBC_SHA, false),
105 CIPHER(TLS_ECDH_RSA_WITH_AES_256_CBC_SHA, false),
106 CIPHER(TLS_ECDH_RSA_WITH_RC4_128_SHA, false),
107 CIPHER(TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA, false),
108 #endif
109 CIPHER(TLS_RSA_WITH_AES_256_GCM_SHA384, false),
110 CIPHER(TLS_RSA_WITH_AES_128_GCM_SHA256, false),
111 CIPHER(TLS_RSA_WITH_AES_256_CBC_SHA256, false),
112 CIPHER(TLS_RSA_WITH_AES_128_CBC_SHA256, false),
113 CIPHER(TLS_RSA_WITH_AES_128_CBC_SHA, false),
114 CIPHER(SSL_RSA_WITH_RC4_128_SHA, false),
115 CIPHER(SSL_RSA_WITH_RC4_128_MD5, false),
116 CIPHER(TLS_RSA_WITH_AES_256_CBC_SHA, false),
117 CIPHER(SSL_RSA_WITH_3DES_EDE_CBC_SHA, false),
118 CIPHER(SSL_RSA_WITH_3DES_EDE_CBC_MD5, false),
119 CIPHER(SSL_RSA_WITH_DES_CBC_SHA, false),
120 CIPHER(SSL_RSA_WITH_DES_CBC_MD5, false),
121 CIPHER(SSL_RSA_EXPORT_WITH_RC4_40_MD5, false),
122 CIPHER(SSL_RSA_EXPORT_WITH_DES40_CBC_SHA, false),
123 CIPHER(SSL_RSA_EXPORT_WITH_RC2_CBC_40_MD5, false),
124 CIPHER(SSL_RSA_WITH_RC2_CBC_MD5, false),
125 CIPHER(TLS_DHE_DSS_WITH_AES_256_GCM_SHA384, false),
126 CIPHER(TLS_DHE_RSA_WITH_AES_256_GCM_SHA384, false),
127 CIPHER(TLS_DHE_DSS_WITH_AES_128_GCM_SHA256, false),
128 CIPHER(TLS_DHE_RSA_WITH_AES_128_GCM_SHA256, false),
129 CIPHER(TLS_DHE_DSS_WITH_AES_128_CBC_SHA256, false),
130 CIPHER(TLS_DHE_RSA_WITH_AES_128_CBC_SHA256, false),
131 CIPHER(TLS_DHE_DSS_WITH_AES_256_CBC_SHA256, false),
132 CIPHER(TLS_DHE_RSA_WITH_AES_256_CBC_SHA256, false),
133 CIPHER(TLS_DHE_DSS_WITH_AES_128_CBC_SHA, false),
134 CIPHER(TLS_DHE_RSA_WITH_AES_128_CBC_SHA, false),
135 CIPHER(TLS_DHE_DSS_WITH_AES_256_CBC_SHA, false),
136 CIPHER(TLS_DHE_RSA_WITH_AES_256_CBC_SHA, false),
137 CIPHER(SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA, false),
138 CIPHER(SSL_DHE_RSA_WITH_DES_CBC_SHA, false),
139 CIPHER(SSL_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA, false),
140 CIPHER(SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA, false),
141 CIPHER(SSL_DHE_DSS_WITH_DES_CBC_SHA, false),
142 CIPHER(SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA, false),
143 CIPHER(TLS_DH_anon_WITH_AES_256_GCM_SHA384, true),
144 CIPHER(TLS_DH_anon_WITH_AES_128_GCM_SHA256, true),
145 CIPHER(TLS_DH_anon_WITH_AES_128_CBC_SHA256, true),
146 CIPHER(TLS_DH_anon_WITH_AES_256_CBC_SHA256, true),
147 CIPHER(TLS_DH_anon_WITH_AES_128_CBC_SHA, true),
148 CIPHER(TLS_DH_anon_WITH_AES_256_CBC_SHA, true),
149 CIPHER(SSL_DH_anon_WITH_RC4_128_MD5, true),
150 CIPHER(SSL_DH_anon_WITH_3DES_EDE_CBC_SHA, true),
151 CIPHER(SSL_DH_anon_WITH_DES_CBC_SHA, true),
152 CIPHER(SSL_DH_anon_EXPORT_WITH_RC4_40_MD5, true),
153 CIPHER(SSL_DH_anon_EXPORT_WITH_DES40_CBC_SHA, true),
154 #if 0
155 CIPHER(TLS_ECDHE_ECDSA_WITH_NULL_SHA, false),
156 CIPHER(TLS_ECDHE_RSA_WITH_NULL_SHA, false),
157 CIPHER(TLS_ECDH_ECDSA_WITH_NULL_SHA, false),
158 CIPHER(TLS_ECDH_RSA_WITH_NULL_SHA, false),
159 #endif
160 CIPHER(TLS_RSA_WITH_NULL_SHA256, false),
161 CIPHER(SSL_RSA_WITH_NULL_SHA, false),
162 CIPHER(SSL_RSA_WITH_NULL_MD5, false),
163 #if 0
164 /* We don't support these yet. */
165 CIPHER(TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA, false),
166 CIPHER(TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA, false),
167 CIPHER(TLS_RSA_WITH_RC4_128_SHA, false),
168 CIPHER(TLS_RSA_WITH_3DES_EDE_CBC_SHA, false),
169 CIPHER(TLS_RSA_WITH_RC4_128_MD5, false),
170 CIPHER(TLS_DH_DSS_WITH_AES_256_GCM_SHA384, false),
171 CIPHER(TLS_DH_DSS_WITH_AES_128_GCM_SHA256, false),
172 CIPHER(TLS_DH_RSA_WITH_AES_256_GCM_SHA384, false),
173 CIPHER(TLS_DH_RSA_WITH_AES_128_GCM_SHA256, false),
174 CIPHER(TLS_DH_DSS_WITH_AES_256_CBC_SHA256, false),
175 CIPHER(TLS_DH_RSA_WITH_AES_256_CBC_SHA256, false),
176 CIPHER(TLS_DH_DSS_WITH_AES_128_CBC_SHA256, false),
177 CIPHER(TLS_DH_RSA_WITH_AES_128_CBC_SHA256, false),
178 CIPHER(TLS_DH_DSS_WITH_AES_256_CBC_SHA, false),
179 CIPHER(TLS_DH_RSA_WITH_AES_256_CBC_SHA, false),
180 CIPHER(TLS_DH_DSS_WITH_AES_128_CBC_SHA, false),
181 CIPHER(TLS_DH_RSA_WITH_AES_128_CBC_SHA, false),
182 CIPHER(TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA, false),
183 CIPHER(TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA, false),
184 CIPHER(TLS_ECDH_anon_WITH_AES_256_CBC_SHA, false),
185 CIPHER(TLS_ECDH_anon_WITH_AES_128_CBC_SHA, false),
186 CIPHER(TLS_ECDH_anon_WITH_RC4_128_SHA, false),
187 CIPHER(TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA, false),
188 CIPHER(TLS_ECDH_anon_WITH_NULL_SHA, false),
189 #endif
190
191 { -1, NULL }
192 };
193
194 static int ciphers_len = array_size(ciphers);
195
196 #if 0 // currently unused
197 static SSLCipherSuite sslcipher_atoi(const char *name)
198 {
199 const CipherSuiteName *a = ciphers;
200 while(a->name) {
201 if (0 == strcmp(a->name, name)) break;
202 a++;
203 }
204 return a->cipher;
205 }
206
207 static const char * sslcipher_itoa(SSLCipherSuite num)
208 {
209 const CipherSuiteName *a = ciphers;
210 while(a->cipher >= 0) {
211 if (num == a->cipher) break;
212 a++;
213 }
214 return a->name;
215 }
216 #endif // currently unused
217
218 static unsigned char dh_param_512_bytes[] = {
219 0x30, 0x46, 0x02, 0x41, 0x00, 0xdb, 0x3c, 0xfa, 0x13, 0xa6, 0xd2, 0x64,
220 0xdf, 0xcc, 0x40, 0xb1, 0x21, 0xd4, 0xf2, 0xad, 0x22, 0x7f, 0xce, 0xa0,
221 0xb9, 0x5b, 0x95, 0x1c, 0x2e, 0x99, 0xb0, 0x27, 0xd0, 0xed, 0xf4, 0xbd,
222 0xbb, 0x36, 0x93, 0xd0, 0x9d, 0x2b, 0x32, 0xa3, 0x56, 0x53, 0xe3, 0x7b,
223 0xed, 0xa1, 0x71, 0x82, 0x2e, 0x83, 0x14, 0xf9, 0xc0, 0x2f, 0x15, 0xcb,
224 0xcf, 0x97, 0xab, 0x88, 0x49, 0x20, 0x28, 0x2e, 0x63, 0x02, 0x01, 0x02
225 };
226 static unsigned char *dh_param_512_der = dh_param_512_bytes;
227 static unsigned int dh_param_512_der_len = 72;
228
229 /* openssl req -newkey rsa:512 -sha1 -days 365 -subj "/C=US/O=Apple Inc./OU=Apple Certification Authority/CN=localhost" -x509 -nodes -outform DER -keyout privkey.der -outform der -out cert.der */
230 static unsigned char pkey_der[] = {
231 0x30, 0x82, 0x01, 0x3b, 0x02, 0x01, 0x00, 0x02, 0x41, 0x00, 0xc0, 0x80,
232 0x43, 0xf1, 0x4d, 0xdc, 0x9a, 0x24, 0xe7, 0x25, 0x7c, 0x8b, 0x8b, 0x65,
233 0x87, 0x97, 0xed, 0x3f, 0xfa, 0xfe, 0xbe, 0xcb, 0x12, 0x43, 0x1f, 0x0c,
234 0xb5, 0xbf, 0x6b, 0x81, 0xee, 0x1b, 0x46, 0x6a, 0x02, 0x86, 0x92, 0xec,
235 0x8a, 0xb3, 0x65, 0x77, 0x15, 0xd0, 0x49, 0xb4, 0x22, 0x84, 0xf4, 0x85,
236 0x56, 0x53, 0xf5, 0x5a, 0x3b, 0xad, 0x23, 0xa8, 0x0c, 0x24, 0xb7, 0xf5,
237 0xf4, 0xa1, 0x02, 0x03, 0x01, 0x00, 0x01, 0x02, 0x41, 0x00, 0xb8, 0x7f,
238 0xf7, 0x1e, 0xa7, 0x0e, 0xc1, 0x9a, 0x8f, 0x04, 0x49, 0xcb, 0x81, 0x4e,
239 0x4d, 0x58, 0x5a, 0xe7, 0x10, 0x8c, 0xea, 0x96, 0xbd, 0xa9, 0x21, 0x70,
240 0x50, 0x1d, 0xe8, 0x4f, 0x7e, 0xc2, 0x71, 0xff, 0x55, 0xc5, 0xa7, 0x28,
241 0xc8, 0xf2, 0xc7, 0x19, 0xd1, 0x2c, 0x10, 0x40, 0x39, 0xa8, 0xe1, 0x5b,
242 0xbd, 0x97, 0x04, 0xff, 0xd3, 0x27, 0x9b, 0xce, 0x5e, 0x8d, 0x2f, 0x0e,
243 0xd9, 0xf1, 0x02, 0x21, 0x00, 0xde, 0xfc, 0x18, 0x88, 0xa4, 0xef, 0x3b,
244 0x18, 0xca, 0x54, 0x3f, 0xa8, 0x14, 0x96, 0x9a, 0xd7, 0x67, 0x57, 0x55,
245 0xdc, 0x6b, 0xd4, 0x8e, 0x7d, 0xb4, 0x32, 0x00, 0x63, 0x67, 0x6a, 0x57,
246 0x65, 0x02, 0x21, 0x00, 0xdd, 0x00, 0xba, 0xdc, 0xa1, 0xe2, 0x5c, 0xda,
247 0xfe, 0xfc, 0x50, 0x1e, 0x9b, 0x95, 0x28, 0x34, 0xf2, 0x52, 0x31, 0x7a,
248 0x15, 0x00, 0x6f, 0xcc, 0x08, 0x2c, 0x6d, 0x55, 0xb0, 0x24, 0x6a, 0x8d,
249 0x02, 0x20, 0x14, 0xf5, 0x7d, 0x18, 0xda, 0xe7, 0xe1, 0x96, 0x22, 0xee,
250 0x68, 0x4d, 0x54, 0x22, 0x13, 0xcb, 0xcb, 0x5a, 0xda, 0x27, 0x2d, 0xbb,
251 0x7c, 0xe9, 0x33, 0xd6, 0xbf, 0x52, 0x98, 0x95, 0xd6, 0x41, 0x02, 0x21,
252 0x00, 0xaa, 0x58, 0x8c, 0xaf, 0xd1, 0x6b, 0xdc, 0x6c, 0xc4, 0xcc, 0x10,
253 0xa9, 0x76, 0xfc, 0xc2, 0x50, 0x05, 0x53, 0xcb, 0x65, 0x31, 0x58, 0xf3,
254 0xd3, 0x4d, 0x9d, 0x88, 0xec, 0xda, 0x67, 0x47, 0x65, 0x02, 0x20, 0x53,
255 0xf2, 0x49, 0x77, 0x7e, 0x10, 0xc1, 0xc4, 0xed, 0xc0, 0xaf, 0x99, 0x79,
256 0xab, 0x7b, 0x25, 0x0e, 0x70, 0x36, 0xd2, 0xd1, 0xa3, 0x81, 0x0d, 0x83,
257 0x4f, 0x6b, 0x1b, 0x48, 0xec, 0x87, 0x90
258 };
259 static unsigned int pkey_der_len = 319;
260
261 static unsigned char cert_der[] = {
262 0x30, 0x82, 0x02, 0x79, 0x30, 0x82, 0x02, 0x23, 0xa0, 0x03, 0x02, 0x01,
263 0x02, 0x02, 0x09, 0x00, 0xc2, 0xa8, 0x3b, 0xaa, 0x40, 0xa4, 0x29, 0x2b,
264 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
265 0x05, 0x05, 0x00, 0x30, 0x5e, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55,
266 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03,
267 0x55, 0x04, 0x0a, 0x13, 0x0a, 0x41, 0x70, 0x70, 0x6c, 0x65, 0x20, 0x49,
268 0x6e, 0x63, 0x2e, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x0b,
269 0x13, 0x1d, 0x41, 0x70, 0x70, 0x6c, 0x65, 0x20, 0x43, 0x65, 0x72, 0x74,
270 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x41, 0x75,
271 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x31, 0x12, 0x30, 0x10, 0x06,
272 0x03, 0x55, 0x04, 0x03, 0x13, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68,
273 0x6f, 0x73, 0x74, 0x30, 0x1e, 0x17, 0x0d, 0x30, 0x38, 0x30, 0x39, 0x31,
274 0x35, 0x32, 0x31, 0x35, 0x30, 0x35, 0x36, 0x5a, 0x17, 0x0d, 0x30, 0x39,
275 0x30, 0x39, 0x31, 0x35, 0x32, 0x31, 0x35, 0x30, 0x35, 0x36, 0x5a, 0x30,
276 0x5e, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02,
277 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x13,
278 0x0a, 0x41, 0x70, 0x70, 0x6c, 0x65, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31,
279 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x13, 0x1d, 0x41, 0x70,
280 0x70, 0x6c, 0x65, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63,
281 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72,
282 0x69, 0x74, 0x79, 0x31, 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04, 0x03,
283 0x13, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73, 0x74, 0x30,
284 0x5c, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01,
285 0x01, 0x01, 0x05, 0x00, 0x03, 0x4b, 0x00, 0x30, 0x48, 0x02, 0x41, 0x00,
286 0xc0, 0x80, 0x43, 0xf1, 0x4d, 0xdc, 0x9a, 0x24, 0xe7, 0x25, 0x7c, 0x8b,
287 0x8b, 0x65, 0x87, 0x97, 0xed, 0x3f, 0xfa, 0xfe, 0xbe, 0xcb, 0x12, 0x43,
288 0x1f, 0x0c, 0xb5, 0xbf, 0x6b, 0x81, 0xee, 0x1b, 0x46, 0x6a, 0x02, 0x86,
289 0x92, 0xec, 0x8a, 0xb3, 0x65, 0x77, 0x15, 0xd0, 0x49, 0xb4, 0x22, 0x84,
290 0xf4, 0x85, 0x56, 0x53, 0xf5, 0x5a, 0x3b, 0xad, 0x23, 0xa8, 0x0c, 0x24,
291 0xb7, 0xf5, 0xf4, 0xa1, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x81, 0xc3,
292 0x30, 0x81, 0xc0, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16,
293 0x04, 0x14, 0xe3, 0x58, 0xab, 0x35, 0xc0, 0x58, 0xb8, 0x65, 0x40, 0xca,
294 0x9b, 0x6c, 0xeb, 0x2f, 0xf5, 0xbf, 0xbd, 0x0b, 0xf3, 0xa6, 0x30, 0x81,
295 0x90, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x81, 0x88, 0x30, 0x81, 0x85,
296 0x80, 0x14, 0xe3, 0x58, 0xab, 0x35, 0xc0, 0x58, 0xb8, 0x65, 0x40, 0xca,
297 0x9b, 0x6c, 0xeb, 0x2f, 0xf5, 0xbf, 0xbd, 0x0b, 0xf3, 0xa6, 0xa1, 0x62,
298 0xa4, 0x60, 0x30, 0x5e, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04,
299 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55,
300 0x04, 0x0a, 0x13, 0x0a, 0x41, 0x70, 0x70, 0x6c, 0x65, 0x20, 0x49, 0x6e,
301 0x63, 0x2e, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x13,
302 0x1d, 0x41, 0x70, 0x70, 0x6c, 0x65, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69,
303 0x66, 0x69, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x41, 0x75, 0x74,
304 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x31, 0x12, 0x30, 0x10, 0x06, 0x03,
305 0x55, 0x04, 0x03, 0x13, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f,
306 0x73, 0x74, 0x82, 0x09, 0x00, 0xc2, 0xa8, 0x3b, 0xaa, 0x40, 0xa4, 0x29,
307 0x2b, 0x30, 0x0c, 0x06, 0x03, 0x55, 0x1d, 0x13, 0x04, 0x05, 0x30, 0x03,
308 0x01, 0x01, 0xff, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7,
309 0x0d, 0x01, 0x01, 0x05, 0x05, 0x00, 0x03, 0x41, 0x00, 0x41, 0x40, 0x07,
310 0xde, 0x1f, 0xd0, 0x00, 0x62, 0x75, 0x36, 0xb3, 0x94, 0xa8, 0xac, 0x3b,
311 0x98, 0xbb, 0x28, 0x56, 0xf6, 0x9f, 0xe3, 0x87, 0xd4, 0xa1, 0x7a, 0x85,
312 0xce, 0x40, 0x8a, 0xfd, 0x12, 0xb4, 0x99, 0x8c, 0x1d, 0x05, 0x61, 0xdb,
313 0x35, 0xb8, 0x04, 0x7c, 0xfb, 0xe4, 0x97, 0x88, 0x66, 0xa0, 0x54, 0x7b,
314 0x1c, 0xce, 0x99, 0xd8, 0xd3, 0x99, 0x80, 0x40, 0x9b, 0xa2, 0x73, 0x8b,
315 0xfd
316 };
317 static unsigned int cert_der_len = 637;
318
319 typedef struct {
320 uint32_t session_id;
321 bool is_session_resume;
322 SSLContextRef handle;
323 bool is_st;
324 bool is_server;
325 bool client_side_auth;
326 bool dh_anonymous;
327 int comm;
328 CFArrayRef certs;
329 } ssl_test_handle;
330
331 #if 0 // currently unused
332 static CFArrayRef SecIdentityCopySSLClientAuthenticationChain(SecIdentityRef identity)
333 {
334 CFMutableArrayRef chain = NULL;
335 SecPolicyRef policy = NULL;
336 SecTrustRef trust = NULL;
337 SecTrustResultType trust_result;
338
339 do {
340 policy = SecPolicyCreateSSL(false, NULL);
341 if (!policy)
342 break;
343
344 SecCertificateRef cert = NULL;
345 if (SecIdentityCopyCertificate(identity, &cert))
346 break;
347
348 CFArrayRef certs = CFArrayCreate(NULL, (const void **)&cert,
349 1, &kCFTypeArrayCallBacks);
350 CFRelease(cert);
351 if (!certs)
352 break;
353
354 if (SecTrustCreateWithCertificates(certs, policy, &trust))
355 break;
356 CFRelease(certs);
357 CFRelease(policy);
358 if (SecTrustEvaluate(trust, &trust_result))
359 break;
360
361 int i, count = SecTrustGetCertificateCount(trust);
362 chain = CFArrayCreateMutable(NULL, count, &kCFTypeArrayCallBacks);
363 CFArrayAppendValue(chain, identity);
364 for (i = 1; i < count; i++) {
365 if ((i+1 == count) && (trust_result == kSecTrustResultUnspecified))
366 continue; /* skip anchor if chain is complete */
367 SecCertificateRef s = SecTrustGetCertificateAtIndex(trust, i);
368 CFArrayAppendValue(chain, s);
369 }
370 } while (0);
371 if (trust)
372 CFRelease(trust);
373 if (policy)
374 CFRelease(policy);
375 return chain;
376 }
377 #endif // currently unused
378
379 static CFArrayRef server_chain()
380 {
381 SecKeyRef pkey = SecKeyCreateRSAPrivateKey(kCFAllocatorDefault,
382 pkey_der, pkey_der_len, kSecKeyEncodingPkcs1);
383 SecCertificateRef cert = SecCertificateCreateWithBytes(kCFAllocatorDefault,
384 cert_der, cert_der_len);
385 SecIdentityRef ident = SecIdentityCreate(kCFAllocatorDefault, cert, pkey);
386 CFRelease(pkey);
387 CFRelease(cert);
388 CFArrayRef items = CFArrayCreate(kCFAllocatorDefault,
389 (const void **)&ident, 1, &kCFTypeArrayCallBacks);
390 CFRelease(ident);
391 return items;
392 }
393
394 // MARK: -
395 // MARK: SecureTransport support
396
397 #if 0
398 static void hexdump(const uint8_t *bytes, size_t len) {
399 size_t ix;
400 printf("socket write(%p, %lu)\n", bytes, len);
401 for (ix = 0; ix < len; ++ix) {
402 if (!(ix % 16))
403 printf("\n");
404 printf("%02X ", bytes[ix]);
405 }
406 printf("\n");
407 }
408 #else
409 #define hexdump(bytes, len)
410 #endif
411
412 static OSStatus SocketWrite(SSLConnectionRef conn, const void *data, size_t *length)
413 {
414 size_t len = *length;
415 uint8_t *ptr = (uint8_t *)data;
416
417 do {
418 ssize_t ret;
419 do {
420 hexdump(ptr, len);
421 ret = write((int)conn, ptr, len);
422 if (ret < 0)
423 perror("send");
424 } while ((ret < 0) && (errno == EAGAIN || errno == EINTR));
425 if (ret > 0) {
426 len -= ret;
427 ptr += ret;
428 }
429 else
430 return -36;
431 } while (len > 0);
432
433 *length = *length - len;
434 return errSecSuccess;
435 }
436
437 static OSStatus SocketRead(SSLConnectionRef conn, void *data, size_t *length)
438 {
439 size_t len = *length;
440 uint8_t *ptr = (uint8_t *)data;
441
442 do {
443 ssize_t ret;
444 do {
445 ret = read((int)conn, ptr, len);
446 if (ret < 0)
447 perror("send");
448 } while ((ret < 0) && (errno == EAGAIN || errno == EINTR));
449 if (ret > 0) {
450 len -= ret;
451 ptr += ret;
452 }
453 else
454 return -36;
455 } while (len > 0);
456
457 *length = *length - len;
458 return errSecSuccess;
459 }
460
461 static unsigned char dn[] = {
462 0x30, 0x5e, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13,
463 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0a,
464 0x13, 0x0a, 0x41, 0x70, 0x70, 0x6c, 0x65, 0x20, 0x49, 0x6e, 0x63, 0x2e,
465 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x13, 0x1d, 0x41,
466 0x70, 0x70, 0x6c, 0x65, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69,
467 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f,
468 0x72, 0x69, 0x74, 0x79, 0x31, 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04,
469 0x03, 0x13, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73, 0x74
470 };
471 static unsigned int dn_len = 96;
472
473 static SSLContextRef make_ssl_ref(bool server, bool client_side_auth, bool dh_anonymous,
474 bool dtls, int sock, CFArrayRef certs)
475 {
476 SSLContextRef ctx = NULL;
477 if(dtls)
478 require_noerr(SSLNewDatagramContext(server, &ctx), out);
479 else
480 require_noerr(SSLNewContext(server, &ctx), out);
481 require_noerr(SSLSetIOFuncs(ctx,
482 (SSLReadFunc)SocketRead, (SSLWriteFunc)SocketWrite), out);
483 require_noerr(SSLSetConnection(ctx, (SSLConnectionRef)sock), out);
484 static const char *peer_domain_name = "localhost";
485 require_noerr(SSLSetPeerDomainName(ctx, peer_domain_name,
486 strlen(peer_domain_name)), out);
487
488 if (!dh_anonymous) {
489 if (server)
490 require_noerr(SSLSetCertificate(ctx, certs), out);
491 if (client_side_auth && server) {
492 require_noerr(SSLSetClientSideAuthenticate(ctx, kAlwaysAuthenticate), out);
493 require_noerr(SSLAddDistinguishedName(ctx, dn, dn_len), out);
494 }
495 #if 0 /* Setting client certificate in advance */
496 if (client_side_auth && !server)
497 require_noerr(SSLSetCertificate(ctx, certs), out);
498 #endif
499 if (client_side_auth && !server) /* enable break from SSLHandshake */
500 require_noerr(SSLSetSessionOption(ctx,
501 kSSLSessionOptionBreakOnCertRequested, true), out);
502 require_noerr(SSLSetSessionOption(ctx,
503 kSSLSessionOptionBreakOnServerAuth, true), out);
504 }
505
506 /* Tell SecureTransport to not check certs itself: it will break out of the
507 handshake to let us take care of it instead. */
508 require_noerr(SSLSetEnableCertVerify(ctx, false), out);
509
510 if (server) {
511 require_noerr(SSLSetDiffieHellmanParams(ctx,
512 dh_param_512_der, dh_param_512_der_len), out);
513 }
514 else /* if client */ {
515 }
516
517 return ctx;
518 out:
519 if (ctx)
520 SSLDisposeContext(ctx);
521 return NULL;
522 }
523
524 static void *securetransport_ssl_thread(void *arg)
525 {
526 OSStatus ortn;
527 ssl_test_handle * ssl = (ssl_test_handle *)arg;
528 SSLContextRef ctx = ssl->handle;
529 SecTrustRef trust = NULL;
530 bool got_server_auth = false, got_client_cert_req = false;
531
532 //uint64_t start = mach_absolute_time();
533 do {
534 ortn = SSLHandshake(ctx);
535
536 if (ortn == errSSLServerAuthCompleted)
537 {
538 require_string(!got_server_auth, out, "second server auth");
539 require_string(!got_client_cert_req, out, "got client cert req before server auth");
540 got_server_auth = true;
541 require_string(!trust, out, "Got errSSLServerAuthCompleted twice?");
542 /* verify peer cert chain */
543 require_noerr(SSLCopyPeerTrust(ctx, &trust), out);
544 SecTrustResultType trust_result = 0;
545 /* this won't verify without setting up a trusted anchor */
546 require_noerr(SecTrustEvaluate(trust, &trust_result), out);
547
548 CFIndex n_certs = SecTrustGetCertificateCount(trust);
549 /*fprintf(stderr, "%ld certs; trust_eval: %d\n", n_certs, trust_result); */
550
551 CFMutableArrayRef peer_cert_array =
552 CFArrayCreateMutable(NULL, n_certs, &kCFTypeArrayCallBacks);
553 CFMutableArrayRef orig_peer_cert_array =
554 CFArrayCreateMutableCopy(NULL, n_certs, ssl->certs);
555 while (n_certs--)
556 CFArrayInsertValueAtIndex(peer_cert_array, 0,
557 SecTrustGetCertificateAtIndex(trust, n_certs));
558
559 SecIdentityRef ident =
560 (SecIdentityRef)CFArrayGetValueAtIndex(orig_peer_cert_array, 0);
561 SecCertificateRef peer_cert = NULL;
562 require_noerr(SecIdentityCopyCertificate(ident, &peer_cert), out);
563 CFArraySetValueAtIndex(orig_peer_cert_array, 0, peer_cert);
564 CFRelease(peer_cert);
565
566 require(CFEqual(orig_peer_cert_array, peer_cert_array), out);
567 CFRelease(orig_peer_cert_array);
568 CFRelease(peer_cert_array);
569
570 /*
571 CFStringRef cert_name = SecCertificateCopySubjectSummary(cert);
572 char cert_name_buffer[1024];
573 require(CFStringGetFileSystemRepresentation(cert_name,
574 cert_name_buffer, sizeof(cert_name_buffer)), out);
575 fprintf(stderr, "cert name: %s\n", cert_name_buffer);
576 CFRelease(trust);
577 */
578 } else if (ortn == errSSLClientCertRequested) {
579 require_string(!got_client_cert_req, out, "second client cert req");
580 require_string(got_server_auth, out, "didn't get server auth first");
581 got_client_cert_req = true;
582
583 /* set client cert */
584 require_string(!ssl->is_server, out, "errSSLClientCertRequested while running server");
585 require_string(!ssl->dh_anonymous, out, "errSSLClientCertRequested while running anon DH");
586
587 CFArrayRef DNs = NULL;
588 require_noerr(SSLCopyDistinguishedNames (ctx, &DNs), out);
589 require(DNs, out);
590 CFRelease(DNs);
591
592 require_string(ssl->client_side_auth, out, "errSSLClientCertRequested in run not testing that");
593 require_noerr(SSLSetCertificate(ctx, ssl->certs), out);
594 }
595 } while (ortn == errSSLWouldBlock
596 || ortn == errSSLServerAuthCompleted
597 || ortn == errSSLClientCertRequested);
598 require_noerr_action_quiet(ortn, out,
599 fprintf(stderr, "Fell out of SSLHandshake with error: %d\n", (int)ortn));
600
601 if (!ssl->is_server && !ssl->dh_anonymous && !ssl->is_session_resume) {
602 require_string(got_server_auth, out, "never got server auth");
603 if (ssl->client_side_auth)
604 require_string(got_client_cert_req, out, "never got client cert req");
605 }
606 //uint64_t elapsed = mach_absolute_time() - start;
607 //fprintf(stderr, "setr elapsed: %lld\n", elapsed);
608
609 /*
610 SSLProtocol proto = kSSLProtocolUnknown;
611 require_noerr_quiet(SSLGetNegotiatedProtocolVersion(ctx, &proto), out); */
612
613 SSLCipherSuite cipherSuite;
614 require_noerr_quiet(ortn = SSLGetNegotiatedCipher(ctx, &cipherSuite), out);
615 //fprintf(stderr, "st negotiated %s\n", sslcipher_itoa(cipherSuite));
616
617 Boolean sessionWasResumed = false;
618 uint8_t session_id_data[MAX_SESSION_ID_LENGTH];
619 size_t session_id_length = sizeof(session_id_data);
620 require_noerr_quiet(ortn = SSLGetResumableSessionInfo(ctx, &sessionWasResumed, session_id_data, &session_id_length), out);
621 require_action(ssl->dh_anonymous || (ssl->is_session_resume == sessionWasResumed), out, ortn = -1);
622 // if (sessionWasResumed) fprintf(stderr, "st resumed session\n");
623 //hexdump(session_id_data, session_id_length);
624
625 unsigned char ibuf[4096], obuf[4096];
626 size_t len;
627 if (ssl->is_server) {
628 SecRandomCopyBytes(kSecRandomDefault, sizeof(obuf), obuf);
629 require_noerr_quiet(ortn = SSLWrite(ctx, obuf, sizeof(obuf), &len), out);
630 require_action_quiet(len == sizeof(obuf), out, ortn = -1);
631 }
632 require_noerr_quiet(ortn = SSLRead(ctx, ibuf, sizeof(ibuf), &len), out);
633 require_action_quiet(len == sizeof(ibuf), out, ortn = -1);
634
635 if (ssl->is_server) {
636 require_noerr(memcmp(ibuf, obuf, sizeof(ibuf)), out);
637 } else {
638 require_noerr_quiet(ortn = SSLWrite(ctx, ibuf, sizeof(ibuf), &len), out);
639 require_action_quiet(len == sizeof(ibuf), out, ortn = -1);
640 }
641
642 out:
643 SSLClose(ctx);
644 SSLDisposeContext(ctx);
645 if (trust) CFRelease(trust);
646
647 pthread_exit((void *)(intptr_t)ortn);
648 return NULL;
649 }
650
651
652
653 static ssl_test_handle *
654 ssl_test_handle_create(uint32_t session_id, bool resume, bool server, bool client_side_auth, bool dh_anonymous, bool dtls,
655 int comm, CFArrayRef certs)
656 {
657 ssl_test_handle *handle = calloc(1, sizeof(ssl_test_handle));
658 if (handle) {
659 handle->session_id = session_id;
660 handle->is_session_resume = resume;
661 handle->is_server = server;
662 handle->client_side_auth = client_side_auth;
663 handle->dh_anonymous = dh_anonymous;
664 handle->comm = comm;
665 handle->certs = certs;
666 handle->handle = make_ssl_ref(server, client_side_auth, dh_anonymous, dtls, comm, certs);
667 }
668 return handle;
669 }
670
671 static void
672 tests(void)
673 {
674 pthread_t client_thread, server_thread;
675 CFArrayRef server_certs = server_chain();
676 ok(server_certs, "got server certs");
677
678 #if 0
679 int i=0, j=1, k=1; {
680 #else
681 int d,i,k,l;
682 for (d=0;d<2; d++) /* dtls or not dtls */
683 for (k=0; k<2; k++)
684 for (i=0; ciphers[i].cipher != (SSLCipherSuite)(-1); i++)
685 for (l = 0; l<2; l++) {
686 #endif
687 SKIP: {
688 skip("ST doesn't support resumption", 1, l != 1);
689
690 int sp[2];
691 if (socketpair(AF_UNIX, SOCK_STREAM, 0, sp)) exit(errno);
692
693 ssl_test_handle *server, *client;
694
695 bool client_side_auth = (k);
696
697 uint32_t session_id = (k+1) << 16 | 1 << 8 | (i+1);
698 //fprintf(stderr, "session_id: %d\n", session_id);
699 server = ssl_test_handle_create(session_id, (l == 1), true /*server*/,
700 client_side_auth, ciphers[i].dh_anonymous, d,
701 sp[0], server_certs);
702 client = ssl_test_handle_create(session_id, (l == 1), false/*client*/,
703 client_side_auth, ciphers[i].dh_anonymous, d,
704 sp[1], server_certs);
705
706 require_noerr(SSLSetPeerID(server->handle, &session_id, sizeof(session_id)), out);
707 require_noerr(SSLSetPeerID(client->handle, &session_id, sizeof(session_id)), out);
708
709 /* set fixed cipher on client and server */
710 require_noerr(SSLSetEnabledCiphers(client->handle, &ciphers[i].cipher, 1), out);
711 require_noerr(SSLSetEnabledCiphers(server->handle, &ciphers[i].cipher, 1), out);
712
713 char test_description[1024];
714 snprintf(test_description, sizeof(test_description),
715 "%40s ADH:%d CSA:%d DTLS:%d",
716 ciphers[i].name,
717 server->dh_anonymous,
718 server->client_side_auth,
719 d);
720
721 printf("Echo test: %s\n", test_description);
722
723 pthread_create(&client_thread, NULL, securetransport_ssl_thread, client);
724 pthread_create(&server_thread, NULL, securetransport_ssl_thread, server);
725
726 int server_err, client_err;
727 pthread_join(client_thread, (void*)&client_err);
728 pthread_join(server_thread, (void*)&server_err);
729
730 ok(!server_err && !client_err, "%40s ADH:%d CSA:%d DTLS:%d",
731 ciphers[i].name,
732 server->dh_anonymous,
733 server->client_side_auth,
734 d);
735 out:
736 close(sp[0]);
737 close(sp[1]);
738 }
739 } /* all configs */
740
741 CFRelease(server_certs);
742
743 }
744
745 int ssl_39_echo(int argc, char *const *argv)
746 {
747 plan_tests(2 * 2 * 2 * 3 * (ciphers_len-1)/* client auth on/off * #configs * #ciphers */
748 + 1 /*cert*/);
749
750
751 tests();
752
753 return 0;
754 }
755
756 #endif
757
758 /*
759 TODO: count errSSLWouldBlock
760 TODO: skip tests that don't matter: client_auth and anonymous dh
761 TODO: we seem to only be negotiating tls - force a round of sslv3
762 TODO: allow secure transport to also defer client side auth to client
763 TODO: make sure anonymous dh is never selected if not expicitly enabled
764 TODO: make sure DHE is not available if not explicitly enabled and no parameters
765 are set
766 TODO: resumable sessions
767 */