Home | History | Annotate | Download | only in crypto
      1 /*
      2  * TLS interface functions and an internal TLS implementation
      3  * Copyright (c) 2004-2011, Jouni Malinen <j (at) w1.fi>
      4  *
      5  * This software may be distributed under the terms of the BSD license.
      6  * See README for more details.
      7  *
      8  * This file interface functions for hostapd/wpa_supplicant to use the
      9  * integrated TLSv1 implementation.
     10  */
     11 
     12 #include "includes.h"
     13 
     14 #include "common.h"
     15 #include "tls.h"
     16 #include "tls/tlsv1_client.h"
     17 #include "tls/tlsv1_server.h"
     18 
     19 
     20 static int tls_ref_count = 0;
     21 
     22 struct tls_global {
     23 	int server;
     24 	struct tlsv1_credentials *server_cred;
     25 	int check_crl;
     26 };
     27 
     28 struct tls_connection {
     29 	struct tlsv1_client *client;
     30 	struct tlsv1_server *server;
     31 	struct tls_global *global;
     32 };
     33 
     34 
     35 void * tls_init(const struct tls_config *conf)
     36 {
     37 	struct tls_global *global;
     38 
     39 	if (tls_ref_count == 0) {
     40 #ifdef CONFIG_TLS_INTERNAL_CLIENT
     41 		if (tlsv1_client_global_init())
     42 			return NULL;
     43 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
     44 #ifdef CONFIG_TLS_INTERNAL_SERVER
     45 		if (tlsv1_server_global_init())
     46 			return NULL;
     47 #endif /* CONFIG_TLS_INTERNAL_SERVER */
     48 	}
     49 	tls_ref_count++;
     50 
     51 	global = os_zalloc(sizeof(*global));
     52 	if (global == NULL)
     53 		return NULL;
     54 
     55 	return global;
     56 }
     57 
     58 void tls_deinit(void *ssl_ctx)
     59 {
     60 	struct tls_global *global = ssl_ctx;
     61 	tls_ref_count--;
     62 	if (tls_ref_count == 0) {
     63 #ifdef CONFIG_TLS_INTERNAL_CLIENT
     64 		tlsv1_client_global_deinit();
     65 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
     66 #ifdef CONFIG_TLS_INTERNAL_SERVER
     67 		tlsv1_cred_free(global->server_cred);
     68 		tlsv1_server_global_deinit();
     69 #endif /* CONFIG_TLS_INTERNAL_SERVER */
     70 	}
     71 	os_free(global);
     72 }
     73 
     74 
     75 int tls_get_errors(void *tls_ctx)
     76 {
     77 	return 0;
     78 }
     79 
     80 
     81 struct tls_connection * tls_connection_init(void *tls_ctx)
     82 {
     83 	struct tls_connection *conn;
     84 	struct tls_global *global = tls_ctx;
     85 
     86 	conn = os_zalloc(sizeof(*conn));
     87 	if (conn == NULL)
     88 		return NULL;
     89 	conn->global = global;
     90 
     91 #ifdef CONFIG_TLS_INTERNAL_CLIENT
     92 	if (!global->server) {
     93 		conn->client = tlsv1_client_init();
     94 		if (conn->client == NULL) {
     95 			os_free(conn);
     96 			return NULL;
     97 		}
     98 	}
     99 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    100 #ifdef CONFIG_TLS_INTERNAL_SERVER
    101 	if (global->server) {
    102 		conn->server = tlsv1_server_init(global->server_cred);
    103 		if (conn->server == NULL) {
    104 			os_free(conn);
    105 			return NULL;
    106 		}
    107 	}
    108 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    109 
    110 	return conn;
    111 }
    112 
    113 
    114 #ifdef CONFIG_TESTING_OPTIONS
    115 #ifdef CONFIG_TLS_INTERNAL_SERVER
    116 void tls_connection_set_test_flags(struct tls_connection *conn, u32 flags)
    117 {
    118 	if (conn->server)
    119 		tlsv1_server_set_test_flags(conn->server, flags);
    120 }
    121 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    122 #endif /* CONFIG_TESTING_OPTIONS */
    123 
    124 
    125 void tls_connection_set_log_cb(struct tls_connection *conn,
    126 			       void (*log_cb)(void *ctx, const char *msg),
    127 			       void *ctx)
    128 {
    129 #ifdef CONFIG_TLS_INTERNAL_SERVER
    130 	if (conn->server)
    131 		tlsv1_server_set_log_cb(conn->server, log_cb, ctx);
    132 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    133 }
    134 
    135 
    136 void tls_connection_deinit(void *tls_ctx, struct tls_connection *conn)
    137 {
    138 	if (conn == NULL)
    139 		return;
    140 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    141 	if (conn->client)
    142 		tlsv1_client_deinit(conn->client);
    143 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    144 #ifdef CONFIG_TLS_INTERNAL_SERVER
    145 	if (conn->server)
    146 		tlsv1_server_deinit(conn->server);
    147 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    148 	os_free(conn);
    149 }
    150 
    151 
    152 int tls_connection_established(void *tls_ctx, struct tls_connection *conn)
    153 {
    154 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    155 	if (conn->client)
    156 		return tlsv1_client_established(conn->client);
    157 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    158 #ifdef CONFIG_TLS_INTERNAL_SERVER
    159 	if (conn->server)
    160 		return tlsv1_server_established(conn->server);
    161 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    162 	return 0;
    163 }
    164 
    165 
    166 int tls_connection_shutdown(void *tls_ctx, struct tls_connection *conn)
    167 {
    168 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    169 	if (conn->client)
    170 		return tlsv1_client_shutdown(conn->client);
    171 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    172 #ifdef CONFIG_TLS_INTERNAL_SERVER
    173 	if (conn->server)
    174 		return tlsv1_server_shutdown(conn->server);
    175 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    176 	return -1;
    177 }
    178 
    179 
    180 int tls_connection_set_params(void *tls_ctx, struct tls_connection *conn,
    181 			      const struct tls_connection_params *params)
    182 {
    183 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    184 	struct tlsv1_credentials *cred;
    185 
    186 	if (conn->client == NULL)
    187 		return -1;
    188 
    189 	cred = tlsv1_cred_alloc();
    190 	if (cred == NULL)
    191 		return -1;
    192 
    193 	if (params->subject_match) {
    194 		wpa_printf(MSG_INFO, "TLS: subject_match not supported");
    195 		tlsv1_cred_free(cred);
    196 		return -1;
    197 	}
    198 
    199 	if (params->altsubject_match) {
    200 		wpa_printf(MSG_INFO, "TLS: altsubject_match not supported");
    201 		tlsv1_cred_free(cred);
    202 		return -1;
    203 	}
    204 
    205 	if (params->suffix_match) {
    206 		wpa_printf(MSG_INFO, "TLS: suffix_match not supported");
    207 		tlsv1_cred_free(cred);
    208 		return -1;
    209 	}
    210 
    211 	if (params->domain_match) {
    212 		wpa_printf(MSG_INFO, "TLS: domain_match not supported");
    213 		tlsv1_cred_free(cred);
    214 		return -1;
    215 	}
    216 
    217 	if (params->openssl_ciphers) {
    218 		wpa_printf(MSG_INFO, "TLS: openssl_ciphers not supported");
    219 		tlsv1_cred_free(cred);
    220 		return -1;
    221 	}
    222 
    223 	if (tlsv1_set_ca_cert(cred, params->ca_cert,
    224 			      params->ca_cert_blob, params->ca_cert_blob_len,
    225 			      params->ca_path)) {
    226 		wpa_printf(MSG_INFO, "TLS: Failed to configure trusted CA "
    227 			   "certificates");
    228 		tlsv1_cred_free(cred);
    229 		return -1;
    230 	}
    231 
    232 	if (tlsv1_set_cert(cred, params->client_cert,
    233 			   params->client_cert_blob,
    234 			   params->client_cert_blob_len)) {
    235 		wpa_printf(MSG_INFO, "TLS: Failed to configure client "
    236 			   "certificate");
    237 		tlsv1_cred_free(cred);
    238 		return -1;
    239 	}
    240 
    241 	if (tlsv1_set_private_key(cred, params->private_key,
    242 				  params->private_key_passwd,
    243 				  params->private_key_blob,
    244 				  params->private_key_blob_len)) {
    245 		wpa_printf(MSG_INFO, "TLS: Failed to load private key");
    246 		tlsv1_cred_free(cred);
    247 		return -1;
    248 	}
    249 
    250 	if (tlsv1_set_dhparams(cred, params->dh_file, params->dh_blob,
    251 			       params->dh_blob_len)) {
    252 		wpa_printf(MSG_INFO, "TLS: Failed to load DH parameters");
    253 		tlsv1_cred_free(cred);
    254 		return -1;
    255 	}
    256 
    257 	if (tlsv1_client_set_cred(conn->client, cred) < 0) {
    258 		tlsv1_cred_free(cred);
    259 		return -1;
    260 	}
    261 
    262 	tlsv1_client_set_time_checks(
    263 		conn->client, !(params->flags & TLS_CONN_DISABLE_TIME_CHECKS));
    264 
    265 	return 0;
    266 #else /* CONFIG_TLS_INTERNAL_CLIENT */
    267 	return -1;
    268 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    269 }
    270 
    271 
    272 int tls_global_set_params(void *tls_ctx,
    273 			  const struct tls_connection_params *params)
    274 {
    275 #ifdef CONFIG_TLS_INTERNAL_SERVER
    276 	struct tls_global *global = tls_ctx;
    277 	struct tlsv1_credentials *cred;
    278 
    279 	/* Currently, global parameters are only set when running in server
    280 	 * mode. */
    281 	global->server = 1;
    282 	tlsv1_cred_free(global->server_cred);
    283 	global->server_cred = cred = tlsv1_cred_alloc();
    284 	if (cred == NULL)
    285 		return -1;
    286 
    287 	if (tlsv1_set_ca_cert(cred, params->ca_cert, params->ca_cert_blob,
    288 			      params->ca_cert_blob_len, params->ca_path)) {
    289 		wpa_printf(MSG_INFO, "TLS: Failed to configure trusted CA "
    290 			   "certificates");
    291 		return -1;
    292 	}
    293 
    294 	if (tlsv1_set_cert(cred, params->client_cert, params->client_cert_blob,
    295 			   params->client_cert_blob_len)) {
    296 		wpa_printf(MSG_INFO, "TLS: Failed to configure server "
    297 			   "certificate");
    298 		return -1;
    299 	}
    300 
    301 	if (tlsv1_set_private_key(cred, params->private_key,
    302 				  params->private_key_passwd,
    303 				  params->private_key_blob,
    304 				  params->private_key_blob_len)) {
    305 		wpa_printf(MSG_INFO, "TLS: Failed to load private key");
    306 		return -1;
    307 	}
    308 
    309 	if (tlsv1_set_dhparams(cred, params->dh_file, params->dh_blob,
    310 			       params->dh_blob_len)) {
    311 		wpa_printf(MSG_INFO, "TLS: Failed to load DH parameters");
    312 		return -1;
    313 	}
    314 
    315 	return 0;
    316 #else /* CONFIG_TLS_INTERNAL_SERVER */
    317 	return -1;
    318 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    319 }
    320 
    321 
    322 int tls_global_set_verify(void *tls_ctx, int check_crl)
    323 {
    324 	struct tls_global *global = tls_ctx;
    325 	global->check_crl = check_crl;
    326 	return 0;
    327 }
    328 
    329 
    330 int tls_connection_set_verify(void *tls_ctx, struct tls_connection *conn,
    331 			      int verify_peer)
    332 {
    333 #ifdef CONFIG_TLS_INTERNAL_SERVER
    334 	if (conn->server)
    335 		return tlsv1_server_set_verify(conn->server, verify_peer);
    336 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    337 	return -1;
    338 }
    339 
    340 
    341 int tls_connection_get_keys(void *tls_ctx, struct tls_connection *conn,
    342 			    struct tls_keys *keys)
    343 {
    344 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    345 	if (conn->client)
    346 		return tlsv1_client_get_keys(conn->client, keys);
    347 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    348 #ifdef CONFIG_TLS_INTERNAL_SERVER
    349 	if (conn->server)
    350 		return tlsv1_server_get_keys(conn->server, keys);
    351 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    352 	return -1;
    353 }
    354 
    355 
    356 static int tls_get_keyblock_size(struct tls_connection *conn)
    357 {
    358 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    359 	if (conn->client)
    360 		return tlsv1_client_get_keyblock_size(conn->client);
    361 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    362 #ifdef CONFIG_TLS_INTERNAL_SERVER
    363 	if (conn->server)
    364 		return tlsv1_server_get_keyblock_size(conn->server);
    365 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    366 	return -1;
    367 }
    368 
    369 
    370 int tls_connection_prf(void *tls_ctx, struct tls_connection *conn,
    371 		       const char *label, int server_random_first,
    372 		       int skip_keyblock, u8 *out, size_t out_len)
    373 {
    374 	int ret = -1, skip = 0;
    375 	u8 *tmp_out = NULL;
    376 	u8 *_out = out;
    377 
    378 	if (skip_keyblock) {
    379 		skip = tls_get_keyblock_size(conn);
    380 		if (skip < 0)
    381 			return -1;
    382 		tmp_out = os_malloc(skip + out_len);
    383 		if (!tmp_out)
    384 			return -1;
    385 		_out = tmp_out;
    386 	}
    387 
    388 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    389 	if (conn->client) {
    390 		ret = tlsv1_client_prf(conn->client, label,
    391 				       server_random_first,
    392 				       _out, out_len);
    393 	}
    394 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    395 #ifdef CONFIG_TLS_INTERNAL_SERVER
    396 	if (conn->server) {
    397 		ret = tlsv1_server_prf(conn->server, label,
    398 				       server_random_first,
    399 				       _out, out_len);
    400 	}
    401 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    402 	if (ret == 0 && skip_keyblock)
    403 		os_memcpy(out, _out + skip, out_len);
    404 	bin_clear_free(tmp_out, skip);
    405 
    406 	return ret;
    407 }
    408 
    409 
    410 struct wpabuf * tls_connection_handshake(void *tls_ctx,
    411 					 struct tls_connection *conn,
    412 					 const struct wpabuf *in_data,
    413 					 struct wpabuf **appl_data)
    414 {
    415 	return tls_connection_handshake2(tls_ctx, conn, in_data, appl_data,
    416 					 NULL);
    417 }
    418 
    419 
    420 struct wpabuf * tls_connection_handshake2(void *tls_ctx,
    421 					  struct tls_connection *conn,
    422 					  const struct wpabuf *in_data,
    423 					  struct wpabuf **appl_data,
    424 					  int *need_more_data)
    425 {
    426 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    427 	u8 *res, *ad;
    428 	size_t res_len, ad_len;
    429 	struct wpabuf *out;
    430 
    431 	if (conn->client == NULL)
    432 		return NULL;
    433 
    434 	ad = NULL;
    435 	res = tlsv1_client_handshake(conn->client,
    436 				     in_data ? wpabuf_head(in_data) : NULL,
    437 				     in_data ? wpabuf_len(in_data) : 0,
    438 				     &res_len, &ad, &ad_len, need_more_data);
    439 	if (res == NULL)
    440 		return NULL;
    441 	out = wpabuf_alloc_ext_data(res, res_len);
    442 	if (out == NULL) {
    443 		os_free(res);
    444 		os_free(ad);
    445 		return NULL;
    446 	}
    447 	if (appl_data) {
    448 		if (ad) {
    449 			*appl_data = wpabuf_alloc_ext_data(ad, ad_len);
    450 			if (*appl_data == NULL)
    451 				os_free(ad);
    452 		} else
    453 			*appl_data = NULL;
    454 	} else
    455 		os_free(ad);
    456 
    457 	return out;
    458 #else /* CONFIG_TLS_INTERNAL_CLIENT */
    459 	return NULL;
    460 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    461 }
    462 
    463 
    464 struct wpabuf * tls_connection_server_handshake(void *tls_ctx,
    465 						struct tls_connection *conn,
    466 						const struct wpabuf *in_data,
    467 						struct wpabuf **appl_data)
    468 {
    469 #ifdef CONFIG_TLS_INTERNAL_SERVER
    470 	u8 *res;
    471 	size_t res_len;
    472 	struct wpabuf *out;
    473 
    474 	if (conn->server == NULL)
    475 		return NULL;
    476 
    477 	if (appl_data)
    478 		*appl_data = NULL;
    479 
    480 	res = tlsv1_server_handshake(conn->server, wpabuf_head(in_data),
    481 				     wpabuf_len(in_data), &res_len);
    482 	if (res == NULL && tlsv1_server_established(conn->server))
    483 		return wpabuf_alloc(0);
    484 	if (res == NULL)
    485 		return NULL;
    486 	out = wpabuf_alloc_ext_data(res, res_len);
    487 	if (out == NULL) {
    488 		os_free(res);
    489 		return NULL;
    490 	}
    491 
    492 	return out;
    493 #else /* CONFIG_TLS_INTERNAL_SERVER */
    494 	return NULL;
    495 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    496 }
    497 
    498 
    499 struct wpabuf * tls_connection_encrypt(void *tls_ctx,
    500 				       struct tls_connection *conn,
    501 				       const struct wpabuf *in_data)
    502 {
    503 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    504 	if (conn->client) {
    505 		struct wpabuf *buf;
    506 		int res;
    507 		buf = wpabuf_alloc(wpabuf_len(in_data) + 300);
    508 		if (buf == NULL)
    509 			return NULL;
    510 		res = tlsv1_client_encrypt(conn->client, wpabuf_head(in_data),
    511 					   wpabuf_len(in_data),
    512 					   wpabuf_mhead(buf),
    513 					   wpabuf_size(buf));
    514 		if (res < 0) {
    515 			wpabuf_free(buf);
    516 			return NULL;
    517 		}
    518 		wpabuf_put(buf, res);
    519 		return buf;
    520 	}
    521 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    522 #ifdef CONFIG_TLS_INTERNAL_SERVER
    523 	if (conn->server) {
    524 		struct wpabuf *buf;
    525 		int res;
    526 		buf = wpabuf_alloc(wpabuf_len(in_data) + 300);
    527 		if (buf == NULL)
    528 			return NULL;
    529 		res = tlsv1_server_encrypt(conn->server, wpabuf_head(in_data),
    530 					   wpabuf_len(in_data),
    531 					   wpabuf_mhead(buf),
    532 					   wpabuf_size(buf));
    533 		if (res < 0) {
    534 			wpabuf_free(buf);
    535 			return NULL;
    536 		}
    537 		wpabuf_put(buf, res);
    538 		return buf;
    539 	}
    540 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    541 	return NULL;
    542 }
    543 
    544 
    545 struct wpabuf * tls_connection_decrypt(void *tls_ctx,
    546 				       struct tls_connection *conn,
    547 				       const struct wpabuf *in_data)
    548 {
    549 	return tls_connection_decrypt2(tls_ctx, conn, in_data, NULL);
    550 }
    551 
    552 
    553 struct wpabuf * tls_connection_decrypt2(void *tls_ctx,
    554 					struct tls_connection *conn,
    555 					const struct wpabuf *in_data,
    556 					int *need_more_data)
    557 {
    558 	if (need_more_data)
    559 		*need_more_data = 0;
    560 
    561 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    562 	if (conn->client) {
    563 		return tlsv1_client_decrypt(conn->client, wpabuf_head(in_data),
    564 					    wpabuf_len(in_data),
    565 					    need_more_data);
    566 	}
    567 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    568 #ifdef CONFIG_TLS_INTERNAL_SERVER
    569 	if (conn->server) {
    570 		struct wpabuf *buf;
    571 		int res;
    572 		buf = wpabuf_alloc((wpabuf_len(in_data) + 500) * 3);
    573 		if (buf == NULL)
    574 			return NULL;
    575 		res = tlsv1_server_decrypt(conn->server, wpabuf_head(in_data),
    576 					   wpabuf_len(in_data),
    577 					   wpabuf_mhead(buf),
    578 					   wpabuf_size(buf));
    579 		if (res < 0) {
    580 			wpabuf_free(buf);
    581 			return NULL;
    582 		}
    583 		wpabuf_put(buf, res);
    584 		return buf;
    585 	}
    586 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    587 	return NULL;
    588 }
    589 
    590 
    591 int tls_connection_resumed(void *tls_ctx, struct tls_connection *conn)
    592 {
    593 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    594 	if (conn->client)
    595 		return tlsv1_client_resumed(conn->client);
    596 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    597 #ifdef CONFIG_TLS_INTERNAL_SERVER
    598 	if (conn->server)
    599 		return tlsv1_server_resumed(conn->server);
    600 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    601 	return -1;
    602 }
    603 
    604 
    605 int tls_connection_set_cipher_list(void *tls_ctx, struct tls_connection *conn,
    606 				   u8 *ciphers)
    607 {
    608 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    609 	if (conn->client)
    610 		return tlsv1_client_set_cipher_list(conn->client, ciphers);
    611 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    612 #ifdef CONFIG_TLS_INTERNAL_SERVER
    613 	if (conn->server)
    614 		return tlsv1_server_set_cipher_list(conn->server, ciphers);
    615 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    616 	return -1;
    617 }
    618 
    619 
    620 int tls_get_cipher(void *tls_ctx, struct tls_connection *conn,
    621 		   char *buf, size_t buflen)
    622 {
    623 	if (conn == NULL)
    624 		return -1;
    625 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    626 	if (conn->client)
    627 		return tlsv1_client_get_cipher(conn->client, buf, buflen);
    628 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    629 #ifdef CONFIG_TLS_INTERNAL_SERVER
    630 	if (conn->server)
    631 		return tlsv1_server_get_cipher(conn->server, buf, buflen);
    632 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    633 	return -1;
    634 }
    635 
    636 
    637 int tls_connection_enable_workaround(void *tls_ctx,
    638 				     struct tls_connection *conn)
    639 {
    640 	return -1;
    641 }
    642 
    643 
    644 int tls_connection_client_hello_ext(void *tls_ctx, struct tls_connection *conn,
    645 				    int ext_type, const u8 *data,
    646 				    size_t data_len)
    647 {
    648 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    649 	if (conn->client) {
    650 		return tlsv1_client_hello_ext(conn->client, ext_type,
    651 					      data, data_len);
    652 	}
    653 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    654 	return -1;
    655 }
    656 
    657 
    658 int tls_connection_get_failed(void *tls_ctx, struct tls_connection *conn)
    659 {
    660 	return 0;
    661 }
    662 
    663 
    664 int tls_connection_get_read_alerts(void *tls_ctx, struct tls_connection *conn)
    665 {
    666 	return 0;
    667 }
    668 
    669 
    670 int tls_connection_get_write_alerts(void *tls_ctx,
    671 				    struct tls_connection *conn)
    672 {
    673 	return 0;
    674 }
    675 
    676 
    677 unsigned int tls_capabilities(void *tls_ctx)
    678 {
    679 	return 0;
    680 }
    681 
    682 
    683 int tls_connection_set_session_ticket_cb(void *tls_ctx,
    684 					 struct tls_connection *conn,
    685 					 tls_session_ticket_cb cb,
    686 					 void *ctx)
    687 {
    688 #ifdef CONFIG_TLS_INTERNAL_CLIENT
    689 	if (conn->client) {
    690 		tlsv1_client_set_session_ticket_cb(conn->client, cb, ctx);
    691 		return 0;
    692 	}
    693 #endif /* CONFIG_TLS_INTERNAL_CLIENT */
    694 #ifdef CONFIG_TLS_INTERNAL_SERVER
    695 	if (conn->server) {
    696 		tlsv1_server_set_session_ticket_cb(conn->server, cb, ctx);
    697 		return 0;
    698 	}
    699 #endif /* CONFIG_TLS_INTERNAL_SERVER */
    700 	return -1;
    701 }
    702 
    703 
    704 int tls_get_library_version(char *buf, size_t buf_len)
    705 {
    706 	return os_snprintf(buf, buf_len, "internal");
    707 }
    708