Oops, forgot to hook CVE-2007-1218 fix into building.
[dragonfly.git] / contrib / hostapd-0.4.9 / tls_openssl.c
blob37878c7c206ebe8a42c269cb00f84c58fe9795da
1 /*
2 * WPA Supplicant / SSL/TLS interface functions for openssl
3 * Copyright (c) 2004-2006, Jouni Malinen <jkmaline@cc.hut.fi>
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 2 as
7 * published by the Free Software Foundation.
9 * Alternatively, this software may be distributed under the terms of BSD
10 * license.
12 * See README and COPYING for more details.
15 #include <stdlib.h>
16 #include <stdio.h>
17 #include <string.h>
19 #ifndef CONFIG_SMARTCARD
20 #ifndef OPENSSL_NO_ENGINE
21 #define OPENSSL_NO_ENGINE
22 #endif
23 #endif
25 #include <openssl/ssl.h>
26 #include <openssl/err.h>
27 #include <openssl/pkcs12.h>
28 #include <openssl/x509v3.h>
29 #ifndef OPENSSL_NO_ENGINE
30 #include <openssl/engine.h>
31 #endif /* OPENSSL_NO_ENGINE */
33 #include "common.h"
34 #include "tls.h"
36 #if OPENSSL_VERSION_NUMBER >= 0x0090800fL
37 #define OPENSSL_d2i_TYPE const unsigned char **
38 #else
39 #define OPENSSL_d2i_TYPE unsigned char **
40 #endif
42 static int tls_openssl_ref_count = 0;
44 struct tls_connection {
45 SSL *ssl;
46 BIO *ssl_in, *ssl_out;
47 #ifndef OPENSSL_NO_ENGINE
48 ENGINE *engine; /* functional reference to the engine */
49 EVP_PKEY *private_key; /* the private key if using engine */
50 #endif /* OPENSSL_NO_ENGINE */
51 char *subject_match, *altsubject_match;
52 int read_alerts, write_alerts, failed;
54 u8 *pre_shared_secret;
55 size_t pre_shared_secret_len;
59 #ifdef CONFIG_NO_STDOUT_DEBUG
61 static void _tls_show_errors(void)
63 unsigned long err;
65 while ((err = ERR_get_error())) {
66 /* Just ignore the errors, since stdout is disabled */
69 #define tls_show_errors(l, f, t) _tls_show_errors()
71 #else /* CONFIG_NO_STDOUT_DEBUG */
73 static void tls_show_errors(int level, const char *func, const char *txt)
75 unsigned long err;
77 wpa_printf(level, "OpenSSL: %s - %s %s",
78 func, txt, ERR_error_string(ERR_get_error(), NULL));
80 while ((err = ERR_get_error())) {
81 wpa_printf(MSG_INFO, "OpenSSL: pending error: %s",
82 ERR_error_string(err, NULL));
86 #endif /* CONFIG_NO_STDOUT_DEBUG */
89 #ifdef CONFIG_NATIVE_WINDOWS
91 /* Windows CryptoAPI and access to certificate stores */
92 #include <wincrypt.h>
94 #ifdef __MINGW32_VERSION
96 * MinGW does not yet include all the needed definitions for CryptoAPI, so
97 * define here whatever extra is needed.
99 #define CALG_SSL3_SHAMD5 (ALG_CLASS_HASH | ALG_TYPE_ANY | ALG_SID_SSL3SHAMD5)
100 #define CERT_SYSTEM_STORE_CURRENT_USER (1 << 16)
101 #define CERT_STORE_READONLY_FLAG 0x00008000
102 #define CERT_STORE_OPEN_EXISTING_FLAG 0x00004000
103 #define CRYPT_ACQUIRE_COMPARE_KEY_FLAG 0x00000004
105 static BOOL WINAPI
106 (*CryptAcquireCertificatePrivateKey)(PCCERT_CONTEXT pCert, DWORD dwFlags,
107 void *pvReserved, HCRYPTPROV *phCryptProv,
108 DWORD *pdwKeySpec, BOOL *pfCallerFreeProv)
109 = NULL; /* to be loaded from crypt32.dll */
111 static PCCERT_CONTEXT WINAPI
112 (*CertEnumCertificatesInStore)(HCERTSTORE hCertStore,
113 PCCERT_CONTEXT pPrevCertContext)
114 = NULL; /* to be loaded from crypt32.dll */
116 static int mingw_load_crypto_func(void)
118 HINSTANCE dll;
120 /* MinGW does not yet have full CryptoAPI support, so load the needed
121 * function here. */
123 if (CryptAcquireCertificatePrivateKey)
124 return 0;
126 dll = LoadLibrary("crypt32");
127 if (dll == NULL) {
128 wpa_printf(MSG_DEBUG, "CryptoAPI: Could not load crypt32 "
129 "library");
130 return -1;
133 CryptAcquireCertificatePrivateKey = GetProcAddress(
134 dll, "CryptAcquireCertificatePrivateKey");
135 if (CryptAcquireCertificatePrivateKey == NULL) {
136 wpa_printf(MSG_DEBUG, "CryptoAPI: Could not get "
137 "CryptAcquireCertificatePrivateKey() address from "
138 "crypt32 library");
139 return -1;
142 CertEnumCertificatesInStore = (void *) GetProcAddress(
143 dll, "CertEnumCertificatesInStore");
144 if (CertEnumCertificatesInStore == NULL) {
145 wpa_printf(MSG_DEBUG, "CryptoAPI: Could not get "
146 "CertEnumCertificatesInStore() address from "
147 "crypt32 library");
148 return -1;
151 return 0;
154 #else /* __MINGW32_VERSION */
156 static int mingw_load_crypto_func(void)
158 return 0;
161 #endif /* __MINGW32_VERSION */
164 struct cryptoapi_rsa_data {
165 const CERT_CONTEXT *cert;
166 HCRYPTPROV crypt_prov;
167 DWORD key_spec;
168 BOOL free_crypt_prov;
172 static void cryptoapi_error(const char *msg)
174 wpa_printf(MSG_INFO, "CryptoAPI: %s; err=%u",
175 msg, (unsigned int) GetLastError());
179 static int cryptoapi_rsa_pub_enc(int flen, const unsigned char *from,
180 unsigned char *to, RSA *rsa, int padding)
182 wpa_printf(MSG_DEBUG, "%s - not implemented", __func__);
183 return 0;
187 static int cryptoapi_rsa_pub_dec(int flen, const unsigned char *from,
188 unsigned char *to, RSA *rsa, int padding)
190 wpa_printf(MSG_DEBUG, "%s - not implemented", __func__);
191 return 0;
195 static int cryptoapi_rsa_priv_enc(int flen, const unsigned char *from,
196 unsigned char *to, RSA *rsa, int padding)
198 struct cryptoapi_rsa_data *priv =
199 (struct cryptoapi_rsa_data *) rsa->meth->app_data;
200 HCRYPTHASH hash;
201 DWORD hash_size, len, i;
202 unsigned char *buf = NULL;
203 int ret = 0;
205 if (priv == NULL) {
206 RSAerr(RSA_F_RSA_EAY_PRIVATE_ENCRYPT,
207 ERR_R_PASSED_NULL_PARAMETER);
208 return 0;
211 if (padding != RSA_PKCS1_PADDING) {
212 RSAerr(RSA_F_RSA_EAY_PRIVATE_ENCRYPT,
213 RSA_R_UNKNOWN_PADDING_TYPE);
214 return 0;
217 if (flen != 16 /* MD5 */ + 20 /* SHA-1 */) {
218 wpa_printf(MSG_INFO, "%s - only MD5-SHA1 hash supported",
219 __func__);
220 RSAerr(RSA_F_RSA_EAY_PRIVATE_ENCRYPT,
221 RSA_R_INVALID_MESSAGE_LENGTH);
222 return 0;
225 if (!CryptCreateHash(priv->crypt_prov, CALG_SSL3_SHAMD5, 0, 0, &hash))
227 cryptoapi_error("CryptCreateHash failed");
228 return 0;
231 len = sizeof(hash_size);
232 if (!CryptGetHashParam(hash, HP_HASHSIZE, (BYTE *) &hash_size, &len,
233 0)) {
234 cryptoapi_error("CryptGetHashParam failed");
235 goto err;
238 if (hash_size != flen) {
239 wpa_printf(MSG_INFO, "CryptoAPI: Invalid hash size (%u != %d)",
240 (unsigned) hash_size, flen);
241 RSAerr(RSA_F_RSA_EAY_PRIVATE_ENCRYPT,
242 RSA_R_INVALID_MESSAGE_LENGTH);
243 goto err;
245 if (!CryptSetHashParam(hash, HP_HASHVAL, (BYTE * ) from, 0)) {
246 cryptoapi_error("CryptSetHashParam failed");
247 goto err;
250 len = RSA_size(rsa);
251 buf = malloc(len);
252 if (buf == NULL) {
253 RSAerr(RSA_F_RSA_EAY_PRIVATE_ENCRYPT, ERR_R_MALLOC_FAILURE);
254 goto err;
257 if (!CryptSignHash(hash, priv->key_spec, NULL, 0, buf, &len)) {
258 cryptoapi_error("CryptSignHash failed");
259 goto err;
262 for (i = 0; i < len; i++)
263 to[i] = buf[len - i - 1];
264 ret = len;
266 err:
267 free(buf);
268 CryptDestroyHash(hash);
270 return ret;
274 static int cryptoapi_rsa_priv_dec(int flen, const unsigned char *from,
275 unsigned char *to, RSA *rsa, int padding)
277 wpa_printf(MSG_DEBUG, "%s - not implemented", __func__);
278 return 0;
282 static void cryptoapi_free_data(struct cryptoapi_rsa_data *priv)
284 if (priv == NULL)
285 return;
286 if (priv->crypt_prov && priv->free_crypt_prov)
287 CryptReleaseContext(priv->crypt_prov, 0);
288 if (priv->cert)
289 CertFreeCertificateContext(priv->cert);
290 free(priv);
294 static int cryptoapi_finish(RSA *rsa)
296 cryptoapi_free_data((struct cryptoapi_rsa_data *) rsa->meth->app_data);
297 free((void *) rsa->meth);
298 rsa->meth = NULL;
299 return 1;
303 static const CERT_CONTEXT * cryptoapi_find_cert(const char *name, DWORD store)
305 HCERTSTORE cs;
306 const CERT_CONTEXT *ret = NULL;
308 cs = CertOpenStore((LPCSTR) CERT_STORE_PROV_SYSTEM, 0, 0,
309 store | CERT_STORE_OPEN_EXISTING_FLAG |
310 CERT_STORE_READONLY_FLAG, L"MY");
311 if (cs == NULL) {
312 cryptoapi_error("Failed to open 'My system store'");
313 return NULL;
316 if (strncmp(name, "cert://", 7) == 0) {
317 unsigned short wbuf[255];
318 MultiByteToWideChar(CP_ACP, 0, name + 7, -1,
319 wbuf, sizeof(wbuf));
320 ret = CertFindCertificateInStore(cs, X509_ASN_ENCODING |
321 PKCS_7_ASN_ENCODING,
322 0, CERT_FIND_SUBJECT_STR,
323 wbuf, NULL);
324 } else if (strncmp(name, "hash://", 7) == 0) {
325 CRYPT_HASH_BLOB blob;
326 int len;
327 const char *hash = name + 7;
328 unsigned char *buf;
330 len = strlen(hash) / 2;
331 buf = malloc(len);
332 if (buf && hexstr2bin(hash, buf, len) == 0) {
333 blob.cbData = len;
334 blob.pbData = buf;
335 ret = CertFindCertificateInStore(cs,
336 X509_ASN_ENCODING |
337 PKCS_7_ASN_ENCODING,
338 0, CERT_FIND_HASH,
339 &blob, NULL);
341 free(buf);
344 CertCloseStore(cs, 0);
346 return ret;
350 static int tls_cryptoapi_cert(SSL *ssl, const char *name)
352 X509 *cert = NULL;
353 RSA *rsa = NULL, *pub_rsa;
354 struct cryptoapi_rsa_data *priv;
355 RSA_METHOD *rsa_meth;
357 if (name == NULL ||
358 (strncmp(name, "cert://", 7) != 0 &&
359 strncmp(name, "hash://", 7) != 0))
360 return -1;
362 priv = malloc(sizeof(*priv));
363 rsa_meth = malloc(sizeof(*rsa_meth));
364 if (priv == NULL || rsa_meth == NULL) {
365 wpa_printf(MSG_WARNING, "CryptoAPI: Failed to allocate memory "
366 "for CryptoAPI RSA method");
367 free(priv);
368 free(rsa_meth);
369 return -1;
371 memset(priv, 0, sizeof(*priv));
372 memset(rsa_meth, 0, sizeof(*rsa_meth));
374 priv->cert = cryptoapi_find_cert(name, CERT_SYSTEM_STORE_CURRENT_USER);
375 if (priv->cert == NULL) {
376 priv->cert = cryptoapi_find_cert(
377 name, CERT_SYSTEM_STORE_LOCAL_MACHINE);
379 if (priv->cert == NULL) {
380 wpa_printf(MSG_INFO, "CryptoAPI: Could not find certificate "
381 "'%s'", name);
382 goto err;
385 cert = d2i_X509(NULL, (OPENSSL_d2i_TYPE) &priv->cert->pbCertEncoded,
386 priv->cert->cbCertEncoded);
387 if (cert == NULL) {
388 wpa_printf(MSG_INFO, "CryptoAPI: Could not process X509 DER "
389 "encoding");
390 goto err;
393 if (mingw_load_crypto_func())
394 goto err;
396 if (!CryptAcquireCertificatePrivateKey(priv->cert,
397 CRYPT_ACQUIRE_COMPARE_KEY_FLAG,
398 NULL, &priv->crypt_prov,
399 &priv->key_spec,
400 &priv->free_crypt_prov)) {
401 cryptoapi_error("Failed to acquire a private key for the "
402 "certificate");
403 goto err;
406 rsa_meth->name = "Microsoft CryptoAPI RSA Method";
407 rsa_meth->rsa_pub_enc = cryptoapi_rsa_pub_enc;
408 rsa_meth->rsa_pub_dec = cryptoapi_rsa_pub_dec;
409 rsa_meth->rsa_priv_enc = cryptoapi_rsa_priv_enc;
410 rsa_meth->rsa_priv_dec = cryptoapi_rsa_priv_dec;
411 rsa_meth->finish = cryptoapi_finish;
412 rsa_meth->flags = RSA_METHOD_FLAG_NO_CHECK;
413 rsa_meth->app_data = (char *) priv;
415 rsa = RSA_new();
416 if (rsa == NULL) {
417 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_FILE,
418 ERR_R_MALLOC_FAILURE);
419 goto err;
422 if (!SSL_use_certificate(ssl, cert))
423 goto err;
424 pub_rsa = cert->cert_info->key->pkey->pkey.rsa;
425 X509_free(cert);
426 cert = NULL;
428 rsa->n = BN_dup(pub_rsa->n);
429 rsa->e = BN_dup(pub_rsa->e);
430 if (!RSA_set_method(rsa, rsa_meth))
431 goto err;
433 if (!SSL_use_RSAPrivateKey(ssl, rsa))
434 goto err;
435 RSA_free(rsa);
437 return 0;
439 err:
440 if (cert)
441 X509_free(cert);
442 if (rsa)
443 RSA_free(rsa);
444 else {
445 free(rsa_meth);
446 cryptoapi_free_data(priv);
448 return -1;
452 static int tls_cryptoapi_ca_cert(SSL_CTX *ssl_ctx, SSL *ssl, const char *name)
454 HCERTSTORE cs;
455 PCCERT_CONTEXT ctx = NULL;
456 X509 *cert;
457 char buf[128];
459 if (mingw_load_crypto_func())
460 return -1;
462 if (name == NULL || strncmp(name, "cert_store://", 13) != 0)
463 return -1;
465 cs = CertOpenSystemStore(0, name + 13);
466 if (cs == NULL) {
467 wpa_printf(MSG_DEBUG, "%s: failed to open system cert store "
468 "'%s': error=%d", __func__, name + 13,
469 (int) GetLastError());
470 return -1;
473 while ((ctx = CertEnumCertificatesInStore(cs, ctx))) {
474 cert = d2i_X509(NULL, (OPENSSL_d2i_TYPE) &ctx->pbCertEncoded,
475 ctx->cbCertEncoded);
476 if (cert == NULL) {
477 wpa_printf(MSG_INFO, "CryptoAPI: Could not process "
478 "X509 DER encoding for CA cert");
479 continue;
482 X509_NAME_oneline(X509_get_subject_name(cert), buf,
483 sizeof(buf));
484 wpa_printf(MSG_DEBUG, "OpenSSL: Loaded CA certificate for "
485 "system certificate store: subject='%s'", buf);
487 if (!X509_STORE_add_cert(ssl_ctx->cert_store, cert)) {
488 tls_show_errors(MSG_WARNING, __func__,
489 "Failed to add ca_cert to OpenSSL "
490 "certificate store");
493 X509_free(cert);
496 if (!CertCloseStore(cs, 0)) {
497 wpa_printf(MSG_DEBUG, "%s: failed to close system cert store "
498 "'%s': error=%d", __func__, name + 13,
499 (int) GetLastError());
502 return 0;
506 #else /* CONFIG_NATIVE_WINDOWS */
508 static int tls_cryptoapi_cert(SSL *ssl, const char *name)
510 return -1;
513 #endif /* CONFIG_NATIVE_WINDOWS */
516 static void ssl_info_cb(const SSL *ssl, int where, int ret)
518 const char *str;
519 int w;
521 wpa_printf(MSG_DEBUG, "SSL: (where=0x%x ret=0x%x)", where, ret);
522 w = where & ~SSL_ST_MASK;
523 if (w & SSL_ST_CONNECT)
524 str = "SSL_connect";
525 else if (w & SSL_ST_ACCEPT)
526 str = "SSL_accept";
527 else
528 str = "undefined";
530 if (where & SSL_CB_LOOP) {
531 wpa_printf(MSG_DEBUG, "SSL: %s:%s",
532 str, SSL_state_string_long(ssl));
533 } else if (where & SSL_CB_ALERT) {
534 wpa_printf(MSG_INFO, "SSL: SSL3 alert: %s:%s:%s",
535 where & SSL_CB_READ ?
536 "read (remote end reported an error)" :
537 "write (local SSL3 detected an error)",
538 SSL_alert_type_string_long(ret),
539 SSL_alert_desc_string_long(ret));
540 if ((ret >> 8) == SSL3_AL_FATAL) {
541 struct tls_connection *conn =
542 SSL_get_app_data((SSL *) ssl);
543 if (where & SSL_CB_READ)
544 conn->read_alerts++;
545 else
546 conn->write_alerts++;
548 } else if (where & SSL_CB_EXIT && ret <= 0) {
549 wpa_printf(MSG_DEBUG, "SSL: %s:%s in %s",
550 str, ret == 0 ? "failed" : "error",
551 SSL_state_string_long(ssl));
556 #ifndef OPENSSL_NO_ENGINE
558 * tls_engine_load_dynamic_generic - load any openssl engine
559 * @pre: an array of commands and values that load an engine initialized
560 * in the engine specific function
561 * @post: an array of commands and values that initialize an already loaded
562 * engine (or %NULL if not required)
563 * @id: the engine id of the engine to load (only required if post is not %NULL
565 * This function is a generic function that loads any openssl engine.
567 * Returns: 0 on success, -1 on failure
569 static int tls_engine_load_dynamic_generic(const char *pre[],
570 const char *post[], const char *id)
572 ENGINE *engine;
573 const char *dynamic_id = "dynamic";
575 engine = ENGINE_by_id(id);
576 if (engine) {
577 ENGINE_free(engine);
578 wpa_printf(MSG_DEBUG, "ENGINE: engine '%s' is already "
579 "available", id);
580 return 0;
582 ERR_clear_error();
584 engine = ENGINE_by_id(dynamic_id);
585 if (engine == NULL) {
586 wpa_printf(MSG_INFO, "ENGINE: Can't find engine %s [%s]",
587 dynamic_id,
588 ERR_error_string(ERR_get_error(), NULL));
589 return -1;
592 /* Perform the pre commands. This will load the engine. */
593 while (pre && pre[0]) {
594 wpa_printf(MSG_DEBUG, "ENGINE: '%s' '%s'", pre[0], pre[1]);
595 if (ENGINE_ctrl_cmd_string(engine, pre[0], pre[1], 0) == 0) {
596 wpa_printf(MSG_INFO, "ENGINE: ctrl cmd_string failed: "
597 "%s %s [%s]", pre[0], pre[1],
598 ERR_error_string(ERR_get_error(), NULL));
599 ENGINE_free(engine);
600 return -1;
602 pre += 2;
606 * Free the reference to the "dynamic" engine. The loaded engine can
607 * now be looked up using ENGINE_by_id().
609 ENGINE_free(engine);
611 engine = ENGINE_by_id(id);
612 if (engine == NULL) {
613 wpa_printf(MSG_INFO, "ENGINE: Can't find engine %s [%s]",
614 id, ERR_error_string(ERR_get_error(), NULL));
615 return -1;
618 while (post && post[0]) {
619 wpa_printf(MSG_DEBUG, "ENGINE: '%s' '%s'", post[0], post[1]);
620 if (ENGINE_ctrl_cmd_string(engine, post[0], post[1], 0) == 0) {
621 wpa_printf(MSG_DEBUG, "ENGINE: ctrl cmd_string failed:"
622 " %s %s [%s]", post[0], post[1],
623 ERR_error_string(ERR_get_error(), NULL));
624 ENGINE_remove(engine);
625 ENGINE_free(engine);
626 return -1;
628 post += 2;
630 ENGINE_free(engine);
632 return 0;
637 * tls_engine_load_dynamic_pkcs11 - load the pkcs11 engine provided by opensc
638 * @pkcs11_so_path: pksc11_so_path from the configuration
639 * @pcks11_module_path: pkcs11_module_path from the configuration
641 static int tls_engine_load_dynamic_pkcs11(const char *pkcs11_so_path,
642 const char *pkcs11_module_path)
644 char *engine_id = "pkcs11";
645 const char *pre_cmd[] = {
646 "SO_PATH", pkcs11_so_path,
647 "ID", engine_id,
648 "LIST_ADD", "1",
649 /* "NO_VCHECK", "1", */
650 "LOAD", NULL,
651 NULL, NULL
653 const char *post_cmd[] = {
654 "MODULE_PATH", pkcs11_module_path,
655 NULL, NULL
658 if (!pkcs11_so_path || !pkcs11_module_path)
659 return 0;
661 wpa_printf(MSG_DEBUG, "ENGINE: Loading pkcs11 Engine from %s",
662 pkcs11_so_path);
664 return tls_engine_load_dynamic_generic(pre_cmd, post_cmd, engine_id);
669 * tls_engine_load_dynamic_opensc - load the opensc engine provided by opensc
670 * @opensc_so_path: opensc_so_path from the configuration
672 static int tls_engine_load_dynamic_opensc(const char *opensc_so_path)
674 char *engine_id = "opensc";
675 const char *pre_cmd[] = {
676 "SO_PATH", opensc_so_path,
677 "ID", engine_id,
678 "LIST_ADD", "1",
679 "LOAD", NULL,
680 NULL, NULL
683 if (!opensc_so_path)
684 return 0;
686 wpa_printf(MSG_DEBUG, "ENGINE: Loading OpenSC Engine from %s",
687 opensc_so_path);
689 return tls_engine_load_dynamic_generic(pre_cmd, NULL, engine_id);
691 #endif /* OPENSSL_NO_ENGINE */
694 void * tls_init(const struct tls_config *conf)
696 SSL_CTX *ssl;
698 if (tls_openssl_ref_count == 0) {
699 SSL_load_error_strings();
700 SSL_library_init();
701 /* TODO: if /dev/urandom is available, PRNG is seeded
702 * automatically. If this is not the case, random data should
703 * be added here. */
705 #ifdef PKCS12_FUNCS
706 PKCS12_PBE_add();
707 #endif /* PKCS12_FUNCS */
709 tls_openssl_ref_count++;
711 ssl = SSL_CTX_new(TLSv1_method());
712 if (ssl == NULL)
713 return NULL;
715 SSL_CTX_set_info_callback(ssl, ssl_info_cb);
717 #ifndef OPENSSL_NO_ENGINE
718 if (conf &&
719 (conf->opensc_engine_path || conf->pkcs11_engine_path ||
720 conf->pkcs11_module_path)) {
721 wpa_printf(MSG_DEBUG, "ENGINE: Loading dynamic engine");
722 ERR_load_ENGINE_strings();
723 ENGINE_load_dynamic();
725 if (tls_engine_load_dynamic_opensc(conf->opensc_engine_path) ||
726 tls_engine_load_dynamic_pkcs11(conf->pkcs11_engine_path,
727 conf->pkcs11_module_path)) {
728 tls_deinit(ssl);
729 return NULL;
732 #endif /* OPENSSL_NO_ENGINE */
734 return ssl;
738 void tls_deinit(void *ssl_ctx)
740 SSL_CTX *ssl = ssl_ctx;
741 SSL_CTX_free(ssl);
743 tls_openssl_ref_count--;
744 if (tls_openssl_ref_count == 0) {
745 #ifndef OPENSSL_NO_ENGINE
746 ENGINE_cleanup();
747 #endif /* OPENSSL_NO_ENGINE */
748 ERR_free_strings();
749 EVP_cleanup();
754 static int tls_engine_init(struct tls_connection *conn, const char *engine_id,
755 const char *pin, const char *key_id)
757 #ifndef OPENSSL_NO_ENGINE
758 int ret = -1;
759 if (engine_id == NULL) {
760 wpa_printf(MSG_ERROR, "ENGINE: Engine ID not set");
761 return -1;
763 if (pin == NULL) {
764 wpa_printf(MSG_ERROR, "ENGINE: Smartcard PIN not set");
765 return -1;
767 if (key_id == NULL) {
768 wpa_printf(MSG_ERROR, "ENGINE: Key Id not set");
769 return -1;
772 ERR_clear_error();
773 conn->engine = ENGINE_by_id(engine_id);
774 if (!conn->engine) {
775 wpa_printf(MSG_ERROR, "ENGINE: engine %s not available [%s]",
776 engine_id, ERR_error_string(ERR_get_error(), NULL));
777 goto err;
779 if (ENGINE_init(conn->engine) != 1) {
780 wpa_printf(MSG_ERROR, "ENGINE: engine init failed "
781 "(engine: %s) [%s]", engine_id,
782 ERR_error_string(ERR_get_error(), NULL));
783 goto err;
785 wpa_printf(MSG_DEBUG, "ENGINE: engine initialized");
787 if (ENGINE_ctrl_cmd_string(conn->engine, "PIN", pin, 0) == 0) {
788 wpa_printf(MSG_ERROR, "ENGINE: cannot set pin [%s]",
789 ERR_error_string(ERR_get_error(), NULL));
790 goto err;
792 conn->private_key = ENGINE_load_private_key(conn->engine,
793 key_id, NULL, NULL);
794 if (!conn->private_key) {
795 wpa_printf(MSG_ERROR, "ENGINE: cannot load private key with id"
796 " '%s' [%s]", key_id,
797 ERR_error_string(ERR_get_error(), NULL));
798 ret = TLS_SET_PARAMS_ENGINE_PRV_INIT_FAILED;
799 goto err;
801 return 0;
803 err:
804 if (conn->engine) {
805 ENGINE_free(conn->engine);
806 conn->engine = NULL;
809 if (conn->private_key) {
810 EVP_PKEY_free(conn->private_key);
811 conn->private_key = NULL;
814 return ret;
815 #else /* OPENSSL_NO_ENGINE */
816 return 0;
817 #endif /* OPENSSL_NO_ENGINE */
821 static void tls_engine_deinit(struct tls_connection *conn)
823 #ifndef OPENSSL_NO_ENGINE
824 wpa_printf(MSG_DEBUG, "ENGINE: engine deinit");
825 if (conn->private_key) {
826 EVP_PKEY_free(conn->private_key);
827 conn->private_key = NULL;
829 if (conn->engine) {
830 ENGINE_finish(conn->engine);
831 conn->engine = NULL;
833 #endif /* OPENSSL_NO_ENGINE */
837 int tls_get_errors(void *ssl_ctx)
839 int count = 0;
840 unsigned long err;
842 while ((err = ERR_get_error())) {
843 wpa_printf(MSG_INFO, "TLS - SSL error: %s",
844 ERR_error_string(err, NULL));
845 count++;
848 return count;
851 struct tls_connection * tls_connection_init(void *ssl_ctx)
853 SSL_CTX *ssl = ssl_ctx;
854 struct tls_connection *conn;
856 conn = malloc(sizeof(*conn));
857 if (conn == NULL)
858 return NULL;
859 memset(conn, 0, sizeof(*conn));
860 conn->ssl = SSL_new(ssl);
861 if (conn->ssl == NULL) {
862 tls_show_errors(MSG_INFO, __func__,
863 "Failed to initialize new SSL connection");
864 free(conn);
865 return NULL;
868 SSL_set_app_data(conn->ssl, conn);
869 SSL_set_options(conn->ssl,
870 SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3 |
871 SSL_OP_SINGLE_DH_USE);
873 conn->ssl_in = BIO_new(BIO_s_mem());
874 if (!conn->ssl_in) {
875 tls_show_errors(MSG_INFO, __func__,
876 "Failed to create a new BIO for ssl_in");
877 SSL_free(conn->ssl);
878 free(conn);
879 return NULL;
882 conn->ssl_out = BIO_new(BIO_s_mem());
883 if (!conn->ssl_out) {
884 tls_show_errors(MSG_INFO, __func__,
885 "Failed to create a new BIO for ssl_out");
886 SSL_free(conn->ssl);
887 BIO_free(conn->ssl_in);
888 free(conn);
889 return NULL;
892 SSL_set_bio(conn->ssl, conn->ssl_in, conn->ssl_out);
894 return conn;
898 void tls_connection_deinit(void *ssl_ctx, struct tls_connection *conn)
900 if (conn == NULL)
901 return;
902 free(conn->pre_shared_secret);
903 SSL_free(conn->ssl);
904 tls_engine_deinit(conn);
905 free(conn->subject_match);
906 free(conn->altsubject_match);
907 free(conn);
911 int tls_connection_established(void *ssl_ctx, struct tls_connection *conn)
913 return conn ? SSL_is_init_finished(conn->ssl) : 0;
917 int tls_connection_shutdown(void *ssl_ctx, struct tls_connection *conn)
919 if (conn == NULL)
920 return -1;
922 /* Shutdown previous TLS connection without notifying the peer
923 * because the connection was already terminated in practice
924 * and "close notify" shutdown alert would confuse AS. */
925 SSL_set_quiet_shutdown(conn->ssl, 1);
926 SSL_shutdown(conn->ssl);
927 return 0;
931 static int tls_match_altsubject(X509 *cert, const char *match)
933 GENERAL_NAME *gen;
934 char *field, *tmp;
935 void *ext;
936 int i, found = 0;
937 size_t len;
939 ext = X509_get_ext_d2i(cert, NID_subject_alt_name, NULL, NULL);
941 for (i = 0; ext && i < sk_GENERAL_NAME_num(ext); i++) {
942 gen = sk_GENERAL_NAME_value(ext, i);
943 switch (gen->type) {
944 case GEN_EMAIL:
945 field = "EMAIL";
946 break;
947 case GEN_DNS:
948 field = "DNS";
949 break;
950 case GEN_URI:
951 field = "URI";
952 break;
953 default:
954 field = NULL;
955 wpa_printf(MSG_DEBUG, "TLS: altSubjectName: "
956 "unsupported type=%d", gen->type);
957 break;
960 if (!field)
961 continue;
963 wpa_printf(MSG_DEBUG, "TLS: altSubjectName: %s:%s",
964 field, gen->d.ia5->data);
965 len = strlen(field) + 1 + strlen((char *) gen->d.ia5->data) +
967 tmp = malloc(len);
968 if (tmp == NULL)
969 continue;
970 snprintf(tmp, len, "%s:%s", field, gen->d.ia5->data);
971 if (strstr(tmp, match))
972 found++;
973 free(tmp);
976 return found;
980 static int tls_verify_cb(int preverify_ok, X509_STORE_CTX *x509_ctx)
982 char buf[256];
983 X509 *err_cert;
984 int err, depth;
985 SSL *ssl;
986 struct tls_connection *conn;
987 char *match, *altmatch;
989 err_cert = X509_STORE_CTX_get_current_cert(x509_ctx);
990 err = X509_STORE_CTX_get_error(x509_ctx);
991 depth = X509_STORE_CTX_get_error_depth(x509_ctx);
992 ssl = X509_STORE_CTX_get_ex_data(x509_ctx,
993 SSL_get_ex_data_X509_STORE_CTX_idx());
994 X509_NAME_oneline(X509_get_subject_name(err_cert), buf, sizeof(buf));
996 conn = SSL_get_app_data(ssl);
997 match = conn ? conn->subject_match : NULL;
998 altmatch = conn ? conn->altsubject_match : NULL;
1000 if (!preverify_ok) {
1001 wpa_printf(MSG_WARNING, "TLS: Certificate verification failed,"
1002 " error %d (%s) depth %d for '%s'", err,
1003 X509_verify_cert_error_string(err), depth, buf);
1004 } else {
1005 wpa_printf(MSG_DEBUG, "TLS: tls_verify_cb - "
1006 "preverify_ok=%d err=%d (%s) depth=%d buf='%s'",
1007 preverify_ok, err,
1008 X509_verify_cert_error_string(err), depth, buf);
1009 if (depth == 0 && match && strstr(buf, match) == NULL) {
1010 wpa_printf(MSG_WARNING, "TLS: Subject '%s' did not "
1011 "match with '%s'", buf, match);
1012 preverify_ok = 0;
1013 } else if (depth == 0 && altmatch &&
1014 !tls_match_altsubject(err_cert, altmatch)) {
1015 wpa_printf(MSG_WARNING, "TLS: altSubjectName match "
1016 "'%s' not found", altmatch);
1017 preverify_ok = 0;
1021 return preverify_ok;
1025 #ifndef OPENSSL_NO_STDIO
1026 static int tls_load_ca_der(void *_ssl_ctx, const char *ca_cert)
1028 SSL_CTX *ssl_ctx = _ssl_ctx;
1029 X509_LOOKUP *lookup;
1030 int ret = 0;
1032 lookup = X509_STORE_add_lookup(ssl_ctx->cert_store,
1033 X509_LOOKUP_file());
1034 if (lookup == NULL) {
1035 tls_show_errors(MSG_WARNING, __func__,
1036 "Failed add lookup for X509 store");
1037 return -1;
1040 if (!X509_LOOKUP_load_file(lookup, ca_cert, X509_FILETYPE_ASN1)) {
1041 unsigned long err = ERR_peek_error();
1042 tls_show_errors(MSG_WARNING, __func__,
1043 "Failed load CA in DER format");
1044 if (ERR_GET_LIB(err) == ERR_LIB_X509 &&
1045 ERR_GET_REASON(err) == X509_R_CERT_ALREADY_IN_HASH_TABLE) {
1046 wpa_printf(MSG_DEBUG, "OpenSSL: %s - ignoring "
1047 "cert already in hash table error",
1048 __func__);
1049 } else
1050 ret = -1;
1053 return ret;
1055 #endif /* OPENSSL_NO_STDIO */
1058 static int tls_connection_ca_cert(void *_ssl_ctx, struct tls_connection *conn,
1059 const char *ca_cert, const u8 *ca_cert_blob,
1060 size_t ca_cert_blob_len, const char *ca_path)
1062 SSL_CTX *ssl_ctx = _ssl_ctx;
1064 if (ca_cert_blob) {
1065 X509 *cert = d2i_X509(NULL, (OPENSSL_d2i_TYPE) &ca_cert_blob,
1066 ca_cert_blob_len);
1067 if (cert == NULL) {
1068 tls_show_errors(MSG_WARNING, __func__,
1069 "Failed to parse ca_cert_blob");
1070 return -1;
1073 if (!X509_STORE_add_cert(ssl_ctx->cert_store, cert)) {
1074 tls_show_errors(MSG_WARNING, __func__,
1075 "Failed to add ca_cert_blob to "
1076 "certificate store");
1077 X509_free(cert);
1078 return -1;
1080 X509_free(cert);
1081 wpa_printf(MSG_DEBUG, "OpenSSL: %s - added ca_cert_blob "
1082 "to certificate store", __func__);
1083 SSL_set_verify(conn->ssl, SSL_VERIFY_PEER, tls_verify_cb);
1084 return 0;
1087 #ifdef CONFIG_NATIVE_WINDOWS
1088 if (ca_cert && tls_cryptoapi_ca_cert(ssl_ctx, conn->ssl, ca_cert) ==
1089 0) {
1090 wpa_printf(MSG_DEBUG, "OpenSSL: Added CA certificates from "
1091 "system certificate store");
1092 SSL_set_verify(conn->ssl, SSL_VERIFY_PEER, tls_verify_cb);
1093 return 0;
1095 #endif /* CONFIG_NATIVE_WINDOWS */
1097 if (ca_cert || ca_path) {
1098 #ifndef OPENSSL_NO_STDIO
1099 if (SSL_CTX_load_verify_locations(ssl_ctx, ca_cert, ca_path) !=
1100 1) {
1101 tls_show_errors(MSG_WARNING, __func__,
1102 "Failed to load root certificates");
1103 if (ca_cert &&
1104 tls_load_ca_der(ssl_ctx, ca_cert) == 0) {
1105 wpa_printf(MSG_DEBUG, "OpenSSL: %s - loaded "
1106 "DER format CA certificate",
1107 __func__);
1108 } else
1109 return -1;
1110 } else {
1111 wpa_printf(MSG_DEBUG, "TLS: Trusted root "
1112 "certificate(s) loaded");
1113 tls_get_errors(ssl_ctx);
1115 SSL_set_verify(conn->ssl, SSL_VERIFY_PEER, tls_verify_cb);
1116 #else /* OPENSSL_NO_STDIO */
1117 wpa_printf(MSG_DEBUG, "OpenSSL: %s - OPENSSL_NO_STDIO",
1118 __func__);
1119 return -1;
1120 #endif /* OPENSSL_NO_STDIO */
1121 } else {
1122 /* No ca_cert configured - do not try to verify server
1123 * certificate */
1124 SSL_set_verify(conn->ssl, SSL_VERIFY_NONE, NULL);
1127 return 0;
1131 int tls_global_ca_cert(void *_ssl_ctx, const char *ca_cert)
1133 SSL_CTX *ssl_ctx = _ssl_ctx;
1134 if (ca_cert) {
1135 if (SSL_CTX_load_verify_locations(ssl_ctx, ca_cert, NULL) != 1)
1137 tls_show_errors(MSG_WARNING, __func__,
1138 "Failed to load root certificates");
1139 return -1;
1142 wpa_printf(MSG_DEBUG, "TLS: Trusted root "
1143 "certificate(s) loaded");
1145 #ifndef OPENSSL_NO_STDIO
1146 /* Add the same CAs to the client certificate requests */
1147 SSL_CTX_set_client_CA_list(ssl_ctx,
1148 SSL_load_client_CA_file(ca_cert));
1149 #endif /* OPENSSL_NO_STDIO */
1152 return 0;
1156 int tls_global_set_verify(void *ssl_ctx, int check_crl)
1158 int flags;
1160 if (check_crl) {
1161 X509_STORE *cs = SSL_CTX_get_cert_store(ssl_ctx);
1162 if (cs == NULL) {
1163 tls_show_errors(MSG_INFO, __func__, "Failed to get "
1164 "certificate store when enabling "
1165 "check_crl");
1166 return -1;
1168 flags = X509_V_FLAG_CRL_CHECK;
1169 if (check_crl == 2)
1170 flags |= X509_V_FLAG_CRL_CHECK_ALL;
1171 X509_STORE_set_flags(cs, flags);
1173 return 0;
1177 static int tls_connection_set_subject_match(void *ssl_ctx,
1178 struct tls_connection *conn,
1179 const char *subject_match,
1180 const char *altsubject_match)
1182 free(conn->subject_match);
1183 conn->subject_match = NULL;
1184 if (subject_match) {
1185 conn->subject_match = strdup(subject_match);
1186 if (conn->subject_match == NULL)
1187 return -1;
1190 free(conn->altsubject_match);
1191 conn->altsubject_match = NULL;
1192 if (altsubject_match) {
1193 conn->altsubject_match = strdup(altsubject_match);
1194 if (conn->altsubject_match == NULL)
1195 return -1;
1198 return 0;
1202 int tls_connection_set_verify(void *ssl_ctx, struct tls_connection *conn,
1203 int verify_peer)
1205 if (conn == NULL)
1206 return -1;
1208 if (verify_peer) {
1209 SSL_set_verify(conn->ssl, SSL_VERIFY_PEER |
1210 SSL_VERIFY_FAIL_IF_NO_PEER_CERT |
1211 SSL_VERIFY_CLIENT_ONCE, tls_verify_cb);
1212 } else {
1213 SSL_set_verify(conn->ssl, SSL_VERIFY_NONE, NULL);
1216 SSL_set_accept_state(conn->ssl);
1218 return 0;
1222 static int tls_connection_client_cert(void *ssl_ctx,
1223 struct tls_connection *conn,
1224 const char *client_cert,
1225 const u8 *client_cert_blob,
1226 size_t client_cert_blob_len)
1228 if (client_cert == NULL && client_cert_blob == NULL)
1229 return 0;
1231 if (client_cert_blob &&
1232 SSL_use_certificate_ASN1(conn->ssl, (u8 *) client_cert_blob,
1233 client_cert_blob_len) == 1) {
1234 wpa_printf(MSG_DEBUG, "OpenSSL: SSL_use_certificate_ASN1 --> "
1235 "OK");
1236 return 0;
1237 } else if (client_cert_blob) {
1238 tls_show_errors(MSG_DEBUG, __func__,
1239 "SSL_use_certificate_ASN1 failed");
1242 if (client_cert == NULL)
1243 return -1;
1245 #ifndef OPENSSL_NO_STDIO
1246 if (SSL_use_certificate_file(conn->ssl, client_cert,
1247 SSL_FILETYPE_ASN1) == 1) {
1248 wpa_printf(MSG_DEBUG, "OpenSSL: SSL_use_certificate_file (DER)"
1249 " --> OK");
1250 return 0;
1251 } else {
1252 tls_show_errors(MSG_DEBUG, __func__,
1253 "SSL_use_certificate_file (DER) failed");
1256 if (SSL_use_certificate_file(conn->ssl, client_cert,
1257 SSL_FILETYPE_PEM) == 1) {
1258 wpa_printf(MSG_DEBUG, "OpenSSL: SSL_use_certificate_file (PEM)"
1259 " --> OK");
1260 return 0;
1261 } else {
1262 tls_show_errors(MSG_DEBUG, __func__,
1263 "SSL_use_certificate_file (PEM) failed");
1265 #else /* OPENSSL_NO_STDIO */
1266 wpa_printf(MSG_DEBUG, "OpenSSL: %s - OPENSSL_NO_STDIO", __func__);
1267 #endif /* OPENSSL_NO_STDIO */
1269 return -1;
1273 int tls_global_client_cert(void *_ssl_ctx, const char *client_cert)
1275 #ifndef OPENSSL_NO_STDIO
1276 SSL_CTX *ssl_ctx = _ssl_ctx;
1277 if (client_cert == NULL)
1278 return 0;
1280 if (SSL_CTX_use_certificate_file(ssl_ctx, client_cert,
1281 SSL_FILETYPE_ASN1) != 1 &&
1282 SSL_CTX_use_certificate_file(ssl_ctx, client_cert,
1283 SSL_FILETYPE_PEM) != 1) {
1284 tls_show_errors(MSG_INFO, __func__,
1285 "Failed to load client certificate");
1286 return -1;
1288 return 0;
1289 #else /* OPENSSL_NO_STDIO */
1290 if (client_cert == NULL)
1291 return 0;
1292 wpa_printf(MSG_DEBUG, "OpenSSL: %s - OPENSSL_NO_STDIO", __func__);
1293 return -1;
1294 #endif /* OPENSSL_NO_STDIO */
1298 static int tls_passwd_cb(char *buf, int size, int rwflag, void *password)
1300 if (password == NULL) {
1301 return 0;
1303 strncpy(buf, (char *) password, size);
1304 buf[size - 1] = '\0';
1305 return strlen(buf);
1309 #ifdef PKCS12_FUNCS
1310 static int tls_parse_pkcs12(SSL_CTX *ssl_ctx, SSL *ssl, PKCS12 *p12,
1311 const char *passwd)
1313 EVP_PKEY *pkey;
1314 X509 *cert;
1315 STACK_OF(X509) *certs;
1316 int res = 0;
1317 char buf[256];
1319 pkey = NULL;
1320 cert = NULL;
1321 certs = NULL;
1322 if (!PKCS12_parse(p12, passwd, &pkey, &cert, &certs)) {
1323 tls_show_errors(MSG_DEBUG, __func__,
1324 "Failed to parse PKCS12 file");
1325 PKCS12_free(p12);
1326 return -1;
1328 wpa_printf(MSG_DEBUG, "TLS: Successfully parsed PKCS12 data");
1330 if (cert) {
1331 X509_NAME_oneline(X509_get_subject_name(cert), buf,
1332 sizeof(buf));
1333 wpa_printf(MSG_DEBUG, "TLS: Got certificate from PKCS12: "
1334 "subject='%s'", buf);
1335 if (ssl) {
1336 if (SSL_use_certificate(ssl, cert) != 1)
1337 res = -1;
1338 } else {
1339 if (SSL_CTX_use_certificate(ssl_ctx, cert) != 1)
1340 res = -1;
1342 X509_free(cert);
1345 if (pkey) {
1346 wpa_printf(MSG_DEBUG, "TLS: Got private key from PKCS12");
1347 if (ssl) {
1348 if (SSL_use_PrivateKey(ssl, pkey) != 1)
1349 res = -1;
1350 } else {
1351 if (SSL_CTX_use_PrivateKey(ssl_ctx, pkey) != 1)
1352 res = -1;
1354 EVP_PKEY_free(pkey);
1357 if (certs) {
1358 while ((cert = sk_X509_pop(certs)) != NULL) {
1359 X509_NAME_oneline(X509_get_subject_name(cert), buf,
1360 sizeof(buf));
1361 wpa_printf(MSG_DEBUG, "TLS: additional certificate"
1362 " from PKCS12: subject='%s'", buf);
1364 * There is no SSL equivalent for the chain cert - so
1365 * always add it to the context...
1367 if (SSL_CTX_add_extra_chain_cert(ssl_ctx, cert) != 1) {
1368 res = -1;
1369 break;
1372 sk_X509_free(certs);
1375 PKCS12_free(p12);
1377 if (res < 0)
1378 tls_get_errors(ssl_ctx);
1380 return res;
1382 #endif /* PKCS12_FUNCS */
1385 static int tls_read_pkcs12(SSL_CTX *ssl_ctx, SSL *ssl, const char *private_key,
1386 const char *passwd)
1388 #ifdef PKCS12_FUNCS
1389 FILE *f;
1390 PKCS12 *p12;
1392 f = fopen(private_key, "r");
1393 if (f == NULL)
1394 return -1;
1396 p12 = d2i_PKCS12_fp(f, NULL);
1397 fclose(f);
1399 if (p12 == NULL) {
1400 tls_show_errors(MSG_INFO, __func__,
1401 "Failed to use PKCS#12 file");
1402 return -1;
1405 return tls_parse_pkcs12(ssl_ctx, ssl, p12, passwd);
1407 #else /* PKCS12_FUNCS */
1408 wpa_printf(MSG_INFO, "TLS: PKCS12 support disabled - cannot read "
1409 "p12/pfx files");
1410 return -1;
1411 #endif /* PKCS12_FUNCS */
1415 static int tls_read_pkcs12_blob(SSL_CTX *ssl_ctx, SSL *ssl,
1416 const u8 *blob, size_t len, const char *passwd)
1418 #ifdef PKCS12_FUNCS
1419 PKCS12 *p12;
1421 p12 = d2i_PKCS12(NULL, (OPENSSL_d2i_TYPE) &blob, len);
1422 if (p12 == NULL) {
1423 tls_show_errors(MSG_INFO, __func__,
1424 "Failed to use PKCS#12 blob");
1425 return -1;
1428 return tls_parse_pkcs12(ssl_ctx, ssl, p12, passwd);
1430 #else /* PKCS12_FUNCS */
1431 wpa_printf(MSG_INFO, "TLS: PKCS12 support disabled - cannot parse "
1432 "p12/pfx blobs");
1433 return -1;
1434 #endif /* PKCS12_FUNCS */
1438 static int tls_connection_engine_private_key(void *_ssl_ctx,
1439 struct tls_connection *conn)
1441 #ifndef OPENSSL_NO_ENGINE
1442 if (SSL_use_PrivateKey(conn->ssl, conn->private_key) != 1) {
1443 tls_show_errors(MSG_ERROR, __func__,
1444 "ENGINE: cannot use private key for TLS");
1445 return -1;
1447 if (!SSL_check_private_key(conn->ssl)) {
1448 tls_show_errors(MSG_INFO, __func__,
1449 "Private key failed verification");
1450 return -1;
1452 return 0;
1453 #else /* OPENSSL_NO_ENGINE */
1454 wpa_printf(MSG_ERROR, "SSL: Configuration uses engine, but "
1455 "engine support was not compiled in");
1456 return -1;
1457 #endif /* OPENSSL_NO_ENGINE */
1461 static int tls_connection_private_key(void *_ssl_ctx,
1462 struct tls_connection *conn,
1463 const char *private_key,
1464 const char *private_key_passwd,
1465 const u8 *private_key_blob,
1466 size_t private_key_blob_len)
1468 SSL_CTX *ssl_ctx = _ssl_ctx;
1469 char *passwd;
1470 int ok;
1472 if (private_key == NULL && private_key_blob == NULL)
1473 return 0;
1475 if (private_key_passwd) {
1476 passwd = strdup(private_key_passwd);
1477 if (passwd == NULL)
1478 return -1;
1479 } else
1480 passwd = NULL;
1482 SSL_CTX_set_default_passwd_cb(ssl_ctx, tls_passwd_cb);
1483 SSL_CTX_set_default_passwd_cb_userdata(ssl_ctx, passwd);
1485 ok = 0;
1486 while (private_key_blob) {
1487 if (SSL_use_PrivateKey_ASN1(EVP_PKEY_RSA, conn->ssl,
1488 (u8 *) private_key_blob,
1489 private_key_blob_len) == 1) {
1490 wpa_printf(MSG_DEBUG, "OpenSSL: SSL_use_PrivateKey_"
1491 "ASN1(EVP_PKEY_RSA) --> OK");
1492 ok = 1;
1493 break;
1494 } else {
1495 tls_show_errors(MSG_DEBUG, __func__,
1496 "SSL_use_PrivateKey_ASN1(EVP_PKEY_RSA)"
1497 " failed");
1500 if (SSL_use_PrivateKey_ASN1(EVP_PKEY_DSA, conn->ssl,
1501 (u8 *) private_key_blob,
1502 private_key_blob_len) == 1) {
1503 wpa_printf(MSG_DEBUG, "OpenSSL: SSL_use_PrivateKey_"
1504 "ASN1(EVP_PKEY_DSA) --> OK");
1505 ok = 1;
1506 break;
1507 } else {
1508 tls_show_errors(MSG_DEBUG, __func__,
1509 "SSL_use_PrivateKey_ASN1(EVP_PKEY_DSA)"
1510 " failed");
1513 if (SSL_use_RSAPrivateKey_ASN1(conn->ssl,
1514 (u8 *) private_key_blob,
1515 private_key_blob_len) == 1) {
1516 wpa_printf(MSG_DEBUG, "OpenSSL: "
1517 "SSL_use_RSAPrivateKey_ASN1 --> OK");
1518 ok = 1;
1519 break;
1520 } else {
1521 tls_show_errors(MSG_DEBUG, __func__,
1522 "SSL_use_RSAPrivateKey_ASN1 failed");
1525 if (tls_read_pkcs12_blob(ssl_ctx, conn->ssl, private_key_blob,
1526 private_key_blob_len, passwd) == 0) {
1527 wpa_printf(MSG_DEBUG, "OpenSSL: PKCS#12 as blob --> "
1528 "OK");
1529 ok = 1;
1530 break;
1533 break;
1536 while (!ok && private_key) {
1537 #ifndef OPENSSL_NO_STDIO
1538 if (SSL_use_PrivateKey_file(conn->ssl, private_key,
1539 SSL_FILETYPE_ASN1) == 1) {
1540 wpa_printf(MSG_DEBUG, "OpenSSL: "
1541 "SSL_use_PrivateKey_File (DER) --> OK");
1542 ok = 1;
1543 break;
1544 } else {
1545 tls_show_errors(MSG_DEBUG, __func__,
1546 "SSL_use_PrivateKey_File (DER) "
1547 "failed");
1550 if (SSL_use_PrivateKey_file(conn->ssl, private_key,
1551 SSL_FILETYPE_PEM) == 1) {
1552 wpa_printf(MSG_DEBUG, "OpenSSL: "
1553 "SSL_use_PrivateKey_File (PEM) --> OK");
1554 ok = 1;
1555 break;
1556 } else {
1557 tls_show_errors(MSG_DEBUG, __func__,
1558 "SSL_use_PrivateKey_File (PEM) "
1559 "failed");
1561 #else /* OPENSSL_NO_STDIO */
1562 wpa_printf(MSG_DEBUG, "OpenSSL: %s - OPENSSL_NO_STDIO",
1563 __func__);
1564 #endif /* OPENSSL_NO_STDIO */
1566 if (tls_read_pkcs12(ssl_ctx, conn->ssl, private_key, passwd)
1567 == 0) {
1568 wpa_printf(MSG_DEBUG, "OpenSSL: Reading PKCS#12 file "
1569 "--> OK");
1570 ok = 1;
1571 break;
1574 if (tls_cryptoapi_cert(conn->ssl, private_key) == 0) {
1575 wpa_printf(MSG_DEBUG, "OpenSSL: Using CryptoAPI to "
1576 "access certificate store --> OK");
1577 ok = 1;
1578 break;
1581 break;
1584 if (!ok) {
1585 wpa_printf(MSG_INFO, "OpenSSL: Failed to load private key");
1586 free(passwd);
1587 ERR_clear_error();
1588 return -1;
1590 ERR_clear_error();
1591 SSL_CTX_set_default_passwd_cb(ssl_ctx, NULL);
1592 free(passwd);
1594 if (!SSL_check_private_key(conn->ssl)) {
1595 tls_show_errors(MSG_INFO, __func__, "Private key failed "
1596 "verification");
1597 return -1;
1600 wpa_printf(MSG_DEBUG, "SSL: Private key loaded successfully");
1601 return 0;
1605 int tls_global_private_key(void *_ssl_ctx, const char *private_key,
1606 const char *private_key_passwd)
1608 SSL_CTX *ssl_ctx = _ssl_ctx;
1609 char *passwd;
1611 if (private_key == NULL)
1612 return 0;
1614 if (private_key_passwd) {
1615 passwd = strdup(private_key_passwd);
1616 if (passwd == NULL)
1617 return -1;
1618 } else
1619 passwd = NULL;
1621 SSL_CTX_set_default_passwd_cb(ssl_ctx, tls_passwd_cb);
1622 SSL_CTX_set_default_passwd_cb_userdata(ssl_ctx, passwd);
1623 if (
1624 #ifndef OPENSSL_NO_STDIO
1625 SSL_CTX_use_PrivateKey_file(ssl_ctx, private_key,
1626 SSL_FILETYPE_ASN1) != 1 &&
1627 SSL_CTX_use_PrivateKey_file(ssl_ctx, private_key,
1628 SSL_FILETYPE_PEM) != 1 &&
1629 #endif /* OPENSSL_NO_STDIO */
1630 tls_read_pkcs12(ssl_ctx, NULL, private_key, passwd)) {
1631 tls_show_errors(MSG_INFO, __func__,
1632 "Failed to load private key");
1633 free(passwd);
1634 ERR_clear_error();
1635 return -1;
1637 free(passwd);
1638 ERR_clear_error();
1639 SSL_CTX_set_default_passwd_cb(ssl_ctx, NULL);
1641 if (!SSL_CTX_check_private_key(ssl_ctx)) {
1642 tls_show_errors(MSG_INFO, __func__,
1643 "Private key failed verification");
1644 return -1;
1647 return 0;
1651 static int tls_connection_dh(void *ssl_ctx, struct tls_connection *conn,
1652 const char *dh_file)
1654 #ifdef OPENSSL_NO_DH
1655 if (dh_file == NULL)
1656 return 0;
1657 wpa_printf(MSG_ERROR, "TLS: openssl does not include DH support, but "
1658 "dh_file specified");
1659 return -1;
1660 #else /* OPENSSL_NO_DH */
1661 DH *dh;
1662 BIO *bio;
1664 /* TODO: add support for dh_blob */
1665 if (dh_file == NULL)
1666 return 0;
1667 if (conn == NULL)
1668 return -1;
1670 bio = BIO_new_file(dh_file, "r");
1671 if (bio == NULL) {
1672 wpa_printf(MSG_INFO, "TLS: Failed to open DH file '%s': %s",
1673 dh_file, ERR_error_string(ERR_get_error(), NULL));
1674 return -1;
1676 dh = PEM_read_bio_DHparams(bio, NULL, NULL, NULL);
1677 BIO_free(bio);
1678 #ifndef OPENSSL_NO_DSA
1679 while (dh == NULL) {
1680 DSA *dsa;
1681 wpa_printf(MSG_DEBUG, "TLS: Failed to parse DH file '%s': %s -"
1682 " trying to parse as DSA params", dh_file,
1683 ERR_error_string(ERR_get_error(), NULL));
1684 bio = BIO_new_file(dh_file, "r");
1685 if (bio == NULL)
1686 break;
1687 dsa = PEM_read_bio_DSAparams(bio, NULL, NULL, NULL);
1688 BIO_free(bio);
1689 if (!dsa) {
1690 wpa_printf(MSG_DEBUG, "TLS: Failed to parse DSA file "
1691 "'%s': %s", dh_file,
1692 ERR_error_string(ERR_get_error(), NULL));
1693 break;
1696 wpa_printf(MSG_DEBUG, "TLS: DH file in DSA param format");
1697 dh = DSA_dup_DH(dsa);
1698 DSA_free(dsa);
1699 if (dh == NULL) {
1700 wpa_printf(MSG_INFO, "TLS: Failed to convert DSA "
1701 "params into DH params");
1702 break;
1704 break;
1706 #endif /* !OPENSSL_NO_DSA */
1707 if (dh == NULL) {
1708 wpa_printf(MSG_INFO, "TLS: Failed to read/parse DH/DSA file "
1709 "'%s'", dh_file);
1710 return -1;
1713 if (SSL_set_tmp_dh(conn->ssl, dh) != 1) {
1714 wpa_printf(MSG_INFO, "TLS: Failed to set DH params from '%s': "
1715 "%s", dh_file,
1716 ERR_error_string(ERR_get_error(), NULL));
1717 DH_free(dh);
1718 return -1;
1720 DH_free(dh);
1721 return 0;
1722 #endif /* OPENSSL_NO_DH */
1726 int tls_connection_get_keys(void *ssl_ctx, struct tls_connection *conn,
1727 struct tls_keys *keys)
1729 SSL *ssl;
1731 if (conn == NULL || keys == NULL)
1732 return -1;
1733 ssl = conn->ssl;
1734 if (ssl == NULL || ssl->s3 == NULL || ssl->session == NULL)
1735 return -1;
1737 memset(keys, 0, sizeof(*keys));
1738 keys->master_key = ssl->session->master_key;
1739 keys->master_key_len = ssl->session->master_key_length;
1740 keys->client_random = ssl->s3->client_random;
1741 keys->client_random_len = SSL3_RANDOM_SIZE;
1742 keys->server_random = ssl->s3->server_random;
1743 keys->server_random_len = SSL3_RANDOM_SIZE;
1745 return 0;
1749 u8 * tls_connection_handshake(void *ssl_ctx, struct tls_connection *conn,
1750 const u8 *in_data, size_t in_len,
1751 size_t *out_len)
1753 int res;
1754 u8 *out_data;
1757 * Give TLS handshake data from the server (if available) to OpenSSL
1758 * for processing.
1760 if (in_data &&
1761 BIO_write(conn->ssl_in, in_data, in_len) < 0) {
1762 tls_show_errors(MSG_INFO, __func__,
1763 "Handshake failed - BIO_write");
1764 return NULL;
1767 /* Initiate TLS handshake or continue the existing handshake */
1768 res = SSL_connect(conn->ssl);
1769 if (res != 1) {
1770 int err = SSL_get_error(conn->ssl, res);
1771 if (err == SSL_ERROR_WANT_READ)
1772 wpa_printf(MSG_DEBUG, "SSL: SSL_connect - want "
1773 "more data");
1774 else if (err == SSL_ERROR_WANT_WRITE)
1775 wpa_printf(MSG_DEBUG, "SSL: SSL_connect - want to "
1776 "write");
1777 else {
1778 tls_show_errors(MSG_INFO, __func__, "SSL_connect");
1779 conn->failed++;
1783 /* Get the TLS handshake data to be sent to the server */
1784 res = BIO_ctrl_pending(conn->ssl_out);
1785 wpa_printf(MSG_DEBUG, "SSL: %d bytes pending from ssl_out", res);
1786 out_data = malloc(res == 0 ? 1 : res);
1787 if (out_data == NULL) {
1788 wpa_printf(MSG_DEBUG, "SSL: Failed to allocate memory for "
1789 "handshake output (%d bytes)", res);
1790 if (BIO_reset(conn->ssl_out) < 0) {
1791 tls_show_errors(MSG_INFO, __func__,
1792 "BIO_reset failed");
1794 *out_len = 0;
1795 return NULL;
1797 res = res == 0 ? 0 : BIO_read(conn->ssl_out, out_data, res);
1798 if (res < 0) {
1799 tls_show_errors(MSG_INFO, __func__,
1800 "Handshake failed - BIO_read");
1801 if (BIO_reset(conn->ssl_out) < 0) {
1802 tls_show_errors(MSG_INFO, __func__,
1803 "BIO_reset failed");
1805 *out_len = 0;
1806 return NULL;
1808 *out_len = res;
1809 return out_data;
1813 u8 * tls_connection_server_handshake(void *ssl_ctx,
1814 struct tls_connection *conn,
1815 const u8 *in_data, size_t in_len,
1816 size_t *out_len)
1818 int res;
1819 u8 *out_data;
1820 char buf[10];
1822 if (in_data &&
1823 BIO_write(conn->ssl_in, in_data, in_len) < 0) {
1824 tls_show_errors(MSG_INFO, __func__,
1825 "Handshake failed - BIO_write");
1826 return NULL;
1829 res = SSL_read(conn->ssl, buf, sizeof(buf));
1830 if (res >= 0) {
1831 wpa_printf(MSG_DEBUG, "SSL: Unexpected data from SSL_read "
1832 "(res=%d)", res);
1835 res = BIO_ctrl_pending(conn->ssl_out);
1836 wpa_printf(MSG_DEBUG, "SSL: %d bytes pending from ssl_out", res);
1837 out_data = malloc(res == 0 ? 1 : res);
1838 if (out_data == NULL) {
1839 wpa_printf(MSG_DEBUG, "SSL: Failed to allocate memory for "
1840 "handshake output (%d bytes)", res);
1841 if (BIO_reset(conn->ssl_out) < 0) {
1842 tls_show_errors(MSG_INFO, __func__,
1843 "BIO_reset failed");
1845 *out_len = 0;
1846 return NULL;
1848 res = res == 0 ? 0 : BIO_read(conn->ssl_out, out_data, res);
1849 if (res < 0) {
1850 tls_show_errors(MSG_INFO, __func__,
1851 "Handshake failed - BIO_read");
1852 if (BIO_reset(conn->ssl_out) < 0) {
1853 tls_show_errors(MSG_INFO, __func__,
1854 "BIO_reset failed");
1856 *out_len = 0;
1857 return NULL;
1859 *out_len = res;
1860 return out_data;
1864 int tls_connection_encrypt(void *ssl_ctx, struct tls_connection *conn,
1865 const u8 *in_data, size_t in_len,
1866 u8 *out_data, size_t out_len)
1868 int res;
1870 if (conn == NULL)
1871 return -1;
1873 /* Give plaintext data for OpenSSL to encrypt into the TLS tunnel. */
1874 if ((res = BIO_reset(conn->ssl_in)) < 0 ||
1875 (res = BIO_reset(conn->ssl_out)) < 0) {
1876 tls_show_errors(MSG_INFO, __func__, "BIO_reset failed");
1877 return res;
1879 res = SSL_write(conn->ssl, in_data, in_len);
1880 if (res < 0) {
1881 tls_show_errors(MSG_INFO, __func__,
1882 "Encryption failed - SSL_write");
1883 return res;
1886 /* Read encrypted data to be sent to the server */
1887 res = BIO_read(conn->ssl_out, out_data, out_len);
1888 if (res < 0) {
1889 tls_show_errors(MSG_INFO, __func__,
1890 "Encryption failed - BIO_read");
1891 return res;
1894 return res;
1898 int tls_connection_decrypt(void *ssl_ctx, struct tls_connection *conn,
1899 const u8 *in_data, size_t in_len,
1900 u8 *out_data, size_t out_len)
1902 int res;
1904 /* Give encrypted data from TLS tunnel for OpenSSL to decrypt. */
1905 res = BIO_write(conn->ssl_in, in_data, in_len);
1906 if (res < 0) {
1907 tls_show_errors(MSG_INFO, __func__,
1908 "Decryption failed - BIO_write");
1909 return res;
1911 if (BIO_reset(conn->ssl_out) < 0) {
1912 tls_show_errors(MSG_INFO, __func__, "BIO_reset failed");
1913 return res;
1916 /* Read decrypted data for further processing */
1917 res = SSL_read(conn->ssl, out_data, out_len);
1918 if (res < 0) {
1919 tls_show_errors(MSG_INFO, __func__,
1920 "Decryption failed - SSL_read");
1921 return res;
1924 return res;
1928 int tls_connection_resumed(void *ssl_ctx, struct tls_connection *conn)
1930 return conn ? conn->ssl->hit : 0;
1934 #ifdef EAP_FAST
1935 /* Pre-shared secred requires a patch to openssl, so this function is
1936 * commented out unless explicitly needed for EAP-FAST in order to be able to
1937 * build this file with unmodified openssl. */
1939 static int tls_sess_sec_cb(SSL *s, void *secret, int *secret_len,
1940 STACK_OF(SSL_CIPHER) *peer_ciphers,
1941 SSL_CIPHER **cipher, void *arg)
1943 struct tls_connection *conn = arg;
1945 if (conn == NULL || conn->pre_shared_secret == 0)
1946 return 0;
1948 memcpy(secret, conn->pre_shared_secret, conn->pre_shared_secret_len);
1949 *secret_len = conn->pre_shared_secret_len;
1951 return 1;
1955 int tls_connection_set_master_key(void *ssl_ctx, struct tls_connection *conn,
1956 const u8 *key, size_t key_len)
1958 if (conn == NULL || key_len > SSL_MAX_MASTER_KEY_LENGTH)
1959 return -1;
1961 free(conn->pre_shared_secret);
1962 conn->pre_shared_secret = NULL;
1963 conn->pre_shared_secret_len = 0;
1965 if (key) {
1966 conn->pre_shared_secret = malloc(key_len);
1967 if (conn->pre_shared_secret) {
1968 memcpy(conn->pre_shared_secret, key, key_len);
1969 conn->pre_shared_secret_len = key_len;
1971 if (SSL_set_session_secret_cb(conn->ssl, tls_sess_sec_cb,
1972 conn) != 1)
1973 return -1;
1974 } else {
1975 if (SSL_set_session_secret_cb(conn->ssl, NULL, NULL) != 1)
1976 return -1;
1979 return 0;
1981 #endif /* EAP_FAST */
1984 int tls_connection_set_anon_dh(void *ssl_ctx, struct tls_connection *conn)
1986 if (conn == NULL || conn->ssl == NULL)
1987 return -1;
1989 if (SSL_set_cipher_list(conn->ssl, "ADH-AES128-SHA") != 1) {
1990 tls_show_errors(MSG_INFO, __func__,
1991 "Anon DH configuration failed");
1992 return -1;
1995 return 0;
1999 int tls_get_cipher(void *ssl_ctx, struct tls_connection *conn,
2000 char *buf, size_t buflen)
2002 const char *name;
2003 if (conn == NULL || conn->ssl == NULL)
2004 return -1;
2006 name = SSL_get_cipher(conn->ssl);
2007 if (name == NULL)
2008 return -1;
2010 snprintf(buf, buflen, "%s", name);
2011 return 0;
2015 int tls_connection_enable_workaround(void *ssl_ctx,
2016 struct tls_connection *conn)
2018 SSL_set_options(conn->ssl, SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS);
2020 return 0;
2024 #ifdef EAP_FAST
2025 /* ClientHello TLS extensions require a patch to openssl, so this function is
2026 * commented out unless explicitly needed for EAP-FAST in order to be able to
2027 * build this file with unmodified openssl. */
2028 int tls_connection_client_hello_ext(void *ssl_ctx, struct tls_connection *conn,
2029 int ext_type, const u8 *data,
2030 size_t data_len)
2032 if (conn == NULL || conn->ssl == NULL)
2033 return -1;
2035 if (SSL_set_hello_extension(conn->ssl, ext_type, (void *) data,
2036 data_len) != 1)
2037 return -1;
2039 return 0;
2041 #endif /* EAP_FAST */
2044 int tls_connection_get_failed(void *ssl_ctx, struct tls_connection *conn)
2046 if (conn == NULL)
2047 return -1;
2048 return conn->failed;
2052 int tls_connection_get_read_alerts(void *ssl_ctx, struct tls_connection *conn)
2054 if (conn == NULL)
2055 return -1;
2056 return conn->read_alerts;
2060 int tls_connection_get_write_alerts(void *ssl_ctx, struct tls_connection *conn)
2062 if (conn == NULL)
2063 return -1;
2064 return conn->write_alerts;
2068 int tls_connection_set_params(void *tls_ctx, struct tls_connection *conn,
2069 const struct tls_connection_params *params)
2071 int ret;
2072 unsigned long err;
2074 if (conn == NULL)
2075 return -1;
2077 while ((err = ERR_get_error())) {
2078 wpa_printf(MSG_INFO, "%s: Clearing pending SSL error: %s",
2079 __func__, ERR_error_string(err, NULL));
2082 if (tls_connection_set_subject_match(tls_ctx, conn,
2083 params->subject_match,
2084 params->altsubject_match))
2085 return -1;
2086 if (tls_connection_ca_cert(tls_ctx, conn, params->ca_cert,
2087 params->ca_cert_blob,
2088 params->ca_cert_blob_len,
2089 params->ca_path))
2090 return -1;
2091 if (tls_connection_client_cert(tls_ctx, conn, params->client_cert,
2092 params->client_cert_blob,
2093 params->client_cert_blob_len))
2094 return -1;
2096 if (params->engine) {
2097 wpa_printf(MSG_DEBUG, "SSL: Initializing TLS engine");
2098 ret = tls_engine_init(conn, params->engine_id, params->pin,
2099 params->key_id);
2100 if (ret)
2101 return ret;
2102 if (tls_connection_engine_private_key(tls_ctx, conn))
2103 return TLS_SET_PARAMS_ENGINE_PRV_VERIFY_FAILED;
2104 } else if (tls_connection_private_key(tls_ctx, conn,
2105 params->private_key,
2106 params->private_key_passwd,
2107 params->private_key_blob,
2108 params->private_key_blob_len)) {
2109 wpa_printf(MSG_INFO, "TLS: Failed to load private key '%s'",
2110 params->private_key);
2111 return -1;
2114 if (tls_connection_dh(tls_ctx, conn, params->dh_file)) {
2115 wpa_printf(MSG_INFO, "TLS: Failed to load DH file '%s'",
2116 params->dh_file);
2117 return -1;
2120 tls_get_errors(tls_ctx);
2122 return 0;
2126 int tls_connection_get_keyblock_size(void *tls_ctx,
2127 struct tls_connection *conn)
2129 const EVP_CIPHER *c;
2130 const EVP_MD *h;
2132 if (conn == NULL || conn->ssl == NULL ||
2133 conn->ssl->enc_read_ctx == NULL ||
2134 conn->ssl->enc_read_ctx->cipher == NULL ||
2135 conn->ssl->read_hash == NULL)
2136 return -1;
2138 c = conn->ssl->enc_read_ctx->cipher;
2139 h = conn->ssl->read_hash;
2141 return 2 * (EVP_CIPHER_key_length(c) +
2142 EVP_MD_size(h) +
2143 EVP_CIPHER_iv_length(c));