• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * SSL/TLS interface functions for NSS
3  * Copyright (c) 2009, Jouni Malinen <j@w1.fi>
4  *
5  * This software may be distributed under the terms of the BSD license.
6  * See README for more details.
7  */
8 
9 #include "includes.h"
10 #include <nspr/prtypes.h>
11 #include <nspr/plarenas.h>
12 #include <nspr/plhash.h>
13 #include <nspr/prio.h>
14 #include <nspr/prclist.h>
15 #include <nspr/prlock.h>
16 #include <nspr/prinit.h>
17 #include <nspr/prerror.h>
18 #include <nspr/prmem.h>
19 #include <nss/nss.h>
20 #include <nss/nssilckt.h>
21 #include <nss/ssl.h>
22 #include <nss/pk11func.h>
23 #include <nss/secerr.h>
24 
25 #include "common.h"
26 #include "tls.h"
27 
28 static int tls_nss_ref_count = 0;
29 
30 static PRDescIdentity nss_layer_id;
31 
32 
33 struct tls_connection {
34 	PRFileDesc *fd;
35 
36 	int established;
37 	int verify_peer;
38 	u8 *push_buf, *pull_buf, *pull_buf_offset;
39 	size_t push_buf_len, pull_buf_len;
40 };
41 
42 
nss_io_close(PRFileDesc * fd)43 static PRStatus nss_io_close(PRFileDesc *fd)
44 {
45 	wpa_printf(MSG_DEBUG, "NSS: I/O close");
46 	return PR_SUCCESS;
47 }
48 
49 
nss_io_read(PRFileDesc * fd,void * buf,PRInt32 amount)50 static PRInt32 nss_io_read(PRFileDesc *fd, void *buf, PRInt32 amount)
51 {
52 	wpa_printf(MSG_DEBUG, "NSS: I/O read(%d)", amount);
53 	return PR_FAILURE;
54 }
55 
56 
nss_io_write(PRFileDesc * fd,const void * buf,PRInt32 amount)57 static PRInt32 nss_io_write(PRFileDesc *fd, const void *buf, PRInt32 amount)
58 {
59 	wpa_printf(MSG_DEBUG, "NSS: I/O write(%d)", amount);
60 	return PR_FAILURE;
61 }
62 
63 
nss_io_writev(PRFileDesc * fd,const PRIOVec * iov,PRInt32 iov_size,PRIntervalTime timeout)64 static PRInt32 nss_io_writev(PRFileDesc *fd, const PRIOVec *iov,
65 			     PRInt32 iov_size, PRIntervalTime timeout)
66 {
67 	wpa_printf(MSG_DEBUG, "NSS: I/O writev(%d)", iov_size);
68 	return PR_FAILURE;
69 }
70 
71 
nss_io_recv(PRFileDesc * fd,void * buf,PRInt32 amount,PRIntn flags,PRIntervalTime timeout)72 static PRInt32 nss_io_recv(PRFileDesc *fd, void *buf, PRInt32 amount,
73 			   PRIntn flags, PRIntervalTime timeout)
74 {
75 	struct tls_connection *conn = (struct tls_connection *) fd->secret;
76 	u8 *end;
77 
78 	wpa_printf(MSG_DEBUG, "NSS: I/O recv(%d)", amount);
79 
80 	if (conn->pull_buf == NULL) {
81 		wpa_printf(MSG_DEBUG, "NSS: No data available to be read yet");
82 		return PR_FAILURE;
83 	}
84 
85 	end = conn->pull_buf + conn->pull_buf_len;
86 	if (end - conn->pull_buf_offset < amount)
87 		amount = end - conn->pull_buf_offset;
88 	os_memcpy(buf, conn->pull_buf_offset, amount);
89 	conn->pull_buf_offset += amount;
90 	if (conn->pull_buf_offset == end) {
91 		wpa_printf(MSG_DEBUG, "%s - pull_buf consumed", __func__);
92 		os_free(conn->pull_buf);
93 		conn->pull_buf = conn->pull_buf_offset = NULL;
94 		conn->pull_buf_len = 0;
95 	} else {
96 		wpa_printf(MSG_DEBUG, "%s - %lu bytes remaining in pull_buf",
97 			   __func__,
98 			   (unsigned long) (end - conn->pull_buf_offset));
99 	}
100 	return amount;
101 }
102 
103 
nss_io_send(PRFileDesc * fd,const void * buf,PRInt32 amount,PRIntn flags,PRIntervalTime timeout)104 static PRInt32 nss_io_send(PRFileDesc *fd, const void *buf, PRInt32 amount,
105 			   PRIntn flags, PRIntervalTime timeout)
106 {
107 	struct tls_connection *conn = (struct tls_connection *) fd->secret;
108 	u8 *nbuf;
109 
110 	wpa_printf(MSG_DEBUG, "NSS: I/O %s", __func__);
111 	wpa_hexdump(MSG_MSGDUMP, "NSS: I/O send data", buf, amount);
112 
113 	nbuf = os_realloc(conn->push_buf, conn->push_buf_len + amount);
114 	if (nbuf == NULL) {
115 		wpa_printf(MSG_ERROR, "NSS: Failed to allocate memory for the "
116 			   "data to be sent");
117 		return PR_FAILURE;
118 	}
119 	os_memcpy(nbuf + conn->push_buf_len, buf, amount);
120 	conn->push_buf = nbuf;
121 	conn->push_buf_len += amount;
122 
123 	return amount;
124 }
125 
126 
nss_io_recvfrom(PRFileDesc * fd,void * buf,PRInt32 amount,PRIntn flags,PRNetAddr * addr,PRIntervalTime timeout)127 static PRInt32 nss_io_recvfrom(PRFileDesc *fd, void *buf, PRInt32 amount,
128 			       PRIntn flags, PRNetAddr *addr,
129 			       PRIntervalTime timeout)
130 {
131 	wpa_printf(MSG_DEBUG, "NSS: I/O %s", __func__);
132 	return PR_FAILURE;
133 }
134 
135 
nss_io_sendto(PRFileDesc * fd,const void * buf,PRInt32 amount,PRIntn flags,const PRNetAddr * addr,PRIntervalTime timeout)136 static PRInt32 nss_io_sendto(PRFileDesc *fd, const void *buf, PRInt32 amount,
137 			     PRIntn flags, const PRNetAddr *addr,
138 			     PRIntervalTime timeout)
139 {
140 	wpa_printf(MSG_DEBUG, "NSS: I/O %s", __func__);
141 	return PR_FAILURE;
142 }
143 
144 
nss_io_getpeername(PRFileDesc * fd,PRNetAddr * addr)145 static PRStatus nss_io_getpeername(PRFileDesc *fd, PRNetAddr *addr)
146 {
147 	wpa_printf(MSG_DEBUG, "NSS: I/O getpeername");
148 
149 	/*
150 	 * It Looks like NSS only supports IPv4 and IPv6 TCP sockets. Provide a
151 	 * fake IPv4 address to work around this even though we are not really
152 	 * using TCP.
153 	 */
154 	os_memset(addr, 0, sizeof(*addr));
155 	addr->inet.family = PR_AF_INET;
156 
157 	return PR_SUCCESS;
158 }
159 
160 
nss_io_getsocketoption(PRFileDesc * fd,PRSocketOptionData * data)161 static PRStatus nss_io_getsocketoption(PRFileDesc *fd,
162 				       PRSocketOptionData *data)
163 {
164 	switch (data->option) {
165 	case PR_SockOpt_Nonblocking:
166 		wpa_printf(MSG_DEBUG, "NSS: I/O getsocketoption(Nonblocking)");
167 		data->value.non_blocking = PR_TRUE;
168 		return PR_SUCCESS;
169 	default:
170 		wpa_printf(MSG_DEBUG, "NSS: I/O getsocketoption(%d)",
171 			   data->option);
172 		return PR_FAILURE;
173 	}
174 }
175 
176 
177 static const PRIOMethods nss_io = {
178 	PR_DESC_LAYERED,
179 	nss_io_close,
180 	nss_io_read,
181 	nss_io_write,
182 	NULL /* available */,
183 	NULL /* available64 */,
184 	NULL /* fsync */,
185 	NULL /* fseek */,
186 	NULL /* fseek64 */,
187 	NULL /* fileinfo */,
188 	NULL /* fileinfo64 */,
189 	nss_io_writev,
190 	NULL /* connect */,
191 	NULL /* accept */,
192 	NULL /* bind */,
193 	NULL /* listen */,
194 	NULL /* shutdown */,
195 	nss_io_recv,
196 	nss_io_send,
197 	nss_io_recvfrom,
198 	nss_io_sendto,
199 	NULL /* poll */,
200 	NULL /* acceptread */,
201 	NULL /* transmitfile */,
202 	NULL /* getsockname */,
203 	nss_io_getpeername,
204 	NULL /* reserved_fn_6 */,
205 	NULL /* reserved_fn_5 */,
206 	nss_io_getsocketoption,
207 	NULL /* setsocketoption */,
208 	NULL /* sendfile */,
209 	NULL /* connectcontinue */,
210 	NULL /* reserved_fn_3 */,
211 	NULL /* reserved_fn_2 */,
212 	NULL /* reserved_fn_1 */,
213 	NULL /* reserved_fn_0 */
214 };
215 
216 
nss_password_cb(PK11SlotInfo * slot,PRBool retry,void * arg)217 static char * nss_password_cb(PK11SlotInfo *slot, PRBool retry, void *arg)
218 {
219 	wpa_printf(MSG_ERROR, "NSS: TODO - %s", __func__);
220 	return NULL;
221 }
222 
223 
tls_init(const struct tls_config * conf)224 void * tls_init(const struct tls_config *conf)
225 {
226 	char *dir;
227 
228 	tls_nss_ref_count++;
229 	if (tls_nss_ref_count > 1)
230 		return (void *) 1;
231 
232 	PR_Init(PR_SYSTEM_THREAD, PR_PRIORITY_NORMAL, 1);
233 
234 	nss_layer_id = PR_GetUniqueIdentity("wpa_supplicant");
235 
236 	PK11_SetPasswordFunc(nss_password_cb);
237 
238 	dir = getenv("SSL_DIR");
239 	if (dir) {
240 		if (NSS_Init(dir) != SECSuccess) {
241 			wpa_printf(MSG_ERROR, "NSS: NSS_Init(cert_dir=%s) "
242 				   "failed", dir);
243 			return NULL;
244 		}
245 	} else {
246 		if (NSS_NoDB_Init(NULL) != SECSuccess) {
247 			wpa_printf(MSG_ERROR, "NSS: NSS_NoDB_Init(NULL) "
248 				   "failed");
249 			return NULL;
250 		}
251 	}
252 
253 	if (SSL_OptionSetDefault(SSL_V2_COMPATIBLE_HELLO, PR_FALSE) !=
254 	    SECSuccess ||
255 	    SSL_OptionSetDefault(SSL_ENABLE_SSL3, PR_FALSE) != SECSuccess ||
256 	    SSL_OptionSetDefault(SSL_ENABLE_SSL2, PR_FALSE) != SECSuccess ||
257 	    SSL_OptionSetDefault(SSL_ENABLE_TLS, PR_TRUE) != SECSuccess) {
258 		wpa_printf(MSG_ERROR, "NSS: SSL_OptionSetDefault failed");
259 		return NULL;
260 	}
261 
262 	if (NSS_SetDomesticPolicy() != SECSuccess) {
263 		wpa_printf(MSG_ERROR, "NSS: NSS_SetDomesticPolicy() failed");
264 		return NULL;
265 	}
266 
267 	return (void *) 1;
268 }
269 
tls_deinit(void * ssl_ctx)270 void tls_deinit(void *ssl_ctx)
271 {
272 	tls_nss_ref_count--;
273 	if (tls_nss_ref_count == 0) {
274 		if (NSS_Shutdown() != SECSuccess)
275 			wpa_printf(MSG_ERROR, "NSS: NSS_Shutdown() failed");
276 	}
277 }
278 
279 
tls_get_errors(void * tls_ctx)280 int tls_get_errors(void *tls_ctx)
281 {
282 	return 0;
283 }
284 
285 
nss_bad_cert_cb(void * arg,PRFileDesc * fd)286 static SECStatus nss_bad_cert_cb(void *arg, PRFileDesc *fd)
287 {
288 	struct tls_connection *conn = arg;
289 	SECStatus res = SECSuccess;
290 	PRErrorCode err;
291 	CERTCertificate *cert;
292 	char *subject, *issuer;
293 
294 	err = PR_GetError();
295 	if (IS_SEC_ERROR(err))
296 		wpa_printf(MSG_DEBUG, "NSS: Bad Server Certificate (sec err "
297 			   "%d)", err - SEC_ERROR_BASE);
298 	else
299 		wpa_printf(MSG_DEBUG, "NSS: Bad Server Certificate (err %d)",
300 			   err);
301 	cert = SSL_PeerCertificate(fd);
302 	subject = CERT_NameToAscii(&cert->subject);
303 	issuer = CERT_NameToAscii(&cert->issuer);
304 	wpa_printf(MSG_DEBUG, "NSS: Peer certificate subject='%s' issuer='%s'",
305 		   subject, issuer);
306 	CERT_DestroyCertificate(cert);
307 	PR_Free(subject);
308 	PR_Free(issuer);
309 	if (conn->verify_peer)
310 		res = SECFailure;
311 
312 	return res;
313 }
314 
315 
nss_handshake_cb(PRFileDesc * fd,void * client_data)316 static void nss_handshake_cb(PRFileDesc *fd, void *client_data)
317 {
318 	struct tls_connection *conn = client_data;
319 	wpa_printf(MSG_DEBUG, "NSS: Handshake completed");
320 	conn->established = 1;
321 }
322 
323 
tls_connection_init(void * tls_ctx)324 struct tls_connection * tls_connection_init(void *tls_ctx)
325 {
326 	struct tls_connection *conn;
327 
328 	conn = os_zalloc(sizeof(*conn));
329 	if (conn == NULL)
330 		return NULL;
331 
332 	conn->fd = PR_CreateIOLayerStub(nss_layer_id, &nss_io);
333 	if (conn->fd == NULL) {
334 		os_free(conn);
335 		return NULL;
336 	}
337 	conn->fd->secret = (void *) conn;
338 
339 	conn->fd = SSL_ImportFD(NULL, conn->fd);
340 	if (conn->fd == NULL) {
341 		os_free(conn);
342 		return NULL;
343 	}
344 
345 	if (SSL_OptionSet(conn->fd, SSL_SECURITY, PR_TRUE) != SECSuccess ||
346 	    SSL_OptionSet(conn->fd, SSL_HANDSHAKE_AS_CLIENT, PR_TRUE) !=
347 	    SECSuccess ||
348 	    SSL_OptionSet(conn->fd, SSL_HANDSHAKE_AS_SERVER, PR_FALSE) !=
349 	    SECSuccess ||
350 	    SSL_OptionSet(conn->fd, SSL_ENABLE_TLS, PR_TRUE) != SECSuccess ||
351 	    SSL_BadCertHook(conn->fd, nss_bad_cert_cb, conn) != SECSuccess ||
352 	    SSL_HandshakeCallback(conn->fd, nss_handshake_cb, conn) !=
353 	    SECSuccess) {
354 		wpa_printf(MSG_ERROR, "NSS: Failed to set options");
355 		PR_Close(conn->fd);
356 		os_free(conn);
357 		return NULL;
358 	}
359 
360 	SSL_ResetHandshake(conn->fd, PR_FALSE);
361 
362 	return conn;
363 }
364 
365 
tls_connection_deinit(void * tls_ctx,struct tls_connection * conn)366 void tls_connection_deinit(void *tls_ctx, struct tls_connection *conn)
367 {
368 	PR_Close(conn->fd);
369 	os_free(conn->push_buf);
370 	os_free(conn->pull_buf);
371 	os_free(conn);
372 }
373 
374 
tls_connection_established(void * tls_ctx,struct tls_connection * conn)375 int tls_connection_established(void *tls_ctx, struct tls_connection *conn)
376 {
377 	return conn->established;
378 }
379 
380 
tls_connection_shutdown(void * tls_ctx,struct tls_connection * conn)381 int tls_connection_shutdown(void *tls_ctx, struct tls_connection *conn)
382 {
383 	return -1;
384 }
385 
386 
tls_connection_set_params(void * tls_ctx,struct tls_connection * conn,const struct tls_connection_params * params)387 int tls_connection_set_params(void *tls_ctx, struct tls_connection *conn,
388 			      const struct tls_connection_params *params)
389 {
390 	wpa_printf(MSG_ERROR, "NSS: TODO - %s", __func__);
391 	return 0;
392 }
393 
394 
tls_global_set_params(void * tls_ctx,const struct tls_connection_params * params)395 int tls_global_set_params(void *tls_ctx,
396 			  const struct tls_connection_params *params)
397 {
398 	return -1;
399 }
400 
401 
tls_global_set_verify(void * tls_ctx,int check_crl)402 int tls_global_set_verify(void *tls_ctx, int check_crl)
403 {
404 	return -1;
405 }
406 
407 
tls_connection_set_verify(void * tls_ctx,struct tls_connection * conn,int verify_peer)408 int tls_connection_set_verify(void *tls_ctx, struct tls_connection *conn,
409 			      int verify_peer)
410 {
411 	conn->verify_peer = verify_peer;
412 	return 0;
413 }
414 
415 
tls_connection_get_keys(void * tls_ctx,struct tls_connection * conn,struct tls_keys * keys)416 int tls_connection_get_keys(void *tls_ctx, struct tls_connection *conn,
417 			    struct tls_keys *keys)
418 {
419 	/* NSS does not export master secret or client/server random. */
420 	return -1;
421 }
422 
423 
tls_connection_prf(void * tls_ctx,struct tls_connection * conn,const char * label,int server_random_first,u8 * out,size_t out_len)424 int tls_connection_prf(void *tls_ctx, struct tls_connection *conn,
425 		       const char *label, int server_random_first,
426 		       u8 *out, size_t out_len)
427 {
428 	if (conn == NULL || server_random_first) {
429 		wpa_printf(MSG_INFO, "NSS: Unsupported PRF request "
430 			   "(server_random_first=%d)",
431 			   server_random_first);
432 		return -1;
433 	}
434 
435 	if (SSL_ExportKeyingMaterial(conn->fd, label, NULL, 0, out, out_len) !=
436 	    SECSuccess) {
437 		wpa_printf(MSG_INFO, "NSS: Failed to use TLS extractor "
438 			   "(label='%s' out_len=%d", label, (int) out_len);
439 		return -1;
440 	}
441 
442 	return 0;
443 }
444 
445 
tls_connection_handshake(void * tls_ctx,struct tls_connection * conn,const struct wpabuf * in_data,struct wpabuf ** appl_data)446 struct wpabuf * tls_connection_handshake(void *tls_ctx,
447 					 struct tls_connection *conn,
448 					 const struct wpabuf *in_data,
449 					 struct wpabuf **appl_data)
450 {
451 	struct wpabuf *out_data;
452 
453 	wpa_printf(MSG_DEBUG, "NSS: handshake: in_len=%u",
454 		   in_data ? (unsigned int) wpabuf_len(in_data) : 0);
455 
456 	if (appl_data)
457 		*appl_data = NULL;
458 
459 	if (in_data && wpabuf_len(in_data) > 0) {
460 		if (conn->pull_buf) {
461 			wpa_printf(MSG_DEBUG, "%s - %lu bytes remaining in "
462 				   "pull_buf", __func__,
463 				   (unsigned long) conn->pull_buf_len);
464 			os_free(conn->pull_buf);
465 		}
466 		conn->pull_buf = os_malloc(wpabuf_len(in_data));
467 		if (conn->pull_buf == NULL)
468 			return NULL;
469 		os_memcpy(conn->pull_buf, wpabuf_head(in_data),
470 			  wpabuf_len(in_data));
471 		conn->pull_buf_offset = conn->pull_buf;
472 		conn->pull_buf_len = wpabuf_len(in_data);
473 	}
474 
475 	SSL_ForceHandshake(conn->fd);
476 
477 	if (conn->established && conn->push_buf == NULL) {
478 		/* Need to return something to get final TLS ACK. */
479 		conn->push_buf = os_malloc(1);
480 	}
481 
482 	if (conn->push_buf == NULL)
483 		return NULL;
484 	out_data = wpabuf_alloc_ext_data(conn->push_buf, conn->push_buf_len);
485 	if (out_data == NULL)
486 		os_free(conn->push_buf);
487 	conn->push_buf = NULL;
488 	conn->push_buf_len = 0;
489 	return out_data;
490 }
491 
492 
tls_connection_server_handshake(void * tls_ctx,struct tls_connection * conn,const struct wpabuf * in_data,struct wpabuf ** appl_data)493 struct wpabuf * tls_connection_server_handshake(void *tls_ctx,
494 						struct tls_connection *conn,
495 						const struct wpabuf *in_data,
496 						struct wpabuf **appl_data)
497 {
498 	return NULL;
499 }
500 
501 
tls_connection_encrypt(void * tls_ctx,struct tls_connection * conn,const struct wpabuf * in_data)502 struct wpabuf * tls_connection_encrypt(void *tls_ctx,
503 				       struct tls_connection *conn,
504 				       const struct wpabuf *in_data)
505 {
506 	PRInt32 res;
507 	struct wpabuf *buf;
508 
509 	wpa_printf(MSG_DEBUG, "NSS: encrypt %d bytes",
510 		   (int) wpabuf_len(in_data));
511 	res = PR_Send(conn->fd, wpabuf_head(in_data), wpabuf_len(in_data), 0,
512 		      0);
513 	if (res < 0) {
514 		wpa_printf(MSG_ERROR, "NSS: Encryption failed");
515 		return NULL;
516 	}
517 	if (conn->push_buf == NULL)
518 		return NULL;
519 	buf = wpabuf_alloc_ext_data(conn->push_buf, conn->push_buf_len);
520 	if (buf == NULL)
521 		os_free(conn->push_buf);
522 	conn->push_buf = NULL;
523 	conn->push_buf_len = 0;
524 	return buf;
525 }
526 
527 
tls_connection_decrypt(void * tls_ctx,struct tls_connection * conn,const struct wpabuf * in_data)528 struct wpabuf * tls_connection_decrypt(void *tls_ctx,
529 				       struct tls_connection *conn,
530 				       const struct wpabuf *in_data)
531 {
532 	PRInt32 res;
533 	struct wpabuf *out;
534 
535 	wpa_printf(MSG_DEBUG, "NSS: decrypt %d bytes",
536 		   (int) wpabuf_len(in_data));
537 	if (conn->pull_buf) {
538 		wpa_printf(MSG_DEBUG, "%s - %lu bytes remaining in "
539 			   "pull_buf", __func__,
540 			   (unsigned long) conn->pull_buf_len);
541 		os_free(conn->pull_buf);
542 	}
543 	conn->pull_buf = os_malloc(wpabuf_len(in_data));
544 	if (conn->pull_buf == NULL)
545 		return NULL;
546 	os_memcpy(conn->pull_buf, wpabuf_head(in_data), wpabuf_len(in_data));
547 	conn->pull_buf_offset = conn->pull_buf;
548 	conn->pull_buf_len = wpabuf_len(in_data);
549 
550 	/*
551 	 * Even though we try to disable TLS compression, it is possible that
552 	 * this cannot be done with all TLS libraries. Add extra buffer space
553 	 * to handle the possibility of the decrypted data being longer than
554 	 * input data.
555 	 */
556 	out = wpabuf_alloc((wpabuf_len(in_data) + 500) * 3);
557 	if (out == NULL)
558 		return NULL;
559 
560 	res = PR_Recv(conn->fd, wpabuf_mhead(out), wpabuf_size(out), 0, 0);
561 	wpa_printf(MSG_DEBUG, "NSS: PR_Recv: %d", res);
562 	if (res < 0) {
563 		wpabuf_free(out);
564 		return NULL;
565 	}
566 	wpabuf_put(out, res);
567 
568 	return out;
569 }
570 
571 
tls_connection_resumed(void * tls_ctx,struct tls_connection * conn)572 int tls_connection_resumed(void *tls_ctx, struct tls_connection *conn)
573 {
574 	return 0;
575 }
576 
577 
tls_connection_set_cipher_list(void * tls_ctx,struct tls_connection * conn,u8 * ciphers)578 int tls_connection_set_cipher_list(void *tls_ctx, struct tls_connection *conn,
579 				   u8 *ciphers)
580 {
581 	return -1;
582 }
583 
584 
tls_get_cipher(void * tls_ctx,struct tls_connection * conn,char * buf,size_t buflen)585 int tls_get_cipher(void *tls_ctx, struct tls_connection *conn,
586 		   char *buf, size_t buflen)
587 {
588 	return -1;
589 }
590 
591 
tls_connection_enable_workaround(void * tls_ctx,struct tls_connection * conn)592 int tls_connection_enable_workaround(void *tls_ctx,
593 				     struct tls_connection *conn)
594 {
595 	return -1;
596 }
597 
598 
tls_connection_client_hello_ext(void * tls_ctx,struct tls_connection * conn,int ext_type,const u8 * data,size_t data_len)599 int tls_connection_client_hello_ext(void *tls_ctx, struct tls_connection *conn,
600 				    int ext_type, const u8 *data,
601 				    size_t data_len)
602 {
603 	return -1;
604 }
605 
606 
tls_connection_get_failed(void * tls_ctx,struct tls_connection * conn)607 int tls_connection_get_failed(void *tls_ctx, struct tls_connection *conn)
608 {
609 	return 0;
610 }
611 
612 
tls_connection_get_read_alerts(void * tls_ctx,struct tls_connection * conn)613 int tls_connection_get_read_alerts(void *tls_ctx, struct tls_connection *conn)
614 {
615 	return 0;
616 }
617 
618 
tls_connection_get_write_alerts(void * tls_ctx,struct tls_connection * conn)619 int tls_connection_get_write_alerts(void *tls_ctx,
620 				    struct tls_connection *conn)
621 {
622 	return 0;
623 }
624 
625 
tls_connection_get_keyblock_size(void * tls_ctx,struct tls_connection * conn)626 int tls_connection_get_keyblock_size(void *tls_ctx,
627 				     struct tls_connection *conn)
628 {
629 	return -1;
630 }
631 
632 
tls_capabilities(void * tls_ctx)633 unsigned int tls_capabilities(void *tls_ctx)
634 {
635 	return 0;
636 }
637 
638 
tls_connection_set_session_ticket_cb(void * tls_ctx,struct tls_connection * conn,tls_session_ticket_cb cb,void * ctx)639 int tls_connection_set_session_ticket_cb(void *tls_ctx,
640 					 struct tls_connection *conn,
641 					 tls_session_ticket_cb cb,
642 					 void *ctx)
643 {
644 	return -1;
645 }
646