1 /***************************************************************************
3 * Project ___| | | | _ \| |
5 * | (__| |_| | _ <| |___
6 * \___|\___/|_| \_\_____|
8 * Copyright (C) 2012 - 2017, Nick Zitzmann, <nickzman@gmail.com>.
9 * Copyright (C) 2012 - 2017, Daniel Stenberg, <daniel@haxx.se>, et al.
11 * This software is licensed as described in the file COPYING, which
12 * you should have received as part of this distribution. The terms
13 * are also available at https://curl.haxx.se/docs/copyright.html.
15 * You may opt to use, copy, modify, merge, publish, distribute and/or sell
16 * copies of the Software, and permit persons to whom the Software is
17 * furnished to do so, under the terms of the COPYING file.
19 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
20 * KIND, either express or implied.
22 ***************************************************************************/
25 * Source file for all iOS and macOS SecureTransport-specific code for the
26 * TLS/SSL layer. No code but vtls.c should ever call or use these functions.
29 #include "curl_setup.h"
31 #include "urldata.h" /* for the Curl_easy definition */
32 #include "curl_base64.h"
38 #pragma clang diagnostic push
39 #pragma clang diagnostic ignored "-Wtautological-pointer-compare"
40 #endif /* __clang__ */
44 #include <Security/Security.h>
45 /* For some reason, when building for iOS, the omnibus header above does
46 * not include SecureTransport.h as of iOS SDK 5.1. */
47 #include <Security/SecureTransport.h>
48 #include <CoreFoundation/CoreFoundation.h>
49 #include <CommonCrypto/CommonDigest.h>
51 /* The Security framework has changed greatly between iOS and different macOS
52 versions, and we will try to support as many of them as we can (back to
53 Leopard and iOS 5) by using macros and weak-linking.
55 In general, you want to build this using the most recent OS SDK, since some
56 features require curl to be built against the latest SDK. TLS 1.1 and 1.2
57 support, for instance, require the macOS 10.8 SDK or later. TLS 1.3
58 requires the macOS 10.13 or iOS 11 SDK or later. */
59 #if (TARGET_OS_MAC && !(TARGET_OS_EMBEDDED || TARGET_OS_IPHONE))
61 #if MAC_OS_X_VERSION_MAX_ALLOWED < 1050
62 #error "The darwinssl back-end requires Leopard or later."
63 #endif /* MAC_OS_X_VERSION_MAX_ALLOWED < 1050 */
65 #define CURL_BUILD_IOS 0
66 #define CURL_BUILD_IOS_7 0
67 #define CURL_BUILD_IOS_11 0
68 #define CURL_BUILD_MAC 1
69 /* This is the maximum API level we are allowed to use when building: */
70 #define CURL_BUILD_MAC_10_5 MAC_OS_X_VERSION_MAX_ALLOWED >= 1050
71 #define CURL_BUILD_MAC_10_6 MAC_OS_X_VERSION_MAX_ALLOWED >= 1060
72 #define CURL_BUILD_MAC_10_7 MAC_OS_X_VERSION_MAX_ALLOWED >= 1070
73 #define CURL_BUILD_MAC_10_8 MAC_OS_X_VERSION_MAX_ALLOWED >= 1080
74 #define CURL_BUILD_MAC_10_9 MAC_OS_X_VERSION_MAX_ALLOWED >= 1090
75 #define CURL_BUILD_MAC_10_13 MAC_OS_X_VERSION_MAX_ALLOWED >= 101300
76 /* These macros mean "the following code is present to allow runtime backward
77 compatibility with at least this cat or earlier":
78 (You set this at build-time using the compiler command line option
79 "-mmacos-version-min.") */
80 #define CURL_SUPPORT_MAC_10_5 MAC_OS_X_VERSION_MIN_REQUIRED <= 1050
81 #define CURL_SUPPORT_MAC_10_6 MAC_OS_X_VERSION_MIN_REQUIRED <= 1060
82 #define CURL_SUPPORT_MAC_10_7 MAC_OS_X_VERSION_MIN_REQUIRED <= 1070
83 #define CURL_SUPPORT_MAC_10_8 MAC_OS_X_VERSION_MIN_REQUIRED <= 1080
84 #define CURL_SUPPORT_MAC_10_9 MAC_OS_X_VERSION_MIN_REQUIRED <= 1090
86 #elif TARGET_OS_EMBEDDED || TARGET_OS_IPHONE
87 #define CURL_BUILD_IOS 1
88 #define CURL_BUILD_IOS_7 __IPHONE_OS_VERSION_MAX_ALLOWED >= 70000
89 #define CURL_BUILD_IOS_11 __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000
90 #define CURL_BUILD_MAC 0
91 #define CURL_BUILD_MAC_10_5 0
92 #define CURL_BUILD_MAC_10_6 0
93 #define CURL_BUILD_MAC_10_7 0
94 #define CURL_BUILD_MAC_10_8 0
95 #define CURL_BUILD_MAC_10_9 0
96 #define CURL_BUILD_MAC_10_13 0
97 #define CURL_SUPPORT_MAC_10_5 0
98 #define CURL_SUPPORT_MAC_10_6 0
99 #define CURL_SUPPORT_MAC_10_7 0
100 #define CURL_SUPPORT_MAC_10_8 0
101 #define CURL_SUPPORT_MAC_10_9 0
104 #error "The darwinssl back-end requires iOS or OS X."
105 #endif /* (TARGET_OS_MAC && !(TARGET_OS_EMBEDDED || TARGET_OS_IPHONE)) */
108 #include <sys/sysctl.h>
109 #endif /* CURL_BUILD_MAC */
113 #include "inet_pton.h"
117 #include "darwinssl.h"
118 #include "curl_printf.h"
120 #include "curl_memory.h"
121 /* The last #include file should be: */
122 #include "memdebug.h"
124 /* From MacTypes.h (which we can't include because it isn't present in iOS: */
128 struct ssl_backend_data {
129 SSLContextRef ssl_ctx;
130 curl_socket_t ssl_sockfd;
131 bool ssl_direction; /* true if writing, false if reading */
132 size_t ssl_write_buffered_length;
135 #define BACKEND connssl->backend
137 /* pinned public key support tests */
139 /* version 1 supports macOS 10.12+ and iOS 10+ */
140 #if ((TARGET_OS_IPHONE && __IPHONE_OS_VERSION_MIN_REQUIRED >= 100000) || \
141 (!TARGET_OS_IPHONE && __MAC_OS_X_VERSION_MIN_REQUIRED >= 101200))
142 #define DARWIN_SSL_PINNEDPUBKEY_V1 1
145 /* version 2 supports MacOSX 10.7+ */
146 #if (!TARGET_OS_IPHONE && __MAC_OS_X_VERSION_MIN_REQUIRED >= 1070)
147 #define DARWIN_SSL_PINNEDPUBKEY_V2 1
150 #if defined(DARWIN_SSL_PINNEDPUBKEY_V1) || defined(DARWIN_SSL_PINNEDPUBKEY_V2)
151 /* this backend supports CURLOPT_PINNEDPUBLICKEY */
152 #define DARWIN_SSL_PINNEDPUBKEY 1
153 #endif /* DARWIN_SSL_PINNEDPUBKEY */
155 #ifdef DARWIN_SSL_PINNEDPUBKEY
156 /* both new and old APIs return rsa keys missing the spki header (not DER) */
157 static const unsigned char rsa4096SpkiHeader[] = {
158 0x30, 0x82, 0x02, 0x22, 0x30, 0x0d,
159 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
160 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05,
161 0x00, 0x03, 0x82, 0x02, 0x0f, 0x00};
163 static const unsigned char rsa2048SpkiHeader[] = {
164 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d,
165 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
166 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05,
167 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00};
168 #ifdef DARWIN_SSL_PINNEDPUBKEY_V1
169 /* the *new* version doesn't return DER encoded ecdsa certs like the old... */
170 static const unsigned char ecDsaSecp256r1SpkiHeader[] = {
171 0x30, 0x59, 0x30, 0x13, 0x06, 0x07,
172 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x02,
173 0x01, 0x06, 0x08, 0x2a, 0x86, 0x48,
174 0xce, 0x3d, 0x03, 0x01, 0x07, 0x03,
177 static const unsigned char ecDsaSecp384r1SpkiHeader[] = {
178 0x30, 0x76, 0x30, 0x10, 0x06, 0x07,
179 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x02,
180 0x01, 0x06, 0x05, 0x2b, 0x81, 0x04,
181 0x00, 0x22, 0x03, 0x62, 0x00};
182 #endif /* DARWIN_SSL_PINNEDPUBKEY_V1 */
183 #endif /* DARWIN_SSL_PINNEDPUBKEY */
185 /* The following two functions were ripped from Apple sample code,
186 * with some modifications: */
187 static OSStatus SocketRead(SSLConnectionRef connection,
188 void *data, /* owned by
191 size_t *dataLength) /* IN/OUT */
193 size_t bytesToGo = *dataLength;
194 size_t initLen = bytesToGo;
195 UInt8 *currData = (UInt8 *)data;
196 /*int sock = *(int *)connection;*/
197 struct ssl_connect_data *connssl = (struct ssl_connect_data *)connection;
198 int sock = BACKEND->ssl_sockfd;
199 OSStatus rtn = noErr;
208 rrtn = read(sock, currData, bytesToGo);
210 /* this is guesswork... */
212 if(rrtn == 0) { /* EOF = server hung up */
213 /* the framework will turn this into errSSLClosedNoNotify */
214 rtn = errSSLClosedGraceful;
216 else /* do the switch */
219 /* connection closed */
220 rtn = errSSLClosedGraceful;
223 rtn = errSSLClosedAbort;
226 rtn = errSSLWouldBlock;
227 BACKEND->ssl_direction = false;
238 bytesToGo -= bytesRead;
239 currData += bytesRead;
242 /* filled buffer with incoming data, done */
246 *dataLength = initLen - bytesToGo;
251 static OSStatus SocketWrite(SSLConnectionRef connection,
253 size_t *dataLength) /* IN/OUT */
255 size_t bytesSent = 0;
256 /*int sock = *(int *)connection;*/
257 struct ssl_connect_data *connssl = (struct ssl_connect_data *)connection;
258 int sock = BACKEND->ssl_sockfd;
260 size_t dataLen = *dataLength;
261 const UInt8 *dataPtr = (UInt8 *)data;
269 (char *)dataPtr + bytesSent,
270 dataLen - bytesSent);
271 } while((length > 0) &&
272 ( (bytesSent += length) < dataLen) );
276 if(theErr == EAGAIN) {
277 ortn = errSSLWouldBlock;
278 BACKEND->ssl_direction = true;
287 *dataLength = bytesSent;
291 #ifndef CURL_DISABLE_VERBOSE_STRINGS
292 CF_INLINE const char *SSLCipherNameForNumber(SSLCipherSuite cipher)
295 /* SSL version 3.0 */
296 case SSL_RSA_WITH_NULL_MD5:
297 return "SSL_RSA_WITH_NULL_MD5";
299 case SSL_RSA_WITH_NULL_SHA:
300 return "SSL_RSA_WITH_NULL_SHA";
302 case SSL_RSA_EXPORT_WITH_RC4_40_MD5:
303 return "SSL_RSA_EXPORT_WITH_RC4_40_MD5";
305 case SSL_RSA_WITH_RC4_128_MD5:
306 return "SSL_RSA_WITH_RC4_128_MD5";
308 case SSL_RSA_WITH_RC4_128_SHA:
309 return "SSL_RSA_WITH_RC4_128_SHA";
311 case SSL_RSA_EXPORT_WITH_RC2_CBC_40_MD5:
312 return "SSL_RSA_EXPORT_WITH_RC2_CBC_40_MD5";
314 case SSL_RSA_WITH_IDEA_CBC_SHA:
315 return "SSL_RSA_WITH_IDEA_CBC_SHA";
317 case SSL_RSA_EXPORT_WITH_DES40_CBC_SHA:
318 return "SSL_RSA_EXPORT_WITH_DES40_CBC_SHA";
320 case SSL_RSA_WITH_DES_CBC_SHA:
321 return "SSL_RSA_WITH_DES_CBC_SHA";
323 case SSL_RSA_WITH_3DES_EDE_CBC_SHA:
324 return "SSL_RSA_WITH_3DES_EDE_CBC_SHA";
326 case SSL_DH_DSS_EXPORT_WITH_DES40_CBC_SHA:
327 return "SSL_DH_DSS_EXPORT_WITH_DES40_CBC_SHA";
329 case SSL_DH_DSS_WITH_DES_CBC_SHA:
330 return "SSL_DH_DSS_WITH_DES_CBC_SHA";
332 case SSL_DH_DSS_WITH_3DES_EDE_CBC_SHA:
333 return "SSL_DH_DSS_WITH_3DES_EDE_CBC_SHA";
335 case SSL_DH_RSA_EXPORT_WITH_DES40_CBC_SHA:
336 return "SSL_DH_RSA_EXPORT_WITH_DES40_CBC_SHA";
338 case SSL_DH_RSA_WITH_DES_CBC_SHA:
339 return "SSL_DH_RSA_WITH_DES_CBC_SHA";
341 case SSL_DH_RSA_WITH_3DES_EDE_CBC_SHA:
342 return "SSL_DH_RSA_WITH_3DES_EDE_CBC_SHA";
344 case SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA:
345 return "SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA";
347 case SSL_DHE_DSS_WITH_DES_CBC_SHA:
348 return "SSL_DHE_DSS_WITH_DES_CBC_SHA";
350 case SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA:
351 return "SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA";
353 case SSL_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA:
354 return "SSL_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA";
356 case SSL_DHE_RSA_WITH_DES_CBC_SHA:
357 return "SSL_DHE_RSA_WITH_DES_CBC_SHA";
359 case SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA:
360 return "SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA";
362 case SSL_DH_anon_EXPORT_WITH_RC4_40_MD5:
363 return "SSL_DH_anon_EXPORT_WITH_RC4_40_MD5";
365 case SSL_DH_anon_WITH_RC4_128_MD5:
366 return "SSL_DH_anon_WITH_RC4_128_MD5";
368 case SSL_DH_anon_EXPORT_WITH_DES40_CBC_SHA:
369 return "SSL_DH_anon_EXPORT_WITH_DES40_CBC_SHA";
371 case SSL_DH_anon_WITH_DES_CBC_SHA:
372 return "SSL_DH_anon_WITH_DES_CBC_SHA";
374 case SSL_DH_anon_WITH_3DES_EDE_CBC_SHA:
375 return "SSL_DH_anon_WITH_3DES_EDE_CBC_SHA";
377 case SSL_FORTEZZA_DMS_WITH_NULL_SHA:
378 return "SSL_FORTEZZA_DMS_WITH_NULL_SHA";
380 case SSL_FORTEZZA_DMS_WITH_FORTEZZA_CBC_SHA:
381 return "SSL_FORTEZZA_DMS_WITH_FORTEZZA_CBC_SHA";
383 /* TLS 1.0 with AES (RFC 3268)
384 (Apparently these are used in SSLv3 implementations as well.) */
385 case TLS_RSA_WITH_AES_128_CBC_SHA:
386 return "TLS_RSA_WITH_AES_128_CBC_SHA";
388 case TLS_DH_DSS_WITH_AES_128_CBC_SHA:
389 return "TLS_DH_DSS_WITH_AES_128_CBC_SHA";
391 case TLS_DH_RSA_WITH_AES_128_CBC_SHA:
392 return "TLS_DH_RSA_WITH_AES_128_CBC_SHA";
394 case TLS_DHE_DSS_WITH_AES_128_CBC_SHA:
395 return "TLS_DHE_DSS_WITH_AES_128_CBC_SHA";
397 case TLS_DHE_RSA_WITH_AES_128_CBC_SHA:
398 return "TLS_DHE_RSA_WITH_AES_128_CBC_SHA";
400 case TLS_DH_anon_WITH_AES_128_CBC_SHA:
401 return "TLS_DH_anon_WITH_AES_128_CBC_SHA";
403 case TLS_RSA_WITH_AES_256_CBC_SHA:
404 return "TLS_RSA_WITH_AES_256_CBC_SHA";
406 case TLS_DH_DSS_WITH_AES_256_CBC_SHA:
407 return "TLS_DH_DSS_WITH_AES_256_CBC_SHA";
409 case TLS_DH_RSA_WITH_AES_256_CBC_SHA:
410 return "TLS_DH_RSA_WITH_AES_256_CBC_SHA";
412 case TLS_DHE_DSS_WITH_AES_256_CBC_SHA:
413 return "TLS_DHE_DSS_WITH_AES_256_CBC_SHA";
415 case TLS_DHE_RSA_WITH_AES_256_CBC_SHA:
416 return "TLS_DHE_RSA_WITH_AES_256_CBC_SHA";
418 case TLS_DH_anon_WITH_AES_256_CBC_SHA:
419 return "TLS_DH_anon_WITH_AES_256_CBC_SHA";
421 /* SSL version 2.0 */
422 case SSL_RSA_WITH_RC2_CBC_MD5:
423 return "SSL_RSA_WITH_RC2_CBC_MD5";
425 case SSL_RSA_WITH_IDEA_CBC_MD5:
426 return "SSL_RSA_WITH_IDEA_CBC_MD5";
428 case SSL_RSA_WITH_DES_CBC_MD5:
429 return "SSL_RSA_WITH_DES_CBC_MD5";
431 case SSL_RSA_WITH_3DES_EDE_CBC_MD5:
432 return "SSL_RSA_WITH_3DES_EDE_CBC_MD5";
435 return "SSL_NULL_WITH_NULL_NULL";
438 CF_INLINE const char *TLSCipherNameForNumber(SSLCipherSuite cipher)
441 /* TLS 1.0 with AES (RFC 3268) */
442 case TLS_RSA_WITH_AES_128_CBC_SHA:
443 return "TLS_RSA_WITH_AES_128_CBC_SHA";
445 case TLS_DH_DSS_WITH_AES_128_CBC_SHA:
446 return "TLS_DH_DSS_WITH_AES_128_CBC_SHA";
448 case TLS_DH_RSA_WITH_AES_128_CBC_SHA:
449 return "TLS_DH_RSA_WITH_AES_128_CBC_SHA";
451 case TLS_DHE_DSS_WITH_AES_128_CBC_SHA:
452 return "TLS_DHE_DSS_WITH_AES_128_CBC_SHA";
454 case TLS_DHE_RSA_WITH_AES_128_CBC_SHA:
455 return "TLS_DHE_RSA_WITH_AES_128_CBC_SHA";
457 case TLS_DH_anon_WITH_AES_128_CBC_SHA:
458 return "TLS_DH_anon_WITH_AES_128_CBC_SHA";
460 case TLS_RSA_WITH_AES_256_CBC_SHA:
461 return "TLS_RSA_WITH_AES_256_CBC_SHA";
463 case TLS_DH_DSS_WITH_AES_256_CBC_SHA:
464 return "TLS_DH_DSS_WITH_AES_256_CBC_SHA";
466 case TLS_DH_RSA_WITH_AES_256_CBC_SHA:
467 return "TLS_DH_RSA_WITH_AES_256_CBC_SHA";
469 case TLS_DHE_DSS_WITH_AES_256_CBC_SHA:
470 return "TLS_DHE_DSS_WITH_AES_256_CBC_SHA";
472 case TLS_DHE_RSA_WITH_AES_256_CBC_SHA:
473 return "TLS_DHE_RSA_WITH_AES_256_CBC_SHA";
475 case TLS_DH_anon_WITH_AES_256_CBC_SHA:
476 return "TLS_DH_anon_WITH_AES_256_CBC_SHA";
478 #if CURL_BUILD_MAC_10_6 || CURL_BUILD_IOS
479 /* TLS 1.0 with ECDSA (RFC 4492) */
480 case TLS_ECDH_ECDSA_WITH_NULL_SHA:
481 return "TLS_ECDH_ECDSA_WITH_NULL_SHA";
483 case TLS_ECDH_ECDSA_WITH_RC4_128_SHA:
484 return "TLS_ECDH_ECDSA_WITH_RC4_128_SHA";
486 case TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA:
487 return "TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA";
489 case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA:
490 return "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA";
492 case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA:
493 return "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA";
495 case TLS_ECDHE_ECDSA_WITH_NULL_SHA:
496 return "TLS_ECDHE_ECDSA_WITH_NULL_SHA";
498 case TLS_ECDHE_ECDSA_WITH_RC4_128_SHA:
499 return "TLS_ECDHE_ECDSA_WITH_RC4_128_SHA";
501 case TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA:
502 return "TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA";
504 case TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA:
505 return "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA";
507 case TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA:
508 return "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA";
510 case TLS_ECDH_RSA_WITH_NULL_SHA:
511 return "TLS_ECDH_RSA_WITH_NULL_SHA";
513 case TLS_ECDH_RSA_WITH_RC4_128_SHA:
514 return "TLS_ECDH_RSA_WITH_RC4_128_SHA";
516 case TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA:
517 return "TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA";
519 case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA:
520 return "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA";
522 case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA:
523 return "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA";
525 case TLS_ECDHE_RSA_WITH_NULL_SHA:
526 return "TLS_ECDHE_RSA_WITH_NULL_SHA";
528 case TLS_ECDHE_RSA_WITH_RC4_128_SHA:
529 return "TLS_ECDHE_RSA_WITH_RC4_128_SHA";
531 case TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA:
532 return "TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA";
534 case TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA:
535 return "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA";
537 case TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA:
538 return "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA";
540 case TLS_ECDH_anon_WITH_NULL_SHA:
541 return "TLS_ECDH_anon_WITH_NULL_SHA";
543 case TLS_ECDH_anon_WITH_RC4_128_SHA:
544 return "TLS_ECDH_anon_WITH_RC4_128_SHA";
546 case TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA:
547 return "TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA";
549 case TLS_ECDH_anon_WITH_AES_128_CBC_SHA:
550 return "TLS_ECDH_anon_WITH_AES_128_CBC_SHA";
552 case TLS_ECDH_anon_WITH_AES_256_CBC_SHA:
553 return "TLS_ECDH_anon_WITH_AES_256_CBC_SHA";
555 #endif /* CURL_BUILD_MAC_10_6 || CURL_BUILD_IOS */
556 #if CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS
557 /* TLS 1.2 (RFC 5246) */
558 case TLS_RSA_WITH_NULL_MD5:
559 return "TLS_RSA_WITH_NULL_MD5";
561 case TLS_RSA_WITH_NULL_SHA:
562 return "TLS_RSA_WITH_NULL_SHA";
564 case TLS_RSA_WITH_RC4_128_MD5:
565 return "TLS_RSA_WITH_RC4_128_MD5";
567 case TLS_RSA_WITH_RC4_128_SHA:
568 return "TLS_RSA_WITH_RC4_128_SHA";
570 case TLS_RSA_WITH_3DES_EDE_CBC_SHA:
571 return "TLS_RSA_WITH_3DES_EDE_CBC_SHA";
573 case TLS_RSA_WITH_NULL_SHA256:
574 return "TLS_RSA_WITH_NULL_SHA256";
576 case TLS_RSA_WITH_AES_128_CBC_SHA256:
577 return "TLS_RSA_WITH_AES_128_CBC_SHA256";
579 case TLS_RSA_WITH_AES_256_CBC_SHA256:
580 return "TLS_RSA_WITH_AES_256_CBC_SHA256";
582 case TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA:
583 return "TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA";
585 case TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA:
586 return "TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA";
588 case TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA:
589 return "TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA";
591 case TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA:
592 return "TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA";
594 case TLS_DH_DSS_WITH_AES_128_CBC_SHA256:
595 return "TLS_DH_DSS_WITH_AES_128_CBC_SHA256";
597 case TLS_DH_RSA_WITH_AES_128_CBC_SHA256:
598 return "TLS_DH_RSA_WITH_AES_128_CBC_SHA256";
600 case TLS_DHE_DSS_WITH_AES_128_CBC_SHA256:
601 return "TLS_DHE_DSS_WITH_AES_128_CBC_SHA256";
603 case TLS_DHE_RSA_WITH_AES_128_CBC_SHA256:
604 return "TLS_DHE_RSA_WITH_AES_128_CBC_SHA256";
606 case TLS_DH_DSS_WITH_AES_256_CBC_SHA256:
607 return "TLS_DH_DSS_WITH_AES_256_CBC_SHA256";
609 case TLS_DH_RSA_WITH_AES_256_CBC_SHA256:
610 return "TLS_DH_RSA_WITH_AES_256_CBC_SHA256";
612 case TLS_DHE_DSS_WITH_AES_256_CBC_SHA256:
613 return "TLS_DHE_DSS_WITH_AES_256_CBC_SHA256";
615 case TLS_DHE_RSA_WITH_AES_256_CBC_SHA256:
616 return "TLS_DHE_RSA_WITH_AES_256_CBC_SHA256";
618 case TLS_DH_anon_WITH_RC4_128_MD5:
619 return "TLS_DH_anon_WITH_RC4_128_MD5";
621 case TLS_DH_anon_WITH_3DES_EDE_CBC_SHA:
622 return "TLS_DH_anon_WITH_3DES_EDE_CBC_SHA";
624 case TLS_DH_anon_WITH_AES_128_CBC_SHA256:
625 return "TLS_DH_anon_WITH_AES_128_CBC_SHA256";
627 case TLS_DH_anon_WITH_AES_256_CBC_SHA256:
628 return "TLS_DH_anon_WITH_AES_256_CBC_SHA256";
630 /* TLS 1.2 with AES GCM (RFC 5288) */
631 case TLS_RSA_WITH_AES_128_GCM_SHA256:
632 return "TLS_RSA_WITH_AES_128_GCM_SHA256";
634 case TLS_RSA_WITH_AES_256_GCM_SHA384:
635 return "TLS_RSA_WITH_AES_256_GCM_SHA384";
637 case TLS_DHE_RSA_WITH_AES_128_GCM_SHA256:
638 return "TLS_DHE_RSA_WITH_AES_128_GCM_SHA256";
640 case TLS_DHE_RSA_WITH_AES_256_GCM_SHA384:
641 return "TLS_DHE_RSA_WITH_AES_256_GCM_SHA384";
643 case TLS_DH_RSA_WITH_AES_128_GCM_SHA256:
644 return "TLS_DH_RSA_WITH_AES_128_GCM_SHA256";
646 case TLS_DH_RSA_WITH_AES_256_GCM_SHA384:
647 return "TLS_DH_RSA_WITH_AES_256_GCM_SHA384";
649 case TLS_DHE_DSS_WITH_AES_128_GCM_SHA256:
650 return "TLS_DHE_DSS_WITH_AES_128_GCM_SHA256";
652 case TLS_DHE_DSS_WITH_AES_256_GCM_SHA384:
653 return "TLS_DHE_DSS_WITH_AES_256_GCM_SHA384";
655 case TLS_DH_DSS_WITH_AES_128_GCM_SHA256:
656 return "TLS_DH_DSS_WITH_AES_128_GCM_SHA256";
658 case TLS_DH_DSS_WITH_AES_256_GCM_SHA384:
659 return "TLS_DH_DSS_WITH_AES_256_GCM_SHA384";
661 case TLS_DH_anon_WITH_AES_128_GCM_SHA256:
662 return "TLS_DH_anon_WITH_AES_128_GCM_SHA256";
664 case TLS_DH_anon_WITH_AES_256_GCM_SHA384:
665 return "TLS_DH_anon_WITH_AES_256_GCM_SHA384";
667 /* TLS 1.2 with elliptic curve ciphers (RFC 5289) */
668 case TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256:
669 return "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256";
671 case TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384:
672 return "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384";
674 case TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256:
675 return "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256";
677 case TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384:
678 return "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384";
680 case TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256:
681 return "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256";
683 case TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384:
684 return "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384";
686 case TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256:
687 return "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256";
689 case TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384:
690 return "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384";
692 case TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256:
693 return "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256";
695 case TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384:
696 return "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384";
698 case TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256:
699 return "TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256";
701 case TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384:
702 return "TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384";
704 case TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256:
705 return "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256";
707 case TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384:
708 return "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384";
710 case TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256:
711 return "TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256";
713 case TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384:
714 return "TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384";
716 case TLS_EMPTY_RENEGOTIATION_INFO_SCSV:
717 return "TLS_EMPTY_RENEGOTIATION_INFO_SCSV";
720 case SSL_RSA_WITH_NULL_MD5:
721 return "TLS_RSA_WITH_NULL_MD5";
723 case SSL_RSA_WITH_NULL_SHA:
724 return "TLS_RSA_WITH_NULL_SHA";
726 case SSL_RSA_WITH_RC4_128_MD5:
727 return "TLS_RSA_WITH_RC4_128_MD5";
729 case SSL_RSA_WITH_RC4_128_SHA:
730 return "TLS_RSA_WITH_RC4_128_SHA";
732 case SSL_RSA_WITH_3DES_EDE_CBC_SHA:
733 return "TLS_RSA_WITH_3DES_EDE_CBC_SHA";
735 case SSL_DH_anon_WITH_RC4_128_MD5:
736 return "TLS_DH_anon_WITH_RC4_128_MD5";
738 case SSL_DH_anon_WITH_3DES_EDE_CBC_SHA:
739 return "TLS_DH_anon_WITH_3DES_EDE_CBC_SHA";
741 #endif /* CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS */
742 #if CURL_BUILD_MAC_10_9 || CURL_BUILD_IOS_7
743 /* TLS PSK (RFC 4279): */
744 case TLS_PSK_WITH_RC4_128_SHA:
745 return "TLS_PSK_WITH_RC4_128_SHA";
747 case TLS_PSK_WITH_3DES_EDE_CBC_SHA:
748 return "TLS_PSK_WITH_3DES_EDE_CBC_SHA";
750 case TLS_PSK_WITH_AES_128_CBC_SHA:
751 return "TLS_PSK_WITH_AES_128_CBC_SHA";
753 case TLS_PSK_WITH_AES_256_CBC_SHA:
754 return "TLS_PSK_WITH_AES_256_CBC_SHA";
756 case TLS_DHE_PSK_WITH_RC4_128_SHA:
757 return "TLS_DHE_PSK_WITH_RC4_128_SHA";
759 case TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA:
760 return "TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA";
762 case TLS_DHE_PSK_WITH_AES_128_CBC_SHA:
763 return "TLS_DHE_PSK_WITH_AES_128_CBC_SHA";
765 case TLS_DHE_PSK_WITH_AES_256_CBC_SHA:
766 return "TLS_DHE_PSK_WITH_AES_256_CBC_SHA";
768 case TLS_RSA_PSK_WITH_RC4_128_SHA:
769 return "TLS_RSA_PSK_WITH_RC4_128_SHA";
771 case TLS_RSA_PSK_WITH_3DES_EDE_CBC_SHA:
772 return "TLS_RSA_PSK_WITH_3DES_EDE_CBC_SHA";
774 case TLS_RSA_PSK_WITH_AES_128_CBC_SHA:
775 return "TLS_RSA_PSK_WITH_AES_128_CBC_SHA";
777 case TLS_RSA_PSK_WITH_AES_256_CBC_SHA:
778 return "TLS_RSA_PSK_WITH_AES_256_CBC_SHA";
780 /* More TLS PSK (RFC 4785): */
781 case TLS_PSK_WITH_NULL_SHA:
782 return "TLS_PSK_WITH_NULL_SHA";
784 case TLS_DHE_PSK_WITH_NULL_SHA:
785 return "TLS_DHE_PSK_WITH_NULL_SHA";
787 case TLS_RSA_PSK_WITH_NULL_SHA:
788 return "TLS_RSA_PSK_WITH_NULL_SHA";
790 /* Even more TLS PSK (RFC 5487): */
791 case TLS_PSK_WITH_AES_128_GCM_SHA256:
792 return "TLS_PSK_WITH_AES_128_GCM_SHA256";
794 case TLS_PSK_WITH_AES_256_GCM_SHA384:
795 return "TLS_PSK_WITH_AES_256_GCM_SHA384";
797 case TLS_DHE_PSK_WITH_AES_128_GCM_SHA256:
798 return "TLS_DHE_PSK_WITH_AES_128_GCM_SHA256";
800 case TLS_DHE_PSK_WITH_AES_256_GCM_SHA384:
801 return "TLS_DHE_PSK_WITH_AES_256_GCM_SHA384";
803 case TLS_RSA_PSK_WITH_AES_128_GCM_SHA256:
804 return "TLS_RSA_PSK_WITH_AES_128_GCM_SHA256";
806 case TLS_RSA_PSK_WITH_AES_256_GCM_SHA384:
807 return "TLS_PSK_WITH_AES_256_GCM_SHA384";
809 case TLS_PSK_WITH_AES_128_CBC_SHA256:
810 return "TLS_PSK_WITH_AES_128_CBC_SHA256";
812 case TLS_PSK_WITH_AES_256_CBC_SHA384:
813 return "TLS_PSK_WITH_AES_256_CBC_SHA384";
815 case TLS_PSK_WITH_NULL_SHA256:
816 return "TLS_PSK_WITH_NULL_SHA256";
818 case TLS_PSK_WITH_NULL_SHA384:
819 return "TLS_PSK_WITH_NULL_SHA384";
821 case TLS_DHE_PSK_WITH_AES_128_CBC_SHA256:
822 return "TLS_DHE_PSK_WITH_AES_128_CBC_SHA256";
824 case TLS_DHE_PSK_WITH_AES_256_CBC_SHA384:
825 return "TLS_DHE_PSK_WITH_AES_256_CBC_SHA384";
827 case TLS_DHE_PSK_WITH_NULL_SHA256:
828 return "TLS_DHE_PSK_WITH_NULL_SHA256";
830 case TLS_DHE_PSK_WITH_NULL_SHA384:
831 return "TLS_RSA_PSK_WITH_NULL_SHA384";
833 case TLS_RSA_PSK_WITH_AES_128_CBC_SHA256:
834 return "TLS_RSA_PSK_WITH_AES_128_CBC_SHA256";
836 case TLS_RSA_PSK_WITH_AES_256_CBC_SHA384:
837 return "TLS_RSA_PSK_WITH_AES_256_CBC_SHA384";
839 case TLS_RSA_PSK_WITH_NULL_SHA256:
840 return "TLS_RSA_PSK_WITH_NULL_SHA256";
842 case TLS_RSA_PSK_WITH_NULL_SHA384:
843 return "TLS_RSA_PSK_WITH_NULL_SHA384";
845 #endif /* CURL_BUILD_MAC_10_9 || CURL_BUILD_IOS_7 */
846 #if CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11
847 /* New ChaCha20+Poly1305 cipher-suites used by TLS 1.3: */
848 case TLS_AES_128_GCM_SHA256:
849 return "TLS_AES_128_GCM_SHA256";
851 case TLS_AES_256_GCM_SHA384:
852 return "TLS_AES_256_GCM_SHA384";
854 case TLS_CHACHA20_POLY1305_SHA256:
855 return "TLS_CHACHA20_POLY1305_SHA256";
857 case TLS_AES_128_CCM_SHA256:
858 return "TLS_AES_128_CCM_SHA256";
860 case TLS_AES_128_CCM_8_SHA256:
861 return "TLS_AES_128_CCM_8_SHA256";
863 case TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256:
864 return "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256";
866 case TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256:
867 return "TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256";
869 #endif /* CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11 */
871 return "TLS_NULL_WITH_NULL_NULL";
873 #endif /* !CURL_DISABLE_VERBOSE_STRINGS */
876 CF_INLINE void GetDarwinVersionNumber(int *major, int *minor)
880 size_t os_version_len;
881 char *os_version_major, *os_version_minor;
884 /* Get the Darwin kernel version from the kernel using sysctl(): */
886 mib[1] = KERN_OSRELEASE;
887 if(sysctl(mib, 2, NULL, &os_version_len, NULL, 0) == -1)
889 os_version = malloc(os_version_len*sizeof(char));
892 if(sysctl(mib, 2, os_version, &os_version_len, NULL, 0) == -1) {
897 /* Parse the version: */
898 os_version_major = strtok_r(os_version, ".", &tok_buf);
899 os_version_minor = strtok_r(NULL, ".", &tok_buf);
900 *major = atoi(os_version_major);
901 *minor = atoi(os_version_minor);
904 #endif /* CURL_BUILD_MAC */
906 /* Apple provides a myriad of ways of getting information about a certificate
907 into a string. Some aren't available under iOS or newer cats. So here's
908 a unified function for getting a string describing the certificate that
909 ought to work in all cats starting with Leopard. */
910 CF_INLINE CFStringRef getsubject(SecCertificateRef cert)
912 CFStringRef server_cert_summary = CFSTR("(null)");
915 /* iOS: There's only one way to do this. */
916 server_cert_summary = SecCertificateCopySubjectSummary(cert);
918 #if CURL_BUILD_MAC_10_7
919 /* Lion & later: Get the long description if we can. */
920 if(SecCertificateCopyLongDescription != NULL)
921 server_cert_summary =
922 SecCertificateCopyLongDescription(NULL, cert, NULL);
924 #endif /* CURL_BUILD_MAC_10_7 */
925 #if CURL_BUILD_MAC_10_6
926 /* Snow Leopard: Get the certificate summary. */
927 if(SecCertificateCopySubjectSummary != NULL)
928 server_cert_summary = SecCertificateCopySubjectSummary(cert);
930 #endif /* CURL_BUILD_MAC_10_6 */
931 /* Leopard is as far back as we go... */
932 (void)SecCertificateCopyCommonName(cert, &server_cert_summary);
933 #endif /* CURL_BUILD_IOS */
934 return server_cert_summary;
937 static CURLcode CopyCertSubject(struct Curl_easy *data,
938 SecCertificateRef cert, char **certp)
940 CFStringRef c = getsubject(cert);
941 CURLcode result = CURLE_OK;
947 failf(data, "SSL: invalid CA certificate subject");
948 return CURLE_OUT_OF_MEMORY;
951 /* If the subject is already available as UTF-8 encoded (ie 'direct') then
952 use that, else convert it. */
953 direct = CFStringGetCStringPtr(c, kCFStringEncodingUTF8);
955 *certp = strdup(direct);
957 failf(data, "SSL: out of memory");
958 result = CURLE_OUT_OF_MEMORY;
962 size_t cbuf_size = ((size_t)CFStringGetLength(c) * 4) + 1;
963 cbuf = calloc(cbuf_size, 1);
965 if(!CFStringGetCString(c, cbuf, cbuf_size,
966 kCFStringEncodingUTF8)) {
967 failf(data, "SSL: invalid CA certificate subject");
968 result = CURLE_SSL_CACERT;
971 /* pass back the buffer */
975 failf(data, "SSL: couldn't allocate %zu bytes of memory", cbuf_size);
976 result = CURLE_OUT_OF_MEMORY;
985 #if CURL_SUPPORT_MAC_10_6
986 /* The SecKeychainSearch API was deprecated in Lion, and using it will raise
987 deprecation warnings, so let's not compile this unless it's necessary: */
988 static OSStatus CopyIdentityWithLabelOldSchool(char *label,
989 SecIdentityRef *out_c_a_k)
991 OSStatus status = errSecItemNotFound;
992 SecKeychainAttributeList attr_list;
993 SecKeychainAttribute attr;
994 SecKeychainSearchRef search = NULL;
995 SecCertificateRef cert = NULL;
997 /* Set up the attribute list: */
998 attr_list.count = 1L;
999 attr_list.attr = &attr;
1001 /* Set up our lone search criterion: */
1002 attr.tag = kSecLabelItemAttr;
1004 attr.length = (UInt32)strlen(label);
1006 /* Start searching: */
1007 status = SecKeychainSearchCreateFromAttributes(NULL,
1008 kSecCertificateItemClass,
1011 if(status == noErr) {
1012 status = SecKeychainSearchCopyNext(search,
1013 (SecKeychainItemRef *)&cert);
1014 if(status == noErr && cert) {
1015 /* If we found a certificate, does it have a private key? */
1016 status = SecIdentityCreateWithCertificate(NULL, cert, out_c_a_k);
1025 #endif /* CURL_SUPPORT_MAC_10_6 */
1027 static OSStatus CopyIdentityWithLabel(char *label,
1028 SecIdentityRef *out_cert_and_key)
1030 OSStatus status = errSecItemNotFound;
1032 #if CURL_BUILD_MAC_10_7 || CURL_BUILD_IOS
1033 CFArrayRef keys_list;
1034 CFIndex keys_list_count;
1036 CFStringRef common_name;
1038 /* SecItemCopyMatching() was introduced in iOS and Snow Leopard.
1039 kSecClassIdentity was introduced in Lion. If both exist, let's use them
1040 to find the certificate. */
1041 if(SecItemCopyMatching != NULL && kSecClassIdentity != NULL) {
1043 CFTypeRef values[5];
1044 CFDictionaryRef query_dict;
1045 CFStringRef label_cf = CFStringCreateWithCString(NULL, label,
1046 kCFStringEncodingUTF8);
1048 /* Set up our search criteria and expected results: */
1049 values[0] = kSecClassIdentity; /* we want a certificate and a key */
1050 keys[0] = kSecClass;
1051 values[1] = kCFBooleanTrue; /* we want a reference */
1052 keys[1] = kSecReturnRef;
1053 values[2] = kSecMatchLimitAll; /* kSecMatchLimitOne would be better if the
1054 * label matching below worked correctly */
1055 keys[2] = kSecMatchLimit;
1056 /* identity searches need a SecPolicyRef in order to work */
1057 values[3] = SecPolicyCreateSSL(false, NULL);
1058 keys[3] = kSecMatchPolicy;
1059 /* match the name of the certificate (doesn't work in macOS 10.12.1) */
1060 values[4] = label_cf;
1061 keys[4] = kSecAttrLabel;
1062 query_dict = CFDictionaryCreate(NULL, (const void **)keys,
1063 (const void **)values, 5L,
1064 &kCFCopyStringDictionaryKeyCallBacks,
1065 &kCFTypeDictionaryValueCallBacks);
1066 CFRelease(values[3]);
1068 /* Do we have a match? */
1069 status = SecItemCopyMatching(query_dict, (CFTypeRef *) &keys_list);
1071 /* Because kSecAttrLabel matching doesn't work with kSecClassIdentity,
1072 * we need to find the correct identity ourselves */
1073 if(status == noErr) {
1074 keys_list_count = CFArrayGetCount(keys_list);
1075 *out_cert_and_key = NULL;
1077 for(i = 0; i<keys_list_count; i++) {
1078 OSStatus err = noErr;
1079 SecCertificateRef cert = NULL;
1080 SecIdentityRef identity =
1081 (SecIdentityRef) CFArrayGetValueAtIndex(keys_list, i);
1082 err = SecIdentityCopyCertificate(identity, &cert);
1085 common_name = SecCertificateCopySubjectSummary(cert);
1086 #elif CURL_BUILD_MAC_10_7
1087 SecCertificateCopyCommonName(cert, &common_name);
1089 if(CFStringCompare(common_name, label_cf, 0) == kCFCompareEqualTo) {
1091 CFRelease(common_name);
1093 *out_cert_and_key = identity;
1097 CFRelease(common_name);
1104 CFRelease(keys_list);
1105 CFRelease(query_dict);
1106 CFRelease(label_cf);
1109 #if CURL_SUPPORT_MAC_10_6
1110 /* On Leopard and Snow Leopard, fall back to SecKeychainSearch. */
1111 status = CopyIdentityWithLabelOldSchool(label, out_cert_and_key);
1112 #endif /* CURL_SUPPORT_MAC_10_6 */
1114 #elif CURL_SUPPORT_MAC_10_6
1115 /* For developers building on older cats, we have no choice but to fall back
1116 to SecKeychainSearch. */
1117 status = CopyIdentityWithLabelOldSchool(label, out_cert_and_key);
1118 #endif /* CURL_BUILD_MAC_10_7 || CURL_BUILD_IOS */
1122 static OSStatus CopyIdentityFromPKCS12File(const char *cPath,
1123 const char *cPassword,
1124 SecIdentityRef *out_cert_and_key)
1126 OSStatus status = errSecItemNotFound;
1127 CFURLRef pkcs_url = CFURLCreateFromFileSystemRepresentation(NULL,
1128 (const UInt8 *)cPath, strlen(cPath), false);
1129 CFStringRef password = cPassword ? CFStringCreateWithCString(NULL,
1130 cPassword, kCFStringEncodingUTF8) : NULL;
1131 CFDataRef pkcs_data = NULL;
1133 /* We can import P12 files on iOS or OS X 10.7 or later: */
1134 /* These constants are documented as having first appeared in 10.6 but they
1135 raise linker errors when used on that cat for some reason. */
1136 #if CURL_BUILD_MAC_10_7 || CURL_BUILD_IOS
1137 if(CFURLCreateDataAndPropertiesFromResource(NULL, pkcs_url, &pkcs_data,
1138 NULL, NULL, &status)) {
1139 CFArrayRef items = NULL;
1141 /* On iOS SecPKCS12Import will never add the client certificate to the
1144 * It gives us back a SecIdentityRef that we can use directly. */
1146 const void *cKeys[] = {kSecImportExportPassphrase};
1147 const void *cValues[] = {password};
1148 CFDictionaryRef options = CFDictionaryCreate(NULL, cKeys, cValues,
1149 password ? 1L : 0L, NULL, NULL);
1151 if(options != NULL) {
1152 status = SecPKCS12Import(pkcs_data, options, &items);
1157 /* On macOS SecPKCS12Import will always add the client certificate to
1160 * As this doesn't match iOS, and apps may not want to see their client
1161 * certificate saved in the the user's keychain, we use SecItemImport
1162 * with a NULL keychain to avoid importing it.
1164 * This returns a SecCertificateRef from which we can construct a
1167 #elif CURL_BUILD_MAC_10_7
1168 SecItemImportExportKeyParameters keyParams;
1169 SecExternalFormat inputFormat = kSecFormatPKCS12;
1170 SecExternalItemType inputType = kSecItemTypeCertificate;
1172 memset(&keyParams, 0x00, sizeof(keyParams));
1173 keyParams.version = SEC_KEY_IMPORT_EXPORT_PARAMS_VERSION;
1174 keyParams.passphrase = password;
1176 status = SecItemImport(pkcs_data, NULL, &inputFormat, &inputType,
1177 0, &keyParams, NULL, &items);
1181 /* Extract the SecIdentityRef */
1182 if(status == errSecSuccess && items && CFArrayGetCount(items)) {
1184 count = CFArrayGetCount(items);
1186 for(i = 0; i < count; i++) {
1187 CFTypeRef item = (CFTypeRef) CFArrayGetValueAtIndex(items, i);
1188 CFTypeID itemID = CFGetTypeID(item);
1190 if(itemID == CFDictionaryGetTypeID()) {
1191 CFTypeRef identity = (CFTypeRef) CFDictionaryGetValue(
1192 (CFDictionaryRef) item,
1193 kSecImportItemIdentity);
1195 *out_cert_and_key = (SecIdentityRef) identity;
1198 else if(itemID == SecCertificateGetTypeID()) {
1199 status = SecIdentityCreateWithCertificate(NULL,
1200 (SecCertificateRef) item,
1209 CFRelease(pkcs_data);
1211 #endif /* CURL_BUILD_MAC_10_7 || CURL_BUILD_IOS */
1213 CFRelease(password);
1214 CFRelease(pkcs_url);
1218 /* This code was borrowed from nss.c, with some modifications:
1219 * Determine whether the nickname passed in is a filename that needs to
1220 * be loaded as a PEM or a regular NSS nickname.
1222 * returns 1 for a file
1223 * returns 0 for not a file
1225 CF_INLINE bool is_file(const char *filename)
1229 if(filename == NULL)
1232 if(stat(filename, &st) == 0)
1233 return S_ISREG(st.st_mode);
1237 #if CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS
1238 static CURLcode darwinssl_version_from_curl(SSLProtocol *darwinver,
1241 switch(ssl_version) {
1242 case CURL_SSLVERSION_TLSv1_0:
1243 *darwinver = kTLSProtocol1;
1245 case CURL_SSLVERSION_TLSv1_1:
1246 *darwinver = kTLSProtocol11;
1248 case CURL_SSLVERSION_TLSv1_2:
1249 *darwinver = kTLSProtocol12;
1251 case CURL_SSLVERSION_TLSv1_3:
1252 /* TLS 1.3 support first appeared in iOS 11 and macOS 10.13 */
1253 #if CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11
1254 /* We can assume __builtin_available() will always work in the
1256 if(__builtin_available(macOS 10.13, iOS 11.0, *)) {
1257 *darwinver = kTLSProtocol13;
1260 #endif /* CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11 */
1263 return CURLE_SSL_CONNECT_ERROR;
1268 set_ssl_version_min_max(struct connectdata *conn, int sockindex)
1270 struct Curl_easy *data = conn->data;
1271 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
1272 long ssl_version = SSL_CONN_CONFIG(version);
1273 long ssl_version_max = SSL_CONN_CONFIG(version_max);
1274 long max_supported_version_by_os;
1276 /* macOS 10.5-10.7 supported TLS 1.0 only.
1277 macOS 10.8 and later, and iOS 5 and later, added TLS 1.1 and 1.2.
1278 macOS 10.13 and later, and iOS 11 and later, added TLS 1.3. */
1279 #if CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11
1280 if(__builtin_available(macOS 10.13, iOS 11.0, *)) {
1281 max_supported_version_by_os = CURL_SSLVERSION_MAX_TLSv1_3;
1284 max_supported_version_by_os = CURL_SSLVERSION_MAX_TLSv1_2;
1287 max_supported_version_by_os = CURL_SSLVERSION_MAX_TLSv1_2;
1288 #endif /* CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11 */
1290 switch(ssl_version) {
1291 case CURL_SSLVERSION_DEFAULT:
1292 case CURL_SSLVERSION_TLSv1:
1293 ssl_version = CURL_SSLVERSION_TLSv1_0;
1294 ssl_version_max = max_supported_version_by_os;
1298 switch(ssl_version_max) {
1299 case CURL_SSLVERSION_MAX_NONE:
1300 ssl_version_max = ssl_version << 16;
1302 case CURL_SSLVERSION_MAX_DEFAULT:
1303 ssl_version_max = max_supported_version_by_os;
1307 #if CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS
1308 if(SSLSetProtocolVersionMax != NULL) {
1309 SSLProtocol darwin_ver_min = kTLSProtocol1;
1310 SSLProtocol darwin_ver_max = kTLSProtocol1;
1311 CURLcode result = darwinssl_version_from_curl(&darwin_ver_min,
1314 failf(data, "unsupported min version passed via CURLOPT_SSLVERSION");
1317 result = darwinssl_version_from_curl(&darwin_ver_max,
1318 ssl_version_max >> 16);
1320 failf(data, "unsupported max version passed via CURLOPT_SSLVERSION");
1324 (void)SSLSetProtocolVersionMin(BACKEND->ssl_ctx, darwin_ver_min);
1325 (void)SSLSetProtocolVersionMax(BACKEND->ssl_ctx, darwin_ver_max);
1329 #if CURL_SUPPORT_MAC_10_8
1330 long i = ssl_version;
1331 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1334 for(; i <= (ssl_version_max >> 16); i++) {
1336 case CURL_SSLVERSION_TLSv1_0:
1337 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1341 case CURL_SSLVERSION_TLSv1_1:
1342 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1346 case CURL_SSLVERSION_TLSv1_2:
1347 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1351 case CURL_SSLVERSION_TLSv1_3:
1352 failf(data, "Your version of the OS does not support TLSv1.3");
1353 return CURLE_SSL_CONNECT_ERROR;
1357 #endif /* CURL_SUPPORT_MAC_10_8 */
1359 #endif /* CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS */
1360 failf(data, "DarwinSSL: cannot set SSL protocol");
1361 return CURLE_SSL_CONNECT_ERROR;
1365 static CURLcode darwinssl_connect_step1(struct connectdata *conn,
1368 struct Curl_easy *data = conn->data;
1369 curl_socket_t sockfd = conn->sock[sockindex];
1370 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
1371 const char * const ssl_cafile = SSL_CONN_CONFIG(CAfile);
1372 const bool verifypeer = SSL_CONN_CONFIG(verifypeer);
1373 char * const ssl_cert = SSL_SET_OPTION(cert);
1374 const char * const hostname = SSL_IS_PROXY() ? conn->http_proxy.host.name :
1376 const long int port = SSL_IS_PROXY() ? conn->port : conn->remote_port;
1378 struct in6_addr addr;
1380 struct in_addr addr;
1381 #endif /* ENABLE_IPV6 */
1382 size_t all_ciphers_count = 0UL, allowed_ciphers_count = 0UL, i;
1383 SSLCipherSuite *all_ciphers = NULL, *allowed_ciphers = NULL;
1384 OSStatus err = noErr;
1386 int darwinver_maj = 0, darwinver_min = 0;
1388 GetDarwinVersionNumber(&darwinver_maj, &darwinver_min);
1389 #endif /* CURL_BUILD_MAC */
1391 #if CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS
1392 if(SSLCreateContext != NULL) { /* use the newer API if avaialble */
1393 if(BACKEND->ssl_ctx)
1394 CFRelease(BACKEND->ssl_ctx);
1395 BACKEND->ssl_ctx = SSLCreateContext(NULL, kSSLClientSide, kSSLStreamType);
1396 if(!BACKEND->ssl_ctx) {
1397 failf(data, "SSL: couldn't create a context!");
1398 return CURLE_OUT_OF_MEMORY;
1402 /* The old ST API does not exist under iOS, so don't compile it: */
1403 #if CURL_SUPPORT_MAC_10_8
1404 if(BACKEND->ssl_ctx)
1405 (void)SSLDisposeContext(BACKEND->ssl_ctx);
1406 err = SSLNewContext(false, &(BACKEND->ssl_ctx));
1408 failf(data, "SSL: couldn't create a context: OSStatus %d", err);
1409 return CURLE_OUT_OF_MEMORY;
1411 #endif /* CURL_SUPPORT_MAC_10_8 */
1414 if(BACKEND->ssl_ctx)
1415 (void)SSLDisposeContext(BACKEND->ssl_ctx);
1416 err = SSLNewContext(false, &(BACKEND->ssl_ctx));
1418 failf(data, "SSL: couldn't create a context: OSStatus %d", err);
1419 return CURLE_OUT_OF_MEMORY;
1421 #endif /* CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS */
1422 BACKEND->ssl_write_buffered_length = 0UL; /* reset buffered write length */
1424 /* check to see if we've been told to use an explicit SSL/TLS version */
1425 #if CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS
1426 if(SSLSetProtocolVersionMax != NULL) {
1427 switch(conn->ssl_config.version) {
1428 case CURL_SSLVERSION_DEFAULT:
1429 case CURL_SSLVERSION_TLSv1:
1430 (void)SSLSetProtocolVersionMin(BACKEND->ssl_ctx, kTLSProtocol1);
1431 #if CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11
1432 if(__builtin_available(macOS 10.13, iOS 11.0, *)) {
1433 (void)SSLSetProtocolVersionMax(BACKEND->ssl_ctx, kTLSProtocol13);
1436 (void)SSLSetProtocolVersionMax(BACKEND->ssl_ctx, kTLSProtocol12);
1439 (void)SSLSetProtocolVersionMax(BACKEND->ssl_ctx, kTLSProtocol12);
1440 #endif /* CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11 */
1442 case CURL_SSLVERSION_TLSv1_0:
1443 case CURL_SSLVERSION_TLSv1_1:
1444 case CURL_SSLVERSION_TLSv1_2:
1445 case CURL_SSLVERSION_TLSv1_3:
1447 CURLcode result = set_ssl_version_min_max(conn, sockindex);
1448 if(result != CURLE_OK)
1452 case CURL_SSLVERSION_SSLv3:
1453 err = SSLSetProtocolVersionMin(BACKEND->ssl_ctx, kSSLProtocol3);
1455 failf(data, "Your version of the OS does not support SSLv3");
1456 return CURLE_SSL_CONNECT_ERROR;
1458 (void)SSLSetProtocolVersionMax(BACKEND->ssl_ctx, kSSLProtocol3);
1460 case CURL_SSLVERSION_SSLv2:
1461 err = SSLSetProtocolVersionMin(BACKEND->ssl_ctx, kSSLProtocol2);
1463 failf(data, "Your version of the OS does not support SSLv2");
1464 return CURLE_SSL_CONNECT_ERROR;
1466 (void)SSLSetProtocolVersionMax(BACKEND->ssl_ctx, kSSLProtocol2);
1469 failf(data, "Unrecognized parameter passed via CURLOPT_SSLVERSION");
1470 return CURLE_SSL_CONNECT_ERROR;
1474 #if CURL_SUPPORT_MAC_10_8
1475 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1478 switch(conn->ssl_config.version) {
1479 case CURL_SSLVERSION_DEFAULT:
1480 case CURL_SSLVERSION_TLSv1:
1481 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1484 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1487 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1491 case CURL_SSLVERSION_TLSv1_0:
1492 case CURL_SSLVERSION_TLSv1_1:
1493 case CURL_SSLVERSION_TLSv1_2:
1494 case CURL_SSLVERSION_TLSv1_3:
1496 CURLcode result = set_ssl_version_min_max(conn, sockindex);
1497 if(result != CURLE_OK)
1501 case CURL_SSLVERSION_SSLv3:
1502 err = SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1506 failf(data, "Your version of the OS does not support SSLv3");
1507 return CURLE_SSL_CONNECT_ERROR;
1510 case CURL_SSLVERSION_SSLv2:
1511 err = SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1515 failf(data, "Your version of the OS does not support SSLv2");
1516 return CURLE_SSL_CONNECT_ERROR;
1520 failf(data, "Unrecognized parameter passed via CURLOPT_SSLVERSION");
1521 return CURLE_SSL_CONNECT_ERROR;
1523 #endif /* CURL_SUPPORT_MAC_10_8 */
1526 if(conn->ssl_config.version_max != CURL_SSLVERSION_MAX_NONE) {
1527 failf(data, "Your version of the OS does not support to set maximum"
1528 " SSL/TLS version");
1529 return CURLE_SSL_CONNECT_ERROR;
1531 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx, kSSLProtocolAll, false);
1532 switch(conn->ssl_config.version) {
1533 case CURL_SSLVERSION_DEFAULT:
1534 case CURL_SSLVERSION_TLSv1:
1535 case CURL_SSLVERSION_TLSv1_0:
1536 (void)SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1540 case CURL_SSLVERSION_TLSv1_1:
1541 failf(data, "Your version of the OS does not support TLSv1.1");
1542 return CURLE_SSL_CONNECT_ERROR;
1543 case CURL_SSLVERSION_TLSv1_2:
1544 failf(data, "Your version of the OS does not support TLSv1.2");
1545 return CURLE_SSL_CONNECT_ERROR;
1546 case CURL_SSLVERSION_TLSv1_3:
1547 failf(data, "Your version of the OS does not support TLSv1.3");
1548 return CURLE_SSL_CONNECT_ERROR;
1549 case CURL_SSLVERSION_SSLv2:
1550 err = SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1554 failf(data, "Your version of the OS does not support SSLv2");
1555 return CURLE_SSL_CONNECT_ERROR;
1558 case CURL_SSLVERSION_SSLv3:
1559 err = SSLSetProtocolVersionEnabled(BACKEND->ssl_ctx,
1563 failf(data, "Your version of the OS does not support SSLv3");
1564 return CURLE_SSL_CONNECT_ERROR;
1568 failf(data, "Unrecognized parameter passed via CURLOPT_SSLVERSION");
1569 return CURLE_SSL_CONNECT_ERROR;
1571 #endif /* CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS */
1573 if(SSL_SET_OPTION(key)) {
1574 infof(data, "WARNING: SSL: CURLOPT_SSLKEY is ignored by Secure "
1575 "Transport. The private key must be in the Keychain.\n");
1579 SecIdentityRef cert_and_key = NULL;
1580 bool is_cert_file = is_file(ssl_cert);
1582 /* User wants to authenticate with a client cert. Look for it:
1583 If we detect that this is a file on disk, then let's load it.
1584 Otherwise, assume that the user wants to use an identity loaded
1585 from the Keychain. */
1587 if(!SSL_SET_OPTION(cert_type))
1588 infof(data, "WARNING: SSL: Certificate type not set, assuming "
1589 "PKCS#12 format.\n");
1590 else if(strncmp(SSL_SET_OPTION(cert_type), "P12",
1591 strlen(SSL_SET_OPTION(cert_type))) != 0)
1592 infof(data, "WARNING: SSL: The Security framework only supports "
1593 "loading identities that are in PKCS#12 format.\n");
1595 err = CopyIdentityFromPKCS12File(ssl_cert,
1596 SSL_SET_OPTION(key_passwd), &cert_and_key);
1599 err = CopyIdentityWithLabel(ssl_cert, &cert_and_key);
1601 if(err == noErr && cert_and_key) {
1602 SecCertificateRef cert = NULL;
1603 CFTypeRef certs_c[1];
1606 /* If we found one, print it out: */
1607 err = SecIdentityCopyCertificate(cert_and_key, &cert);
1610 CURLcode result = CopyCertSubject(data, cert, &certp);
1612 infof(data, "Client certificate: %s\n", certp);
1620 certs_c[0] = cert_and_key;
1621 certs = CFArrayCreate(NULL, (const void **)certs_c, 1L,
1622 &kCFTypeArrayCallBacks);
1623 err = SSLSetCertificate(BACKEND->ssl_ctx, certs);
1627 failf(data, "SSL: SSLSetCertificate() failed: OSStatus %d", err);
1628 return CURLE_SSL_CERTPROBLEM;
1630 CFRelease(cert_and_key);
1634 case errSecAuthFailed: case -25264: /* errSecPkcs12VerifyFailure */
1635 failf(data, "SSL: Incorrect password for the certificate \"%s\" "
1636 "and its private key.", ssl_cert);
1638 case -26275: /* errSecDecode */ case -25257: /* errSecUnknownFormat */
1639 failf(data, "SSL: Couldn't make sense of the data in the "
1640 "certificate \"%s\" and its private key.",
1643 case -25260: /* errSecPassphraseRequired */
1644 failf(data, "SSL The certificate \"%s\" requires a password.",
1647 case errSecItemNotFound:
1648 failf(data, "SSL: Can't find the certificate \"%s\" and its private "
1649 "key in the Keychain.", ssl_cert);
1652 failf(data, "SSL: Can't load the certificate \"%s\" and its private "
1653 "key: OSStatus %d", ssl_cert, err);
1656 return CURLE_SSL_CERTPROBLEM;
1660 /* SSL always tries to verify the peer, this only says whether it should
1661 * fail to connect if the verification fails, or if it should continue
1662 * anyway. In the latter case the result of the verification is checked with
1663 * SSL_get_verify_result() below. */
1664 #if CURL_BUILD_MAC_10_6 || CURL_BUILD_IOS
1665 /* Snow Leopard introduced the SSLSetSessionOption() function, but due to
1666 a library bug with the way the kSSLSessionOptionBreakOnServerAuth flag
1667 works, it doesn't work as expected under Snow Leopard, Lion or
1669 So we need to call SSLSetEnableCertVerify() on those older cats in order
1670 to disable certificate validation if the user turned that off.
1671 (SecureTransport will always validate the certificate chain by
1674 Darwin 11.x.x is Lion (10.7)
1675 Darwin 12.x.x is Mountain Lion (10.8)
1676 Darwin 13.x.x is Mavericks (10.9)
1677 Darwin 14.x.x is Yosemite (10.10)
1678 Darwin 15.x.x is El Capitan (10.11)
1681 if(SSLSetSessionOption != NULL && darwinver_maj >= 13) {
1683 if(SSLSetSessionOption != NULL) {
1684 #endif /* CURL_BUILD_MAC */
1685 bool break_on_auth = !conn->ssl_config.verifypeer || ssl_cafile;
1686 err = SSLSetSessionOption(BACKEND->ssl_ctx,
1687 kSSLSessionOptionBreakOnServerAuth,
1690 failf(data, "SSL: SSLSetSessionOption() failed: OSStatus %d", err);
1691 return CURLE_SSL_CONNECT_ERROR;
1695 #if CURL_SUPPORT_MAC_10_8
1696 err = SSLSetEnableCertVerify(BACKEND->ssl_ctx,
1697 conn->ssl_config.verifypeer?true:false);
1699 failf(data, "SSL: SSLSetEnableCertVerify() failed: OSStatus %d", err);
1700 return CURLE_SSL_CONNECT_ERROR;
1702 #endif /* CURL_SUPPORT_MAC_10_8 */
1705 err = SSLSetEnableCertVerify(BACKEND->ssl_ctx,
1706 conn->ssl_config.verifypeer?true:false);
1708 failf(data, "SSL: SSLSetEnableCertVerify() failed: OSStatus %d", err);
1709 return CURLE_SSL_CONNECT_ERROR;
1711 #endif /* CURL_BUILD_MAC_10_6 || CURL_BUILD_IOS */
1713 if(ssl_cafile && verifypeer) {
1714 bool is_cert_file = is_file(ssl_cafile);
1717 failf(data, "SSL: can't load CA certificate file %s", ssl_cafile);
1718 return CURLE_SSL_CACERT_BADFILE;
1722 /* Configure hostname check. SNI is used if available.
1723 * Both hostname check and SNI require SSLSetPeerDomainName().
1724 * Also: the verifyhost setting influences SNI usage */
1725 if(conn->ssl_config.verifyhost) {
1726 err = SSLSetPeerDomainName(BACKEND->ssl_ctx, hostname,
1730 infof(data, "WARNING: SSL: SSLSetPeerDomainName() failed: OSStatus %d\n",
1734 if((Curl_inet_pton(AF_INET, hostname, &addr))
1736 || (Curl_inet_pton(AF_INET6, hostname, &addr))
1739 infof(data, "WARNING: using IP address, SNI is being disabled by "
1744 infof(data, "WARNING: disabling hostname validation also disables SNI.\n");
1747 /* Disable cipher suites that ST supports but are not safe. These ciphers
1748 are unlikely to be used in any case since ST gives other ciphers a much
1749 higher priority, but it's probably better that we not connect at all than
1750 to give the user a false sense of security if the server only supports
1751 insecure ciphers. (Note: We don't care about SSLv2-only ciphers.) */
1752 (void)SSLGetNumberSupportedCiphers(BACKEND->ssl_ctx, &all_ciphers_count);
1753 all_ciphers = malloc(all_ciphers_count*sizeof(SSLCipherSuite));
1754 allowed_ciphers = malloc(all_ciphers_count*sizeof(SSLCipherSuite));
1755 if(all_ciphers && allowed_ciphers &&
1756 SSLGetSupportedCiphers(BACKEND->ssl_ctx, all_ciphers,
1757 &all_ciphers_count) == noErr) {
1758 for(i = 0UL ; i < all_ciphers_count ; i++) {
1760 /* There's a known bug in early versions of Mountain Lion where ST's ECC
1761 ciphers (cipher suite 0xC001 through 0xC032) simply do not work.
1762 Work around the problem here by disabling those ciphers if we are
1763 running in an affected version of OS X. */
1764 if(darwinver_maj == 12 && darwinver_min <= 3 &&
1765 all_ciphers[i] >= 0xC001 && all_ciphers[i] <= 0xC032) {
1768 #endif /* CURL_BUILD_MAC */
1769 switch(all_ciphers[i]) {
1770 /* Disable NULL ciphersuites: */
1771 case SSL_NULL_WITH_NULL_NULL:
1772 case SSL_RSA_WITH_NULL_MD5:
1773 case SSL_RSA_WITH_NULL_SHA:
1774 case 0x003B: /* TLS_RSA_WITH_NULL_SHA256 */
1775 case SSL_FORTEZZA_DMS_WITH_NULL_SHA:
1776 case 0xC001: /* TLS_ECDH_ECDSA_WITH_NULL_SHA */
1777 case 0xC006: /* TLS_ECDHE_ECDSA_WITH_NULL_SHA */
1778 case 0xC00B: /* TLS_ECDH_RSA_WITH_NULL_SHA */
1779 case 0xC010: /* TLS_ECDHE_RSA_WITH_NULL_SHA */
1780 case 0x002C: /* TLS_PSK_WITH_NULL_SHA */
1781 case 0x002D: /* TLS_DHE_PSK_WITH_NULL_SHA */
1782 case 0x002E: /* TLS_RSA_PSK_WITH_NULL_SHA */
1783 case 0x00B0: /* TLS_PSK_WITH_NULL_SHA256 */
1784 case 0x00B1: /* TLS_PSK_WITH_NULL_SHA384 */
1785 case 0x00B4: /* TLS_DHE_PSK_WITH_NULL_SHA256 */
1786 case 0x00B5: /* TLS_DHE_PSK_WITH_NULL_SHA384 */
1787 case 0x00B8: /* TLS_RSA_PSK_WITH_NULL_SHA256 */
1788 case 0x00B9: /* TLS_RSA_PSK_WITH_NULL_SHA384 */
1789 /* Disable anonymous ciphersuites: */
1790 case SSL_DH_anon_EXPORT_WITH_RC4_40_MD5:
1791 case SSL_DH_anon_WITH_RC4_128_MD5:
1792 case SSL_DH_anon_EXPORT_WITH_DES40_CBC_SHA:
1793 case SSL_DH_anon_WITH_DES_CBC_SHA:
1794 case SSL_DH_anon_WITH_3DES_EDE_CBC_SHA:
1795 case TLS_DH_anon_WITH_AES_128_CBC_SHA:
1796 case TLS_DH_anon_WITH_AES_256_CBC_SHA:
1797 case 0xC015: /* TLS_ECDH_anon_WITH_NULL_SHA */
1798 case 0xC016: /* TLS_ECDH_anon_WITH_RC4_128_SHA */
1799 case 0xC017: /* TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA */
1800 case 0xC018: /* TLS_ECDH_anon_WITH_AES_128_CBC_SHA */
1801 case 0xC019: /* TLS_ECDH_anon_WITH_AES_256_CBC_SHA */
1802 case 0x006C: /* TLS_DH_anon_WITH_AES_128_CBC_SHA256 */
1803 case 0x006D: /* TLS_DH_anon_WITH_AES_256_CBC_SHA256 */
1804 case 0x00A6: /* TLS_DH_anon_WITH_AES_128_GCM_SHA256 */
1805 case 0x00A7: /* TLS_DH_anon_WITH_AES_256_GCM_SHA384 */
1806 /* Disable weak key ciphersuites: */
1807 case SSL_RSA_EXPORT_WITH_RC4_40_MD5:
1808 case SSL_RSA_EXPORT_WITH_RC2_CBC_40_MD5:
1809 case SSL_RSA_EXPORT_WITH_DES40_CBC_SHA:
1810 case SSL_DH_DSS_EXPORT_WITH_DES40_CBC_SHA:
1811 case SSL_DH_RSA_EXPORT_WITH_DES40_CBC_SHA:
1812 case SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA:
1813 case SSL_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA:
1814 case SSL_RSA_WITH_DES_CBC_SHA:
1815 case SSL_DH_DSS_WITH_DES_CBC_SHA:
1816 case SSL_DH_RSA_WITH_DES_CBC_SHA:
1817 case SSL_DHE_DSS_WITH_DES_CBC_SHA:
1818 case SSL_DHE_RSA_WITH_DES_CBC_SHA:
1820 case SSL_RSA_WITH_IDEA_CBC_SHA:
1821 case SSL_RSA_WITH_IDEA_CBC_MD5:
1823 case SSL_RSA_WITH_RC4_128_MD5:
1824 case SSL_RSA_WITH_RC4_128_SHA:
1825 case 0xC002: /* TLS_ECDH_ECDSA_WITH_RC4_128_SHA */
1826 case 0xC007: /* TLS_ECDHE_ECDSA_WITH_RC4_128_SHA*/
1827 case 0xC00C: /* TLS_ECDH_RSA_WITH_RC4_128_SHA */
1828 case 0xC011: /* TLS_ECDHE_RSA_WITH_RC4_128_SHA */
1829 case 0x008A: /* TLS_PSK_WITH_RC4_128_SHA */
1830 case 0x008E: /* TLS_DHE_PSK_WITH_RC4_128_SHA */
1831 case 0x0092: /* TLS_RSA_PSK_WITH_RC4_128_SHA */
1833 default: /* enable everything else */
1834 allowed_ciphers[allowed_ciphers_count++] = all_ciphers[i];
1838 err = SSLSetEnabledCiphers(BACKEND->ssl_ctx, allowed_ciphers,
1839 allowed_ciphers_count);
1841 failf(data, "SSL: SSLSetEnabledCiphers() failed: OSStatus %d", err);
1842 return CURLE_SSL_CONNECT_ERROR;
1846 Curl_safefree(all_ciphers);
1847 Curl_safefree(allowed_ciphers);
1848 failf(data, "SSL: Failed to allocate memory for allowed ciphers");
1849 return CURLE_OUT_OF_MEMORY;
1851 Curl_safefree(all_ciphers);
1852 Curl_safefree(allowed_ciphers);
1854 #if CURL_BUILD_MAC_10_9 || CURL_BUILD_IOS_7
1855 /* We want to enable 1/n-1 when using a CBC cipher unless the user
1856 specifically doesn't want us doing that: */
1857 if(SSLSetSessionOption != NULL) {
1858 /* TODO s/data->set.ssl.enable_beast/SSL_SET_OPTION(enable_beast)/g */
1859 SSLSetSessionOption(BACKEND->ssl_ctx, kSSLSessionOptionSendOneByteRecord,
1860 !data->set.ssl.enable_beast);
1861 SSLSetSessionOption(BACKEND->ssl_ctx, kSSLSessionOptionFalseStart,
1862 data->set.ssl.falsestart); /* false start support */
1864 #endif /* CURL_BUILD_MAC_10_9 || CURL_BUILD_IOS_7 */
1866 /* Check if there's a cached ID we can/should use here! */
1867 if(SSL_SET_OPTION(primary.sessionid)) {
1868 char *ssl_sessionid;
1869 size_t ssl_sessionid_len;
1871 Curl_ssl_sessionid_lock(conn);
1872 if(!Curl_ssl_getsessionid(conn, (void **)&ssl_sessionid,
1873 &ssl_sessionid_len, sockindex)) {
1874 /* we got a session id, use it! */
1875 err = SSLSetPeerID(BACKEND->ssl_ctx, ssl_sessionid, ssl_sessionid_len);
1876 Curl_ssl_sessionid_unlock(conn);
1878 failf(data, "SSL: SSLSetPeerID() failed: OSStatus %d", err);
1879 return CURLE_SSL_CONNECT_ERROR;
1881 /* Informational message */
1882 infof(data, "SSL re-using session ID\n");
1884 /* If there isn't one, then let's make one up! This has to be done prior
1885 to starting the handshake. */
1889 aprintf("%s:%d:%d:%s:%hu", ssl_cafile,
1890 verifypeer, SSL_CONN_CONFIG(verifyhost), hostname, port);
1891 ssl_sessionid_len = strlen(ssl_sessionid);
1893 err = SSLSetPeerID(BACKEND->ssl_ctx, ssl_sessionid, ssl_sessionid_len);
1895 Curl_ssl_sessionid_unlock(conn);
1896 failf(data, "SSL: SSLSetPeerID() failed: OSStatus %d", err);
1897 return CURLE_SSL_CONNECT_ERROR;
1900 result = Curl_ssl_addsessionid(conn, ssl_sessionid, ssl_sessionid_len,
1902 Curl_ssl_sessionid_unlock(conn);
1904 failf(data, "failed to store ssl session");
1910 err = SSLSetIOFuncs(BACKEND->ssl_ctx, SocketRead, SocketWrite);
1912 failf(data, "SSL: SSLSetIOFuncs() failed: OSStatus %d", err);
1913 return CURLE_SSL_CONNECT_ERROR;
1916 /* pass the raw socket into the SSL layers */
1917 /* We need to store the FD in a constant memory address, because
1918 * SSLSetConnection() will not copy that address. I've found that
1919 * conn->sock[sockindex] may change on its own. */
1920 BACKEND->ssl_sockfd = sockfd;
1921 err = SSLSetConnection(BACKEND->ssl_ctx, connssl);
1923 failf(data, "SSL: SSLSetConnection() failed: %d", err);
1924 return CURLE_SSL_CONNECT_ERROR;
1927 connssl->connecting_state = ssl_connect_2;
1931 static long pem_to_der(const char *in, unsigned char **out, size_t *outlen)
1933 char *sep_start, *sep_end, *cert_start, *cert_end;
1938 /* Jump through the separators at the beginning of the certificate. */
1939 sep_start = strstr(in, "-----");
1940 if(sep_start == NULL)
1942 cert_start = strstr(sep_start + 1, "-----");
1943 if(cert_start == NULL)
1948 /* Find separator after the end of the certificate. */
1949 cert_end = strstr(cert_start, "-----");
1950 if(cert_end == NULL)
1953 sep_end = strstr(cert_end + 1, "-----");
1958 len = cert_end - cert_start;
1959 b64 = malloc(len + 1);
1963 /* Create base64 string without linefeeds. */
1964 for(i = 0, j = 0; i < len; i++) {
1965 if(cert_start[i] != '\r' && cert_start[i] != '\n')
1966 b64[j++] = cert_start[i];
1970 err = Curl_base64_decode((const char *)b64, out, outlen);
1977 return sep_end - in;
1980 static int read_cert(const char *file, unsigned char **out, size_t *outlen)
1983 ssize_t n, len = 0, cap = 512;
1984 unsigned char buf[512], *data;
1997 n = read(fd, buf, sizeof(buf));
2008 if(len + n >= cap) {
2010 data = realloc(data, cap);
2017 memcpy(data + len, buf, n);
2028 static int sslerr_to_curlerr(struct Curl_easy *data, int err)
2031 case errSSLXCertChainInvalid:
2032 failf(data, "SSL certificate problem: Invalid certificate chain");
2033 return CURLE_SSL_CACERT;
2034 case errSSLUnknownRootCert:
2035 failf(data, "SSL certificate problem: Untrusted root certificate");
2036 return CURLE_SSL_CACERT;
2037 case errSSLNoRootCert:
2038 failf(data, "SSL certificate problem: No root certificate");
2039 return CURLE_SSL_CACERT;
2040 case errSSLCertExpired:
2041 failf(data, "SSL certificate problem: Certificate chain had an "
2042 "expired certificate");
2043 return CURLE_SSL_CACERT;
2045 failf(data, "SSL certificate problem: Couldn't understand the server "
2046 "certificate format");
2047 return CURLE_SSL_CONNECT_ERROR;
2048 case errSSLHostNameMismatch:
2049 failf(data, "SSL certificate peer hostname mismatch");
2050 return CURLE_PEER_FAILED_VERIFICATION;
2052 failf(data, "SSL unexpected certificate error %d", err);
2053 return CURLE_SSL_CACERT;
2057 static int append_cert_to_array(struct Curl_easy *data,
2058 unsigned char *buf, size_t buflen,
2059 CFMutableArrayRef array)
2061 CFDataRef certdata = CFDataCreate(kCFAllocatorDefault, buf, buflen);
2065 failf(data, "SSL: failed to allocate array for CA certificate");
2066 return CURLE_OUT_OF_MEMORY;
2069 SecCertificateRef cacert =
2070 SecCertificateCreateWithData(kCFAllocatorDefault, certdata);
2071 CFRelease(certdata);
2073 failf(data, "SSL: failed to create SecCertificate from CA certificate");
2074 return CURLE_SSL_CACERT;
2077 /* Check if cacert is valid. */
2078 result = CopyCertSubject(data, cacert, &certp);
2083 CFArrayAppendValue(array, cacert);
2089 static int verify_cert(const char *cafile, struct Curl_easy *data,
2094 unsigned char *certbuf, *der;
2095 size_t buflen, derlen, offset = 0;
2097 if(read_cert(cafile, &certbuf, &buflen) < 0) {
2098 failf(data, "SSL: failed to read or invalid CA certificate");
2099 return CURLE_SSL_CACERT;
2103 * Certbuf now contains the contents of the certificate file, which can be
2104 * - a single DER certificate,
2105 * - a single PEM certificate or
2106 * - a bunch of PEM certificates (certificate bundle).
2108 * Go through certbuf, and convert any PEM certificate in it into DER
2111 CFMutableArrayRef array = CFArrayCreateMutable(kCFAllocatorDefault, 0,
2112 &kCFTypeArrayCallBacks);
2115 failf(data, "SSL: out of memory creating CA certificate array");
2116 return CURLE_OUT_OF_MEMORY;
2119 while(offset < buflen) {
2123 * Check if the certificate is in PEM format, and convert it to DER. If
2124 * this fails, we assume the certificate is in DER format.
2126 res = pem_to_der((const char *)certbuf + offset, &der, &derlen);
2130 failf(data, "SSL: invalid CA certificate #%d (offset %d) in bundle",
2132 return CURLE_SSL_CACERT;
2136 if(res == 0 && offset == 0) {
2137 /* This is not a PEM file, probably a certificate in DER format. */
2138 rc = append_cert_to_array(data, certbuf, buflen, array);
2140 if(rc != CURLE_OK) {
2147 /* No more certificates in the bundle. */
2152 rc = append_cert_to_array(data, der, derlen, array);
2154 if(rc != CURLE_OK) {
2162 OSStatus ret = SSLCopyPeerTrust(ctx, &trust);
2164 failf(data, "SSL: error getting certificate chain");
2166 return CURLE_OUT_OF_MEMORY;
2168 else if(ret != noErr) {
2170 return sslerr_to_curlerr(data, ret);
2173 ret = SecTrustSetAnchorCertificates(trust, array);
2176 return sslerr_to_curlerr(data, ret);
2178 ret = SecTrustSetAnchorCertificatesOnly(trust, true);
2181 return sslerr_to_curlerr(data, ret);
2184 SecTrustResultType trust_eval = 0;
2185 ret = SecTrustEvaluate(trust, &trust_eval);
2189 return sslerr_to_curlerr(data, ret);
2192 switch(trust_eval) {
2193 case kSecTrustResultUnspecified:
2194 case kSecTrustResultProceed:
2197 case kSecTrustResultRecoverableTrustFailure:
2198 case kSecTrustResultDeny:
2200 failf(data, "SSL: certificate verification failed (result: %d)",
2202 return CURLE_PEER_FAILED_VERIFICATION;
2206 #ifdef DARWIN_SSL_PINNEDPUBKEY
2207 static CURLcode pkp_pin_peer_pubkey(struct Curl_easy *data,
2209 const char *pinnedpubkey)
2211 size_t pubkeylen, realpubkeylen, spkiHeaderLength = 24;
2212 unsigned char *pubkey = NULL, *realpubkey = NULL;
2213 const unsigned char *spkiHeader = NULL;
2214 CFDataRef publicKeyBits = NULL;
2216 /* Result is returned to caller */
2217 CURLcode result = CURLE_SSL_PINNEDPUBKEYNOTMATCH;
2219 /* if a path wasn't specified, don't pin */
2229 OSStatus ret = SSLCopyPeerTrust(ctx, &trust);
2230 if(ret != noErr || trust == NULL)
2233 SecKeyRef keyRef = SecTrustCopyPublicKey(trust);
2238 #ifdef DARWIN_SSL_PINNEDPUBKEY_V1
2240 publicKeyBits = SecKeyCopyExternalRepresentation(keyRef, NULL);
2242 if(publicKeyBits == NULL)
2245 #elif DARWIN_SSL_PINNEDPUBKEY_V2
2247 OSStatus success = SecItemExport(keyRef, kSecFormatOpenSSL, 0, NULL,
2250 if(success != errSecSuccess || publicKeyBits == NULL)
2253 #endif /* DARWIN_SSL_PINNEDPUBKEY_V2 */
2255 pubkeylen = CFDataGetLength(publicKeyBits);
2256 pubkey = (unsigned char *)CFDataGetBytePtr(publicKeyBits);
2260 /* 4096 bit RSA pubkeylen == 526 */
2261 spkiHeader = rsa4096SpkiHeader;
2264 /* 2048 bit RSA pubkeylen == 270 */
2265 spkiHeader = rsa2048SpkiHeader;
2267 #ifdef DARWIN_SSL_PINNEDPUBKEY_V1
2269 /* ecDSA secp256r1 pubkeylen == 65 */
2270 spkiHeader = ecDsaSecp256r1SpkiHeader;
2271 spkiHeaderLength = 26;
2274 /* ecDSA secp384r1 pubkeylen == 97 */
2275 spkiHeader = ecDsaSecp384r1SpkiHeader;
2276 spkiHeaderLength = 23;
2279 infof(data, "SSL: unhandled public key length: %d\n", pubkeylen);
2280 #elif DARWIN_SSL_PINNEDPUBKEY_V2
2282 /* ecDSA secp256r1 pubkeylen == 91 header already included?
2283 * ecDSA secp384r1 header already included too
2284 * we assume rest of algorithms do same, so do nothing
2286 result = Curl_pin_peer_pubkey(data, pinnedpubkey, pubkey,
2288 #endif /* DARWIN_SSL_PINNEDPUBKEY_V2 */
2289 continue; /* break from loop */
2292 realpubkeylen = pubkeylen + spkiHeaderLength;
2293 realpubkey = malloc(realpubkeylen);
2297 memcpy(realpubkey, spkiHeader, spkiHeaderLength);
2298 memcpy(realpubkey + spkiHeaderLength, pubkey, pubkeylen);
2300 result = Curl_pin_peer_pubkey(data, pinnedpubkey, realpubkey,
2305 Curl_safefree(realpubkey);
2306 if(publicKeyBits != NULL)
2307 CFRelease(publicKeyBits);
2311 #endif /* DARWIN_SSL_PINNEDPUBKEY */
2314 darwinssl_connect_step2(struct connectdata *conn, int sockindex)
2316 struct Curl_easy *data = conn->data;
2317 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
2319 SSLCipherSuite cipher;
2320 SSLProtocol protocol = 0;
2321 const char * const hostname = SSL_IS_PROXY() ? conn->http_proxy.host.name :
2324 DEBUGASSERT(ssl_connect_2 == connssl->connecting_state
2325 || ssl_connect_2_reading == connssl->connecting_state
2326 || ssl_connect_2_writing == connssl->connecting_state);
2328 /* Here goes nothing: */
2329 err = SSLHandshake(BACKEND->ssl_ctx);
2333 case errSSLWouldBlock: /* they're not done with us yet */
2334 connssl->connecting_state = BACKEND->ssl_direction ?
2335 ssl_connect_2_writing : ssl_connect_2_reading;
2338 /* The below is errSSLServerAuthCompleted; it's not defined in
2339 Leopard's headers */
2341 if(SSL_CONN_CONFIG(CAfile) && SSL_CONN_CONFIG(verifypeer)) {
2342 int res = verify_cert(SSL_CONN_CONFIG(CAfile), data,
2347 /* the documentation says we need to call SSLHandshake() again */
2348 return darwinssl_connect_step2(conn, sockindex);
2350 /* These are all certificate problems with the server: */
2351 case errSSLXCertChainInvalid:
2352 failf(data, "SSL certificate problem: Invalid certificate chain");
2353 return CURLE_SSL_CACERT;
2354 case errSSLUnknownRootCert:
2355 failf(data, "SSL certificate problem: Untrusted root certificate");
2356 return CURLE_SSL_CACERT;
2357 case errSSLNoRootCert:
2358 failf(data, "SSL certificate problem: No root certificate");
2359 return CURLE_SSL_CACERT;
2360 case errSSLCertExpired:
2361 failf(data, "SSL certificate problem: Certificate chain had an "
2362 "expired certificate");
2363 return CURLE_SSL_CACERT;
2365 failf(data, "SSL certificate problem: Couldn't understand the server "
2366 "certificate format");
2367 return CURLE_SSL_CONNECT_ERROR;
2369 /* These are all certificate problems with the client: */
2370 case errSecAuthFailed:
2371 failf(data, "SSL authentication failed");
2372 return CURLE_SSL_CONNECT_ERROR;
2373 case errSSLPeerHandshakeFail:
2374 failf(data, "SSL peer handshake failed, the server most likely "
2375 "requires a client certificate to connect");
2376 return CURLE_SSL_CONNECT_ERROR;
2377 case errSSLPeerUnknownCA:
2378 failf(data, "SSL server rejected the client certificate due to "
2379 "the certificate being signed by an unknown certificate "
2381 return CURLE_SSL_CONNECT_ERROR;
2383 /* This error is raised if the server's cert didn't match the server's
2385 case errSSLHostNameMismatch:
2386 failf(data, "SSL certificate peer verification failed, the "
2387 "certificate did not match \"%s\"\n", conn->host.dispname);
2388 return CURLE_PEER_FAILED_VERIFICATION;
2390 /* Generic handshake errors: */
2391 case errSSLConnectionRefused:
2392 failf(data, "Server dropped the connection during the SSL handshake");
2393 return CURLE_SSL_CONNECT_ERROR;
2394 case errSSLClosedAbort:
2395 failf(data, "Server aborted the SSL handshake");
2396 return CURLE_SSL_CONNECT_ERROR;
2397 case errSSLNegotiation:
2398 failf(data, "Could not negotiate an SSL cipher suite with the server");
2399 return CURLE_SSL_CONNECT_ERROR;
2400 /* Sometimes paramErr happens with buggy ciphers: */
2401 case paramErr: case errSSLInternal:
2402 failf(data, "Internal SSL engine error encountered during the "
2404 return CURLE_SSL_CONNECT_ERROR;
2405 case errSSLFatalAlert:
2406 failf(data, "Fatal SSL engine error encountered during the SSL "
2408 return CURLE_SSL_CONNECT_ERROR;
2410 failf(data, "Unknown SSL protocol error in connection to %s:%d",
2412 return CURLE_SSL_CONNECT_ERROR;
2416 /* we have been connected fine, we're not waiting for anything else. */
2417 connssl->connecting_state = ssl_connect_3;
2419 #ifdef DARWIN_SSL_PINNEDPUBKEY
2420 if(data->set.str[STRING_SSL_PINNEDPUBLICKEY_ORIG]) {
2421 CURLcode result = pkp_pin_peer_pubkey(data, BACKEND->ssl_ctx,
2422 data->set.str[STRING_SSL_PINNEDPUBLICKEY_ORIG]);
2424 failf(data, "SSL: public key does not match pinned public key!");
2428 #endif /* DARWIN_SSL_PINNEDPUBKEY */
2430 /* Informational message */
2431 (void)SSLGetNegotiatedCipher(BACKEND->ssl_ctx, &cipher);
2432 (void)SSLGetNegotiatedProtocolVersion(BACKEND->ssl_ctx, &protocol);
2435 infof(data, "SSL 2.0 connection using %s\n",
2436 SSLCipherNameForNumber(cipher));
2439 infof(data, "SSL 3.0 connection using %s\n",
2440 SSLCipherNameForNumber(cipher));
2443 infof(data, "TLS 1.0 connection using %s\n",
2444 TLSCipherNameForNumber(cipher));
2446 #if CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS
2447 case kTLSProtocol11:
2448 infof(data, "TLS 1.1 connection using %s\n",
2449 TLSCipherNameForNumber(cipher));
2451 case kTLSProtocol12:
2452 infof(data, "TLS 1.2 connection using %s\n",
2453 TLSCipherNameForNumber(cipher));
2455 #endif /* CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS */
2456 #if CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11
2457 case kTLSProtocol13:
2458 infof(data, "TLS 1.3 connection using %s\n",
2459 TLSCipherNameForNumber(cipher));
2461 #endif /* CURL_BUILD_MAC_10_13 || CURL_BUILD_IOS_11 */
2463 infof(data, "Unknown protocol connection\n");
2471 #ifndef CURL_DISABLE_VERBOSE_STRINGS
2472 /* This should be called during step3 of the connection at the earliest */
2474 show_verbose_server_cert(struct connectdata *conn,
2477 struct Curl_easy *data = conn->data;
2478 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
2479 CFArrayRef server_certs = NULL;
2480 SecCertificateRef server_cert;
2483 SecTrustRef trust = NULL;
2485 if(!BACKEND->ssl_ctx)
2488 #if CURL_BUILD_MAC_10_7 || CURL_BUILD_IOS
2490 #pragma unused(server_certs)
2491 err = SSLCopyPeerTrust(BACKEND->ssl_ctx, &trust);
2492 /* For some reason, SSLCopyPeerTrust() can return noErr and yet return
2493 a null trust, so be on guard for that: */
2494 if(err == noErr && trust) {
2495 count = SecTrustGetCertificateCount(trust);
2496 for(i = 0L ; i < count ; i++) {
2499 server_cert = SecTrustGetCertificateAtIndex(trust, i);
2500 result = CopyCertSubject(data, server_cert, &certp);
2502 infof(data, "Server certificate: %s\n", certp);
2509 /* SSLCopyPeerCertificates() is deprecated as of Mountain Lion.
2510 The function SecTrustGetCertificateAtIndex() is officially present
2511 in Lion, but it is unfortunately also present in Snow Leopard as
2512 private API and doesn't work as expected. So we have to look for
2513 a different symbol to make sure this code is only executed under
2515 if(SecTrustEvaluateAsync != NULL) {
2516 #pragma unused(server_certs)
2517 err = SSLCopyPeerTrust(BACKEND->ssl_ctx, &trust);
2518 /* For some reason, SSLCopyPeerTrust() can return noErr and yet return
2519 a null trust, so be on guard for that: */
2520 if(err == noErr && trust) {
2521 count = SecTrustGetCertificateCount(trust);
2522 for(i = 0L ; i < count ; i++) {
2525 server_cert = SecTrustGetCertificateAtIndex(trust, i);
2526 result = CopyCertSubject(data, server_cert, &certp);
2528 infof(data, "Server certificate: %s\n", certp);
2536 #if CURL_SUPPORT_MAC_10_8
2537 err = SSLCopyPeerCertificates(BACKEND->ssl_ctx, &server_certs);
2538 /* Just in case SSLCopyPeerCertificates() returns null too... */
2539 if(err == noErr && server_certs) {
2540 count = CFArrayGetCount(server_certs);
2541 for(i = 0L ; i < count ; i++) {
2544 server_cert = (SecCertificateRef)CFArrayGetValueAtIndex(server_certs,
2546 result = CopyCertSubject(data, server_cert, &certp);
2548 infof(data, "Server certificate: %s\n", certp);
2552 CFRelease(server_certs);
2554 #endif /* CURL_SUPPORT_MAC_10_8 */
2556 #endif /* CURL_BUILD_IOS */
2558 #pragma unused(trust)
2559 err = SSLCopyPeerCertificates(BACKEND->ssl_ctx, &server_certs);
2561 count = CFArrayGetCount(server_certs);
2562 for(i = 0L ; i < count ; i++) {
2565 server_cert = (SecCertificateRef)CFArrayGetValueAtIndex(server_certs, i);
2566 result = CopyCertSubject(data, server_cert, &certp);
2568 infof(data, "Server certificate: %s\n", certp);
2572 CFRelease(server_certs);
2574 #endif /* CURL_BUILD_MAC_10_7 || CURL_BUILD_IOS */
2576 #endif /* !CURL_DISABLE_VERBOSE_STRINGS */
2579 darwinssl_connect_step3(struct connectdata *conn,
2582 struct Curl_easy *data = conn->data;
2583 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
2585 /* There is no step 3!
2586 * Well, okay, if verbose mode is on, let's print the details of the
2587 * server certificates. */
2588 #ifndef CURL_DISABLE_VERBOSE_STRINGS
2589 if(data->set.verbose)
2590 show_verbose_server_cert(conn, sockindex);
2593 connssl->connecting_state = ssl_connect_done;
2597 static Curl_recv darwinssl_recv;
2598 static Curl_send darwinssl_send;
2601 darwinssl_connect_common(struct connectdata *conn,
2607 struct Curl_easy *data = conn->data;
2608 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
2609 curl_socket_t sockfd = conn->sock[sockindex];
2613 /* check if the connection has already been established */
2614 if(ssl_connection_complete == connssl->state) {
2619 if(ssl_connect_1 == connssl->connecting_state) {
2620 /* Find out how much more time we're allowed */
2621 timeout_ms = Curl_timeleft(data, NULL, TRUE);
2623 if(timeout_ms < 0) {
2624 /* no need to continue if time already is up */
2625 failf(data, "SSL connection timeout");
2626 return CURLE_OPERATION_TIMEDOUT;
2629 result = darwinssl_connect_step1(conn, sockindex);
2634 while(ssl_connect_2 == connssl->connecting_state ||
2635 ssl_connect_2_reading == connssl->connecting_state ||
2636 ssl_connect_2_writing == connssl->connecting_state) {
2638 /* check allowed time left */
2639 timeout_ms = Curl_timeleft(data, NULL, TRUE);
2641 if(timeout_ms < 0) {
2642 /* no need to continue if time already is up */
2643 failf(data, "SSL connection timeout");
2644 return CURLE_OPERATION_TIMEDOUT;
2647 /* if ssl is expecting something, check if it's available. */
2648 if(connssl->connecting_state == ssl_connect_2_reading ||
2649 connssl->connecting_state == ssl_connect_2_writing) {
2651 curl_socket_t writefd = ssl_connect_2_writing ==
2652 connssl->connecting_state?sockfd:CURL_SOCKET_BAD;
2653 curl_socket_t readfd = ssl_connect_2_reading ==
2654 connssl->connecting_state?sockfd:CURL_SOCKET_BAD;
2656 what = Curl_socket_check(readfd, CURL_SOCKET_BAD, writefd,
2657 nonblocking?0:timeout_ms);
2660 failf(data, "select/poll on SSL socket, errno: %d", SOCKERRNO);
2661 return CURLE_SSL_CONNECT_ERROR;
2663 else if(0 == what) {
2670 failf(data, "SSL connection timeout");
2671 return CURLE_OPERATION_TIMEDOUT;
2674 /* socket is readable or writable */
2677 /* Run transaction, and return to the caller if it failed or if this
2678 * connection is done nonblocking and this loop would execute again. This
2679 * permits the owner of a multi handle to abort a connection attempt
2680 * before step2 has completed while ensuring that a client using select()
2681 * or epoll() will always have a valid fdset to wait on.
2683 result = darwinssl_connect_step2(conn, sockindex);
2684 if(result || (nonblocking &&
2685 (ssl_connect_2 == connssl->connecting_state ||
2686 ssl_connect_2_reading == connssl->connecting_state ||
2687 ssl_connect_2_writing == connssl->connecting_state)))
2690 } /* repeat step2 until all transactions are done. */
2693 if(ssl_connect_3 == connssl->connecting_state) {
2694 result = darwinssl_connect_step3(conn, sockindex);
2699 if(ssl_connect_done == connssl->connecting_state) {
2700 connssl->state = ssl_connection_complete;
2701 conn->recv[sockindex] = darwinssl_recv;
2702 conn->send[sockindex] = darwinssl_send;
2708 /* Reset our connect state machine */
2709 connssl->connecting_state = ssl_connect_1;
2714 static CURLcode Curl_darwinssl_connect_nonblocking(struct connectdata *conn,
2715 int sockindex, bool *done)
2717 return darwinssl_connect_common(conn, sockindex, TRUE, done);
2720 static CURLcode Curl_darwinssl_connect(struct connectdata *conn, int sockindex)
2725 result = darwinssl_connect_common(conn, sockindex, FALSE, &done);
2735 static void Curl_darwinssl_close(struct connectdata *conn, int sockindex)
2737 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
2739 if(BACKEND->ssl_ctx) {
2740 (void)SSLClose(BACKEND->ssl_ctx);
2741 #if CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS
2742 if(SSLCreateContext != NULL)
2743 CFRelease(BACKEND->ssl_ctx);
2744 #if CURL_SUPPORT_MAC_10_8
2746 (void)SSLDisposeContext(BACKEND->ssl_ctx);
2747 #endif /* CURL_SUPPORT_MAC_10_8 */
2749 (void)SSLDisposeContext(BACKEND->ssl_ctx);
2750 #endif /* CURL_BUILD_MAC_10_8 || CURL_BUILD_IOS */
2751 BACKEND->ssl_ctx = NULL;
2753 BACKEND->ssl_sockfd = 0;
2756 static int Curl_darwinssl_shutdown(struct connectdata *conn, int sockindex)
2758 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
2759 struct Curl_easy *data = conn->data;
2765 if(!BACKEND->ssl_ctx)
2768 if(data->set.ftp_ccc != CURLFTPSSL_CCC_ACTIVE)
2771 Curl_darwinssl_close(conn, sockindex);
2775 what = SOCKET_READABLE(conn->sock[sockindex], SSL_SHUTDOWN_TIMEOUT);
2779 /* anything that gets here is fatally bad */
2780 failf(data, "select/poll on SSL socket, errno: %d", SOCKERRNO);
2785 if(!what) { /* timeout */
2786 failf(data, "SSL shutdown timeout");
2790 /* Something to read, let's do it and hope that it is the close
2791 notify alert from the server. No way to SSL_Read now, so use read(). */
2793 nread = read(conn->sock[sockindex], buf, sizeof(buf));
2796 failf(data, "read: %s", strerror(errno));
2803 what = SOCKET_READABLE(conn->sock[sockindex], 0);
2809 static void Curl_darwinssl_session_free(void *ptr)
2811 /* ST, as of iOS 5 and Mountain Lion, has no public method of deleting a
2812 cached session ID inside the Security framework. There is a private
2813 function that does this, but I don't want to have to explain to you why I
2814 got your application rejected from the App Store due to the use of a
2815 private API, so the best we can do is free up our own char array that we
2816 created way back in darwinssl_connect_step1... */
2820 static size_t Curl_darwinssl_version(char *buffer, size_t size)
2822 return snprintf(buffer, size, "SecureTransport");
2826 * This function uses SSLGetSessionState to determine connection status.
2829 * 1 means the connection is still in place
2830 * 0 means the connection has been closed
2831 * -1 means the connection status is unknown
2833 static int Curl_darwinssl_check_cxn(struct connectdata *conn)
2835 struct ssl_connect_data *connssl = &conn->ssl[FIRSTSOCKET];
2837 SSLSessionState state;
2839 if(BACKEND->ssl_ctx) {
2840 err = SSLGetSessionState(BACKEND->ssl_ctx, &state);
2842 return state == kSSLConnected || state == kSSLHandshake;
2848 static bool Curl_darwinssl_data_pending(const struct connectdata *conn,
2851 const struct ssl_connect_data *connssl = &conn->ssl[connindex];
2855 if(BACKEND->ssl_ctx) { /* SSL is in use */
2856 err = SSLGetBufferedReadSize(BACKEND->ssl_ctx, &buffer);
2858 return buffer > 0UL;
2865 static CURLcode Curl_darwinssl_random(struct Curl_easy *data UNUSED_PARAM,
2866 unsigned char *entropy, size_t length)
2868 /* arc4random_buf() isn't available on cats older than Lion, so let's
2869 do this manually for the benefit of the older cats. */
2871 u_int32_t random_number = 0;
2875 for(i = 0 ; i < length ; i++) {
2876 if(i % sizeof(u_int32_t) == 0)
2877 random_number = arc4random();
2878 entropy[i] = random_number & 0xFF;
2879 random_number >>= 8;
2881 i = random_number = 0;
2885 static CURLcode Curl_darwinssl_md5sum(unsigned char *tmp, /* input */
2887 unsigned char *md5sum, /* output */
2891 (void)CC_MD5(tmp, (CC_LONG)tmplen, md5sum);
2895 static void Curl_darwinssl_sha256sum(const unsigned char *tmp, /* input */
2897 unsigned char *sha256sum, /* output */
2900 assert(sha256len >= CURL_SHA256_DIGEST_LENGTH);
2901 (void)CC_SHA256(tmp, (CC_LONG)tmplen, sha256sum);
2904 static bool Curl_darwinssl_false_start(void)
2906 #if CURL_BUILD_MAC_10_9 || CURL_BUILD_IOS_7
2907 if(SSLSetSessionOption != NULL)
2913 static ssize_t darwinssl_send(struct connectdata *conn,
2919 /*struct Curl_easy *data = conn->data;*/
2920 struct ssl_connect_data *connssl = &conn->ssl[sockindex];
2921 size_t processed = 0UL;
2924 /* The SSLWrite() function works a little differently than expected. The
2925 fourth argument (processed) is currently documented in Apple's
2926 documentation as: "On return, the length, in bytes, of the data actually
2929 Now, one could interpret that as "written to the socket," but actually,
2930 it returns the amount of data that was written to a buffer internal to
2931 the SSLContextRef instead. So it's possible for SSLWrite() to return
2932 errSSLWouldBlock and a number of bytes "written" because those bytes were
2933 encrypted and written to a buffer, not to the socket.
2935 So if this happens, then we need to keep calling SSLWrite() over and
2936 over again with no new data until it quits returning errSSLWouldBlock. */
2938 /* Do we have buffered data to write from the last time we were called? */
2939 if(BACKEND->ssl_write_buffered_length) {
2940 /* Write the buffered data: */
2941 err = SSLWrite(BACKEND->ssl_ctx, NULL, 0UL, &processed);
2944 /* processed is always going to be 0 because we didn't write to
2945 the buffer, so return how much was written to the socket */
2946 processed = BACKEND->ssl_write_buffered_length;
2947 BACKEND->ssl_write_buffered_length = 0UL;
2949 case errSSLWouldBlock: /* argh, try again */
2950 *curlcode = CURLE_AGAIN;
2953 failf(conn->data, "SSLWrite() returned error %d", err);
2954 *curlcode = CURLE_SEND_ERROR;
2959 /* We've got new data to write: */
2960 err = SSLWrite(BACKEND->ssl_ctx, mem, len, &processed);
2963 case errSSLWouldBlock:
2964 /* Data was buffered but not sent, we have to tell the caller
2965 to try sending again, and remember how much was buffered */
2966 BACKEND->ssl_write_buffered_length = len;
2967 *curlcode = CURLE_AGAIN;
2970 failf(conn->data, "SSLWrite() returned error %d", err);
2971 *curlcode = CURLE_SEND_ERROR;
2976 return (ssize_t)processed;
2979 static ssize_t darwinssl_recv(struct connectdata *conn,
2985 /*struct Curl_easy *data = conn->data;*/
2986 struct ssl_connect_data *connssl = &conn->ssl[num];
2987 size_t processed = 0UL;
2988 OSStatus err = SSLRead(BACKEND->ssl_ctx, buf, buffersize, &processed);
2992 case errSSLWouldBlock: /* return how much we read (if anything) */
2994 return (ssize_t)processed;
2995 *curlcode = CURLE_AGAIN;
2999 /* errSSLClosedGraceful - server gracefully shut down the SSL session
3000 errSSLClosedNoNotify - server hung up on us instead of sending a
3001 closure alert notice, read() is returning 0
3002 Either way, inform the caller that the server disconnected. */
3003 case errSSLClosedGraceful:
3004 case errSSLClosedNoNotify:
3005 *curlcode = CURLE_OK;
3010 failf(conn->data, "SSLRead() return error %d", err);
3011 *curlcode = CURLE_RECV_ERROR;
3016 return (ssize_t)processed;
3019 static void *Curl_darwinssl_get_internals(struct ssl_connect_data *connssl,
3020 CURLINFO info UNUSED_PARAM)
3023 return BACKEND->ssl_ctx;
3026 const struct Curl_ssl Curl_ssl_darwinssl = {
3027 { CURLSSLBACKEND_DARWINSSL, "darwinssl" }, /* info */
3029 0, /* have_ca_path */
3030 0, /* have_certinfo */
3031 #ifdef DARWIN_SSL_PINNEDPUBKEY
3032 1, /* have_pinnedpubkey */
3034 0, /* have_pinnedpubkey */
3035 #endif /* DARWIN_SSL_PINNEDPUBKEY */
3036 0, /* have_ssl_ctx */
3037 0, /* support_https_proxy */
3039 sizeof(struct ssl_backend_data),
3041 Curl_none_init, /* init */
3042 Curl_none_cleanup, /* cleanup */
3043 Curl_darwinssl_version, /* version */
3044 Curl_darwinssl_check_cxn, /* check_cxn */
3045 Curl_darwinssl_shutdown, /* shutdown */
3046 Curl_darwinssl_data_pending, /* data_pending */
3047 Curl_darwinssl_random, /* random */
3048 Curl_none_cert_status_request, /* cert_status_request */
3049 Curl_darwinssl_connect, /* connect */
3050 Curl_darwinssl_connect_nonblocking, /* connect_nonblocking */
3051 Curl_darwinssl_get_internals, /* get_internals */
3052 Curl_darwinssl_close, /* close_one */
3053 Curl_none_close_all, /* close_all */
3054 Curl_darwinssl_session_free, /* session_free */
3055 Curl_none_set_engine, /* set_engine */
3056 Curl_none_set_engine_default, /* set_engine_default */
3057 Curl_none_engines_list, /* engines_list */
3058 Curl_darwinssl_false_start, /* false_start */
3059 Curl_darwinssl_md5sum, /* md5sum */
3060 Curl_darwinssl_sha256sum /* sha256sum */
3064 #pragma clang diagnostic pop
3067 #endif /* USE_DARWINSSL */