xref: /aosp_15_r20/external/libwebsockets/lib/tls/openssl/openssl-ssl.c (revision 1c60b9aca93fdbc9b5f19b2d2194c91294b22281)
1*1c60b9acSAndroid Build Coastguard Worker /*
2*1c60b9acSAndroid Build Coastguard Worker  * libwebsockets - small server side websockets and web server implementation
3*1c60b9acSAndroid Build Coastguard Worker  *
4*1c60b9acSAndroid Build Coastguard Worker  * Copyright (C) 2010 - 2019 Andy Green <[email protected]>
5*1c60b9acSAndroid Build Coastguard Worker  *
6*1c60b9acSAndroid Build Coastguard Worker  * Permission is hereby granted, free of charge, to any person obtaining a copy
7*1c60b9acSAndroid Build Coastguard Worker  * of this software and associated documentation files (the "Software"), to
8*1c60b9acSAndroid Build Coastguard Worker  * deal in the Software without restriction, including without limitation the
9*1c60b9acSAndroid Build Coastguard Worker  * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
10*1c60b9acSAndroid Build Coastguard Worker  * sell copies of the Software, and to permit persons to whom the Software is
11*1c60b9acSAndroid Build Coastguard Worker  * furnished to do so, subject to the following conditions:
12*1c60b9acSAndroid Build Coastguard Worker  *
13*1c60b9acSAndroid Build Coastguard Worker  * The above copyright notice and this permission notice shall be included in
14*1c60b9acSAndroid Build Coastguard Worker  * all copies or substantial portions of the Software.
15*1c60b9acSAndroid Build Coastguard Worker  *
16*1c60b9acSAndroid Build Coastguard Worker  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17*1c60b9acSAndroid Build Coastguard Worker  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18*1c60b9acSAndroid Build Coastguard Worker  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19*1c60b9acSAndroid Build Coastguard Worker  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20*1c60b9acSAndroid Build Coastguard Worker  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21*1c60b9acSAndroid Build Coastguard Worker  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
22*1c60b9acSAndroid Build Coastguard Worker  * IN THE SOFTWARE.
23*1c60b9acSAndroid Build Coastguard Worker  */
24*1c60b9acSAndroid Build Coastguard Worker 
25*1c60b9acSAndroid Build Coastguard Worker #include "private-lib-core.h"
26*1c60b9acSAndroid Build Coastguard Worker #include "private-lib-tls-openssl.h"
27*1c60b9acSAndroid Build Coastguard Worker 
28*1c60b9acSAndroid Build Coastguard Worker int openssl_websocket_private_data_index,
29*1c60b9acSAndroid Build Coastguard Worker 	   openssl_SSL_CTX_private_data_index;
30*1c60b9acSAndroid Build Coastguard Worker 
31*1c60b9acSAndroid Build Coastguard Worker /*
32*1c60b9acSAndroid Build Coastguard Worker  * Care: many openssl apis return 1 for success.  These are translated to the
33*1c60b9acSAndroid Build Coastguard Worker  * lws convention of 0 for success.
34*1c60b9acSAndroid Build Coastguard Worker  */
35*1c60b9acSAndroid Build Coastguard Worker 
lws_openssl_describe_cipher(struct lws * wsi)36*1c60b9acSAndroid Build Coastguard Worker int lws_openssl_describe_cipher(struct lws *wsi)
37*1c60b9acSAndroid Build Coastguard Worker {
38*1c60b9acSAndroid Build Coastguard Worker #if !defined(LWS_WITH_NO_LOGS) && !defined(USE_WOLFSSL)
39*1c60b9acSAndroid Build Coastguard Worker 	int np = -1;
40*1c60b9acSAndroid Build Coastguard Worker 	SSL *s = wsi->tls.ssl;
41*1c60b9acSAndroid Build Coastguard Worker 
42*1c60b9acSAndroid Build Coastguard Worker 	SSL_get_cipher_bits(s, &np);
43*1c60b9acSAndroid Build Coastguard Worker 	lwsl_info("%s: %s: %s, %s, %d bits, %s\n", __func__, lws_wsi_tag(wsi),
44*1c60b9acSAndroid Build Coastguard Worker 			SSL_get_cipher_name(s), SSL_get_cipher(s), np,
45*1c60b9acSAndroid Build Coastguard Worker 			SSL_get_cipher_version(s));
46*1c60b9acSAndroid Build Coastguard Worker #endif
47*1c60b9acSAndroid Build Coastguard Worker 
48*1c60b9acSAndroid Build Coastguard Worker 	return 0;
49*1c60b9acSAndroid Build Coastguard Worker }
50*1c60b9acSAndroid Build Coastguard Worker 
lws_ssl_get_error(struct lws * wsi,int n)51*1c60b9acSAndroid Build Coastguard Worker int lws_ssl_get_error(struct lws *wsi, int n)
52*1c60b9acSAndroid Build Coastguard Worker {
53*1c60b9acSAndroid Build Coastguard Worker 	int m;
54*1c60b9acSAndroid Build Coastguard Worker 
55*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->tls.ssl)
56*1c60b9acSAndroid Build Coastguard Worker 		return 99;
57*1c60b9acSAndroid Build Coastguard Worker 
58*1c60b9acSAndroid Build Coastguard Worker 	m = SSL_get_error(wsi->tls.ssl, n);
59*1c60b9acSAndroid Build Coastguard Worker        lwsl_debug("%s: %p %d -> %d (errno %d)\n", __func__, wsi->tls.ssl, n, m, LWS_ERRNO);
60*1c60b9acSAndroid Build Coastguard Worker 	if (m == SSL_ERROR_SSL)
61*1c60b9acSAndroid Build Coastguard Worker 		lws_tls_err_describe_clear();
62*1c60b9acSAndroid Build Coastguard Worker 
63*1c60b9acSAndroid Build Coastguard Worker        // assert (LWS_ERRNO != 9);
64*1c60b9acSAndroid Build Coastguard Worker 
65*1c60b9acSAndroid Build Coastguard Worker 	return m;
66*1c60b9acSAndroid Build Coastguard Worker }
67*1c60b9acSAndroid Build Coastguard Worker 
68*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SERVER)
69*1c60b9acSAndroid Build Coastguard Worker static int
lws_context_init_ssl_pem_passwd_cb(char * buf,int size,int rwflag,void * userdata)70*1c60b9acSAndroid Build Coastguard Worker lws_context_init_ssl_pem_passwd_cb(char *buf, int size, int rwflag,
71*1c60b9acSAndroid Build Coastguard Worker 				   void *userdata)
72*1c60b9acSAndroid Build Coastguard Worker {
73*1c60b9acSAndroid Build Coastguard Worker 	struct lws_context_creation_info * info =
74*1c60b9acSAndroid Build Coastguard Worker 			(struct lws_context_creation_info *)userdata;
75*1c60b9acSAndroid Build Coastguard Worker 
76*1c60b9acSAndroid Build Coastguard Worker 	strncpy(buf, info->ssl_private_key_password, (unsigned int)size);
77*1c60b9acSAndroid Build Coastguard Worker 	buf[size - 1] = '\0';
78*1c60b9acSAndroid Build Coastguard Worker 
79*1c60b9acSAndroid Build Coastguard Worker 	return (int)strlen(buf);
80*1c60b9acSAndroid Build Coastguard Worker }
81*1c60b9acSAndroid Build Coastguard Worker #endif
82*1c60b9acSAndroid Build Coastguard Worker 
83*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_CLIENT)
84*1c60b9acSAndroid Build Coastguard Worker static int
lws_context_init_ssl_pem_passwd_client_cb(char * buf,int size,int rwflag,void * userdata)85*1c60b9acSAndroid Build Coastguard Worker lws_context_init_ssl_pem_passwd_client_cb(char *buf, int size, int rwflag,
86*1c60b9acSAndroid Build Coastguard Worker 					  void *userdata)
87*1c60b9acSAndroid Build Coastguard Worker {
88*1c60b9acSAndroid Build Coastguard Worker 	struct lws_context_creation_info * info =
89*1c60b9acSAndroid Build Coastguard Worker 			(struct lws_context_creation_info *)userdata;
90*1c60b9acSAndroid Build Coastguard Worker 	const char *p = info->ssl_private_key_password;
91*1c60b9acSAndroid Build Coastguard Worker 
92*1c60b9acSAndroid Build Coastguard Worker 	if (info->client_ssl_private_key_password)
93*1c60b9acSAndroid Build Coastguard Worker 		p = info->client_ssl_private_key_password;
94*1c60b9acSAndroid Build Coastguard Worker 
95*1c60b9acSAndroid Build Coastguard Worker 	strncpy(buf, p, (unsigned int)size);
96*1c60b9acSAndroid Build Coastguard Worker 	buf[size - 1] = '\0';
97*1c60b9acSAndroid Build Coastguard Worker 
98*1c60b9acSAndroid Build Coastguard Worker 	return (int)strlen(buf);
99*1c60b9acSAndroid Build Coastguard Worker }
100*1c60b9acSAndroid Build Coastguard Worker #endif
101*1c60b9acSAndroid Build Coastguard Worker 
102*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_bind_passphrase(SSL_CTX * ssl_ctx,int is_client,const struct lws_context_creation_info * info)103*1c60b9acSAndroid Build Coastguard Worker lws_ssl_bind_passphrase(SSL_CTX *ssl_ctx, int is_client,
104*1c60b9acSAndroid Build Coastguard Worker 			const struct lws_context_creation_info *info)
105*1c60b9acSAndroid Build Coastguard Worker {
106*1c60b9acSAndroid Build Coastguard Worker 	if (
107*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SERVER)
108*1c60b9acSAndroid Build Coastguard Worker 		!info->ssl_private_key_password
109*1c60b9acSAndroid Build Coastguard Worker #endif
110*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SERVER) && defined(LWS_WITH_CLIENT)
111*1c60b9acSAndroid Build Coastguard Worker 			&&
112*1c60b9acSAndroid Build Coastguard Worker #endif
113*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_CLIENT)
114*1c60b9acSAndroid Build Coastguard Worker 	    !info->client_ssl_private_key_password
115*1c60b9acSAndroid Build Coastguard Worker #endif
116*1c60b9acSAndroid Build Coastguard Worker 	    )
117*1c60b9acSAndroid Build Coastguard Worker 		return;
118*1c60b9acSAndroid Build Coastguard Worker 	/*
119*1c60b9acSAndroid Build Coastguard Worker 	 * password provided, set ssl callback and user data
120*1c60b9acSAndroid Build Coastguard Worker 	 * for checking password which will be trigered during
121*1c60b9acSAndroid Build Coastguard Worker 	 * SSL_CTX_use_PrivateKey_file function
122*1c60b9acSAndroid Build Coastguard Worker 	 */
123*1c60b9acSAndroid Build Coastguard Worker 	SSL_CTX_set_default_passwd_cb_userdata(ssl_ctx, (void *)info);
124*1c60b9acSAndroid Build Coastguard Worker 	SSL_CTX_set_default_passwd_cb(ssl_ctx, is_client ?
125*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_CLIENT)
126*1c60b9acSAndroid Build Coastguard Worker 				      lws_context_init_ssl_pem_passwd_client_cb:
127*1c60b9acSAndroid Build Coastguard Worker #else
128*1c60b9acSAndroid Build Coastguard Worker 					NULL:
129*1c60b9acSAndroid Build Coastguard Worker #endif
130*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SERVER)
131*1c60b9acSAndroid Build Coastguard Worker 				      lws_context_init_ssl_pem_passwd_cb
132*1c60b9acSAndroid Build Coastguard Worker #else
133*1c60b9acSAndroid Build Coastguard Worker 				      	NULL
134*1c60b9acSAndroid Build Coastguard Worker #endif
135*1c60b9acSAndroid Build Coastguard Worker 				  );
136*1c60b9acSAndroid Build Coastguard Worker }
137*1c60b9acSAndroid Build Coastguard Worker 
138*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_CLIENT)
139*1c60b9acSAndroid Build Coastguard Worker static void
lws_ssl_destroy_client_ctx(struct lws_vhost * vhost)140*1c60b9acSAndroid Build Coastguard Worker lws_ssl_destroy_client_ctx(struct lws_vhost *vhost)
141*1c60b9acSAndroid Build Coastguard Worker {
142*1c60b9acSAndroid Build Coastguard Worker 	if (vhost->tls.user_supplied_ssl_ctx || !vhost->tls.ssl_client_ctx)
143*1c60b9acSAndroid Build Coastguard Worker 		return;
144*1c60b9acSAndroid Build Coastguard Worker 
145*1c60b9acSAndroid Build Coastguard Worker 	if (vhost->tls.tcr && --vhost->tls.tcr->refcount)
146*1c60b9acSAndroid Build Coastguard Worker 		return;
147*1c60b9acSAndroid Build Coastguard Worker 
148*1c60b9acSAndroid Build Coastguard Worker 	SSL_CTX_free(vhost->tls.ssl_client_ctx);
149*1c60b9acSAndroid Build Coastguard Worker 	vhost->tls.ssl_client_ctx = NULL;
150*1c60b9acSAndroid Build Coastguard Worker 
151*1c60b9acSAndroid Build Coastguard Worker 	vhost->context->tls.count_client_contexts--;
152*1c60b9acSAndroid Build Coastguard Worker 
153*1c60b9acSAndroid Build Coastguard Worker 	if (vhost->tls.tcr) {
154*1c60b9acSAndroid Build Coastguard Worker 		lws_dll2_remove(&vhost->tls.tcr->cc_list);
155*1c60b9acSAndroid Build Coastguard Worker 		lws_free(vhost->tls.tcr);
156*1c60b9acSAndroid Build Coastguard Worker 		vhost->tls.tcr = NULL;
157*1c60b9acSAndroid Build Coastguard Worker 	}
158*1c60b9acSAndroid Build Coastguard Worker }
159*1c60b9acSAndroid Build Coastguard Worker #endif
160*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_destroy(struct lws_vhost * vhost)161*1c60b9acSAndroid Build Coastguard Worker lws_ssl_destroy(struct lws_vhost *vhost)
162*1c60b9acSAndroid Build Coastguard Worker {
163*1c60b9acSAndroid Build Coastguard Worker 	if (!lws_check_opt(vhost->context->options,
164*1c60b9acSAndroid Build Coastguard Worker 			   LWS_SERVER_OPTION_DO_SSL_GLOBAL_INIT))
165*1c60b9acSAndroid Build Coastguard Worker 		return;
166*1c60b9acSAndroid Build Coastguard Worker 
167*1c60b9acSAndroid Build Coastguard Worker 	if (vhost->tls.ssl_ctx)
168*1c60b9acSAndroid Build Coastguard Worker 		SSL_CTX_free(vhost->tls.ssl_ctx);
169*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_CLIENT)
170*1c60b9acSAndroid Build Coastguard Worker 	lws_ssl_destroy_client_ctx(vhost);
171*1c60b9acSAndroid Build Coastguard Worker #endif
172*1c60b9acSAndroid Build Coastguard Worker 
173*1c60b9acSAndroid Build Coastguard Worker // after 1.1.0 no need
174*1c60b9acSAndroid Build Coastguard Worker #if (OPENSSL_VERSION_NUMBER <  0x10100000)
175*1c60b9acSAndroid Build Coastguard Worker // <= 1.0.1f = old api, 1.0.1g+ = new api
176*1c60b9acSAndroid Build Coastguard Worker #if (OPENSSL_VERSION_NUMBER <= 0x1000106f) || defined(USE_WOLFSSL)
177*1c60b9acSAndroid Build Coastguard Worker 	ERR_remove_state(0);
178*1c60b9acSAndroid Build Coastguard Worker #else
179*1c60b9acSAndroid Build Coastguard Worker #if OPENSSL_VERSION_NUMBER >= 0x1010005f && \
180*1c60b9acSAndroid Build Coastguard Worker     !defined(LIBRESSL_VERSION_NUMBER) && \
181*1c60b9acSAndroid Build Coastguard Worker     !defined(OPENSSL_IS_BORINGSSL)
182*1c60b9acSAndroid Build Coastguard Worker 	ERR_remove_thread_state();
183*1c60b9acSAndroid Build Coastguard Worker #else
184*1c60b9acSAndroid Build Coastguard Worker 	ERR_remove_thread_state(NULL);
185*1c60b9acSAndroid Build Coastguard Worker #endif
186*1c60b9acSAndroid Build Coastguard Worker #endif
187*1c60b9acSAndroid Build Coastguard Worker 	/* not needed after 1.1.0 */
188*1c60b9acSAndroid Build Coastguard Worker #if  (OPENSSL_VERSION_NUMBER >= 0x10002000) && \
189*1c60b9acSAndroid Build Coastguard Worker      (OPENSSL_VERSION_NUMBER <= 0x10100000)
190*1c60b9acSAndroid Build Coastguard Worker 	SSL_COMP_free_compression_methods();
191*1c60b9acSAndroid Build Coastguard Worker #endif
192*1c60b9acSAndroid Build Coastguard Worker 	ERR_free_strings();
193*1c60b9acSAndroid Build Coastguard Worker 	EVP_cleanup();
194*1c60b9acSAndroid Build Coastguard Worker 	CRYPTO_cleanup_all_ex_data();
195*1c60b9acSAndroid Build Coastguard Worker #endif
196*1c60b9acSAndroid Build Coastguard Worker }
197*1c60b9acSAndroid Build Coastguard Worker 
198*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_capable_read(struct lws * wsi,unsigned char * buf,size_t len)199*1c60b9acSAndroid Build Coastguard Worker lws_ssl_capable_read(struct lws *wsi, unsigned char *buf, size_t len)
200*1c60b9acSAndroid Build Coastguard Worker {
201*1c60b9acSAndroid Build Coastguard Worker 	struct lws_context *context = wsi->a.context;
202*1c60b9acSAndroid Build Coastguard Worker 	struct lws_context_per_thread *pt = &context->pt[(int)wsi->tsi];
203*1c60b9acSAndroid Build Coastguard Worker 	int n = 0, m;
204*1c60b9acSAndroid Build Coastguard Worker 
205*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->tls.ssl)
206*1c60b9acSAndroid Build Coastguard Worker 		return lws_ssl_capable_read_no_ssl(wsi, buf, len);
207*1c60b9acSAndroid Build Coastguard Worker 
208*1c60b9acSAndroid Build Coastguard Worker #ifndef WIN32
209*1c60b9acSAndroid Build Coastguard Worker 	errno = 0;
210*1c60b9acSAndroid Build Coastguard Worker #else
211*1c60b9acSAndroid Build Coastguard Worker   WSASetLastError(0);
212*1c60b9acSAndroid Build Coastguard Worker #endif
213*1c60b9acSAndroid Build Coastguard Worker 	ERR_clear_error();
214*1c60b9acSAndroid Build Coastguard Worker 	n = SSL_read(wsi->tls.ssl, buf, (int)(ssize_t)len);
215*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_PLAT_FREERTOS)
216*1c60b9acSAndroid Build Coastguard Worker 	if (!n && errno == LWS_ENOTCONN) {
217*1c60b9acSAndroid Build Coastguard Worker 		lwsl_debug("%s: SSL_read ENOTCONN\n", lws_wsi_tag(wsi));
218*1c60b9acSAndroid Build Coastguard Worker 		return LWS_SSL_CAPABLE_ERROR;
219*1c60b9acSAndroid Build Coastguard Worker 	}
220*1c60b9acSAndroid Build Coastguard Worker #endif
221*1c60b9acSAndroid Build Coastguard Worker 
222*1c60b9acSAndroid Build Coastguard Worker 	lwsl_debug("%s: SSL_read says %d\n", lws_wsi_tag(wsi), n);
223*1c60b9acSAndroid Build Coastguard Worker 	/* manpage: returning 0 means connection shut down
224*1c60b9acSAndroid Build Coastguard Worker 	 *
225*1c60b9acSAndroid Build Coastguard Worker 	 * 2018-09-10: https://github.com/openssl/openssl/issues/1903
226*1c60b9acSAndroid Build Coastguard Worker 	 *
227*1c60b9acSAndroid Build Coastguard Worker 	 * So, in summary, if you get a 0 or -1 return from SSL_read() /
228*1c60b9acSAndroid Build Coastguard Worker 	 * SSL_write(), you should call SSL_get_error():
229*1c60b9acSAndroid Build Coastguard Worker 	 *
230*1c60b9acSAndroid Build Coastguard Worker 	 *  - If you get back SSL_ERROR_RETURN_ZERO then you know the connection
231*1c60b9acSAndroid Build Coastguard Worker 	 *    has been cleanly shutdown by the peer. To fully close the
232*1c60b9acSAndroid Build Coastguard Worker 	 *    connection you may choose to call SSL_shutdown() to send a
233*1c60b9acSAndroid Build Coastguard Worker 	 *    close_notify back.
234*1c60b9acSAndroid Build Coastguard Worker 	 *
235*1c60b9acSAndroid Build Coastguard Worker 	 *  - If you get back SSL_ERROR_SSL then some kind of internal or
236*1c60b9acSAndroid Build Coastguard Worker 	 *    protocol error has occurred. More details will be on the SSL error
237*1c60b9acSAndroid Build Coastguard Worker 	 *    queue. You can also call SSL_get_shutdown(). If this indicates a
238*1c60b9acSAndroid Build Coastguard Worker 	 *    state of SSL_RECEIVED_SHUTDOWN then you know a fatal alert has
239*1c60b9acSAndroid Build Coastguard Worker 	 *    been received from the peer (if it had been a close_notify then
240*1c60b9acSAndroid Build Coastguard Worker 	 *    SSL_get_error() would have returned SSL_ERROR_RETURN_ZERO).
241*1c60b9acSAndroid Build Coastguard Worker 	 *    SSL_ERROR_SSL is considered fatal - you should not call
242*1c60b9acSAndroid Build Coastguard Worker 	 *    SSL_shutdown() in this case.
243*1c60b9acSAndroid Build Coastguard Worker 	 *
244*1c60b9acSAndroid Build Coastguard Worker 	 *  - If you get back SSL_ERROR_SYSCALL then some kind of fatal (i.e.
245*1c60b9acSAndroid Build Coastguard Worker 	 *    non-retryable) error has occurred in a system call.
246*1c60b9acSAndroid Build Coastguard Worker 	 */
247*1c60b9acSAndroid Build Coastguard Worker 	if (n <= 0) {
248*1c60b9acSAndroid Build Coastguard Worker 		m = lws_ssl_get_error(wsi, n);
249*1c60b9acSAndroid Build Coastguard Worker                lwsl_debug("%s: ssl err %d errno %d\n", lws_wsi_tag(wsi), m, LWS_ERRNO);
250*1c60b9acSAndroid Build Coastguard Worker 		if (m == SSL_ERROR_ZERO_RETURN) /* cleanly shut down */
251*1c60b9acSAndroid Build Coastguard Worker 			goto do_err;
252*1c60b9acSAndroid Build Coastguard Worker 
253*1c60b9acSAndroid Build Coastguard Worker 		/* hm not retryable.. could be 0 size pkt or error  */
254*1c60b9acSAndroid Build Coastguard Worker 
255*1c60b9acSAndroid Build Coastguard Worker 		if (m == SSL_ERROR_SSL || m == SSL_ERROR_SYSCALL ||
256*1c60b9acSAndroid Build Coastguard Worker         LWS_ERRNO == LWS_ENOTCONN) {
257*1c60b9acSAndroid Build Coastguard Worker 
258*1c60b9acSAndroid Build Coastguard Worker 			/* unclean, eg closed conn */
259*1c60b9acSAndroid Build Coastguard Worker 
260*1c60b9acSAndroid Build Coastguard Worker 			wsi->socket_is_permanently_unusable = 1;
261*1c60b9acSAndroid Build Coastguard Worker do_err:
262*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
263*1c60b9acSAndroid Build Coastguard Worker 		if (wsi->a.vhost)
264*1c60b9acSAndroid Build Coastguard Worker 			lws_metric_event(wsi->a.vhost->mt_traffic_rx,
265*1c60b9acSAndroid Build Coastguard Worker 					 METRES_NOGO, 0);
266*1c60b9acSAndroid Build Coastguard Worker #endif
267*1c60b9acSAndroid Build Coastguard Worker 			return LWS_SSL_CAPABLE_ERROR;
268*1c60b9acSAndroid Build Coastguard Worker 		}
269*1c60b9acSAndroid Build Coastguard Worker 
270*1c60b9acSAndroid Build Coastguard Worker 		/* retryable? */
271*1c60b9acSAndroid Build Coastguard Worker 
272*1c60b9acSAndroid Build Coastguard Worker 		if (SSL_want_read(wsi->tls.ssl)) {
273*1c60b9acSAndroid Build Coastguard Worker 			lwsl_debug("%s: WANT_READ\n", __func__);
274*1c60b9acSAndroid Build Coastguard Worker 			lwsl_debug("%s: LWS_SSL_CAPABLE_MORE_SERVICE\n", lws_wsi_tag(wsi));
275*1c60b9acSAndroid Build Coastguard Worker 			return LWS_SSL_CAPABLE_MORE_SERVICE;
276*1c60b9acSAndroid Build Coastguard Worker 		}
277*1c60b9acSAndroid Build Coastguard Worker 		if (SSL_want_write(wsi->tls.ssl)) {
278*1c60b9acSAndroid Build Coastguard Worker 			lwsl_info("%s: WANT_WRITE\n", __func__);
279*1c60b9acSAndroid Build Coastguard Worker 			lwsl_debug("%s: LWS_SSL_CAPABLE_MORE_SERVICE\n", lws_wsi_tag(wsi));
280*1c60b9acSAndroid Build Coastguard Worker 			wsi->tls_read_wanted_write = 1;
281*1c60b9acSAndroid Build Coastguard Worker 			lws_callback_on_writable(wsi);
282*1c60b9acSAndroid Build Coastguard Worker 			return LWS_SSL_CAPABLE_MORE_SERVICE;
283*1c60b9acSAndroid Build Coastguard Worker 		}
284*1c60b9acSAndroid Build Coastguard Worker 
285*1c60b9acSAndroid Build Coastguard Worker 		/* keep on trucking it seems */
286*1c60b9acSAndroid Build Coastguard Worker 	}
287*1c60b9acSAndroid Build Coastguard Worker 
288*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_TLS_LOG_PLAINTEXT_RX)
289*1c60b9acSAndroid Build Coastguard Worker 	/*
290*1c60b9acSAndroid Build Coastguard Worker 	 * If using openssl type tls library, this is the earliest point for all
291*1c60b9acSAndroid Build Coastguard Worker 	 * paths to dump what was received as decrypted data from the tls tunnel
292*1c60b9acSAndroid Build Coastguard Worker 	 */
293*1c60b9acSAndroid Build Coastguard Worker 	lwsl_notice("%s: len %d\n", __func__, n);
294*1c60b9acSAndroid Build Coastguard Worker 	lwsl_hexdump_notice(buf, (unsigned int)n);
295*1c60b9acSAndroid Build Coastguard Worker #endif
296*1c60b9acSAndroid Build Coastguard Worker 
297*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
298*1c60b9acSAndroid Build Coastguard Worker 	if (wsi->a.vhost)
299*1c60b9acSAndroid Build Coastguard Worker 		lws_metric_event(wsi->a.vhost->mt_traffic_rx, METRES_GO, (u_mt_t)n);
300*1c60b9acSAndroid Build Coastguard Worker #endif
301*1c60b9acSAndroid Build Coastguard Worker 
302*1c60b9acSAndroid Build Coastguard Worker 	/*
303*1c60b9acSAndroid Build Coastguard Worker 	 * if it was our buffer that limited what we read,
304*1c60b9acSAndroid Build Coastguard Worker 	 * check if SSL has additional data pending inside SSL buffers.
305*1c60b9acSAndroid Build Coastguard Worker 	 *
306*1c60b9acSAndroid Build Coastguard Worker 	 * Because these won't signal at the network layer with POLLIN
307*1c60b9acSAndroid Build Coastguard Worker 	 * and if we don't realize, this data will sit there forever
308*1c60b9acSAndroid Build Coastguard Worker 	 */
309*1c60b9acSAndroid Build Coastguard Worker 	if (n != (int)(ssize_t)len)
310*1c60b9acSAndroid Build Coastguard Worker 		goto bail;
311*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->tls.ssl)
312*1c60b9acSAndroid Build Coastguard Worker 		goto bail;
313*1c60b9acSAndroid Build Coastguard Worker 
314*1c60b9acSAndroid Build Coastguard Worker 	if (SSL_pending(wsi->tls.ssl)) {
315*1c60b9acSAndroid Build Coastguard Worker 		if (lws_dll2_is_detached(&wsi->tls.dll_pending_tls))
316*1c60b9acSAndroid Build Coastguard Worker 			lws_dll2_add_head(&wsi->tls.dll_pending_tls,
317*1c60b9acSAndroid Build Coastguard Worker 					  &pt->tls.dll_pending_tls_owner);
318*1c60b9acSAndroid Build Coastguard Worker 	} else
319*1c60b9acSAndroid Build Coastguard Worker 		__lws_ssl_remove_wsi_from_buffered_list(wsi);
320*1c60b9acSAndroid Build Coastguard Worker 
321*1c60b9acSAndroid Build Coastguard Worker 	return n;
322*1c60b9acSAndroid Build Coastguard Worker bail:
323*1c60b9acSAndroid Build Coastguard Worker 	lws_ssl_remove_wsi_from_buffered_list(wsi);
324*1c60b9acSAndroid Build Coastguard Worker 
325*1c60b9acSAndroid Build Coastguard Worker 	return n;
326*1c60b9acSAndroid Build Coastguard Worker }
327*1c60b9acSAndroid Build Coastguard Worker 
328*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_pending(struct lws * wsi)329*1c60b9acSAndroid Build Coastguard Worker lws_ssl_pending(struct lws *wsi)
330*1c60b9acSAndroid Build Coastguard Worker {
331*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->tls.ssl)
332*1c60b9acSAndroid Build Coastguard Worker 		return 0;
333*1c60b9acSAndroid Build Coastguard Worker 
334*1c60b9acSAndroid Build Coastguard Worker 	return SSL_pending(wsi->tls.ssl);
335*1c60b9acSAndroid Build Coastguard Worker }
336*1c60b9acSAndroid Build Coastguard Worker 
337*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_capable_write(struct lws * wsi,unsigned char * buf,size_t len)338*1c60b9acSAndroid Build Coastguard Worker lws_ssl_capable_write(struct lws *wsi, unsigned char *buf, size_t len)
339*1c60b9acSAndroid Build Coastguard Worker {
340*1c60b9acSAndroid Build Coastguard Worker 	int n, m;
341*1c60b9acSAndroid Build Coastguard Worker 
342*1c60b9acSAndroid Build Coastguard Worker 
343*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_TLS_LOG_PLAINTEXT_TX)
344*1c60b9acSAndroid Build Coastguard Worker 	/*
345*1c60b9acSAndroid Build Coastguard Worker 	 * If using OpenSSL type tls library, this is the last point for all
346*1c60b9acSAndroid Build Coastguard Worker 	 * paths before sending data into the tls tunnel, where you can dump it
347*1c60b9acSAndroid Build Coastguard Worker 	 * and see what is being sent.
348*1c60b9acSAndroid Build Coastguard Worker 	 */
349*1c60b9acSAndroid Build Coastguard Worker 	lwsl_notice("%s: len %u\n", __func__, (unsigned int)len);
350*1c60b9acSAndroid Build Coastguard Worker 	lwsl_hexdump_notice(buf, len);
351*1c60b9acSAndroid Build Coastguard Worker #endif
352*1c60b9acSAndroid Build Coastguard Worker 
353*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->tls.ssl)
354*1c60b9acSAndroid Build Coastguard Worker 		return lws_ssl_capable_write_no_ssl(wsi, buf, len);
355*1c60b9acSAndroid Build Coastguard Worker 
356*1c60b9acSAndroid Build Coastguard Worker 	errno = 0;
357*1c60b9acSAndroid Build Coastguard Worker 	ERR_clear_error();
358*1c60b9acSAndroid Build Coastguard Worker 	n = SSL_write(wsi->tls.ssl, buf, (int)(ssize_t)len);
359*1c60b9acSAndroid Build Coastguard Worker 	if (n > 0) {
360*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
361*1c60b9acSAndroid Build Coastguard Worker 		if (wsi->a.vhost)
362*1c60b9acSAndroid Build Coastguard Worker 			lws_metric_event(wsi->a.vhost->mt_traffic_tx,
363*1c60b9acSAndroid Build Coastguard Worker 					 METRES_GO, (u_mt_t)n);
364*1c60b9acSAndroid Build Coastguard Worker #endif
365*1c60b9acSAndroid Build Coastguard Worker 		return n;
366*1c60b9acSAndroid Build Coastguard Worker 	}
367*1c60b9acSAndroid Build Coastguard Worker 
368*1c60b9acSAndroid Build Coastguard Worker 	m = lws_ssl_get_error(wsi, n);
369*1c60b9acSAndroid Build Coastguard Worker 	if (m != SSL_ERROR_SYSCALL) {
370*1c60b9acSAndroid Build Coastguard Worker 		if (m == SSL_ERROR_WANT_READ || SSL_want_read(wsi->tls.ssl)) {
371*1c60b9acSAndroid Build Coastguard Worker 			lwsl_notice("%s: want read\n", __func__);
372*1c60b9acSAndroid Build Coastguard Worker 
373*1c60b9acSAndroid Build Coastguard Worker 			return LWS_SSL_CAPABLE_MORE_SERVICE;
374*1c60b9acSAndroid Build Coastguard Worker 		}
375*1c60b9acSAndroid Build Coastguard Worker 
376*1c60b9acSAndroid Build Coastguard Worker 		if (m == SSL_ERROR_WANT_WRITE || SSL_want_write(wsi->tls.ssl)) {
377*1c60b9acSAndroid Build Coastguard Worker 			lws_set_blocking_send(wsi);
378*1c60b9acSAndroid Build Coastguard Worker 
379*1c60b9acSAndroid Build Coastguard Worker 			lwsl_debug("%s: want write\n", __func__);
380*1c60b9acSAndroid Build Coastguard Worker 
381*1c60b9acSAndroid Build Coastguard Worker 			return LWS_SSL_CAPABLE_MORE_SERVICE;
382*1c60b9acSAndroid Build Coastguard Worker 		}
383*1c60b9acSAndroid Build Coastguard Worker 	}
384*1c60b9acSAndroid Build Coastguard Worker 
385*1c60b9acSAndroid Build Coastguard Worker 	lwsl_debug("%s failed: %s\n",__func__, ERR_error_string((unsigned int)m, NULL));
386*1c60b9acSAndroid Build Coastguard Worker 	lws_tls_err_describe_clear();
387*1c60b9acSAndroid Build Coastguard Worker 
388*1c60b9acSAndroid Build Coastguard Worker 	wsi->socket_is_permanently_unusable = 1;
389*1c60b9acSAndroid Build Coastguard Worker 
390*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
391*1c60b9acSAndroid Build Coastguard Worker 		if (wsi->a.vhost)
392*1c60b9acSAndroid Build Coastguard Worker 			lws_metric_event(wsi->a.vhost->mt_traffic_tx,
393*1c60b9acSAndroid Build Coastguard Worker 					 METRES_NOGO, 0);
394*1c60b9acSAndroid Build Coastguard Worker #endif
395*1c60b9acSAndroid Build Coastguard Worker 
396*1c60b9acSAndroid Build Coastguard Worker 	return LWS_SSL_CAPABLE_ERROR;
397*1c60b9acSAndroid Build Coastguard Worker }
398*1c60b9acSAndroid Build Coastguard Worker 
399*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_info_callback(const SSL * ssl,int where,int ret)400*1c60b9acSAndroid Build Coastguard Worker lws_ssl_info_callback(const SSL *ssl, int where, int ret)
401*1c60b9acSAndroid Build Coastguard Worker {
402*1c60b9acSAndroid Build Coastguard Worker 	struct lws *wsi;
403*1c60b9acSAndroid Build Coastguard Worker 	struct lws_context *context;
404*1c60b9acSAndroid Build Coastguard Worker 	struct lws_ssl_info si;
405*1c60b9acSAndroid Build Coastguard Worker 	int fd;
406*1c60b9acSAndroid Build Coastguard Worker 
407*1c60b9acSAndroid Build Coastguard Worker #ifndef USE_WOLFSSL
408*1c60b9acSAndroid Build Coastguard Worker 	context = (struct lws_context *)SSL_CTX_get_ex_data(
409*1c60b9acSAndroid Build Coastguard Worker 					SSL_get_SSL_CTX(ssl),
410*1c60b9acSAndroid Build Coastguard Worker 					openssl_SSL_CTX_private_data_index);
411*1c60b9acSAndroid Build Coastguard Worker #else
412*1c60b9acSAndroid Build Coastguard Worker 	context = (struct lws_context *)SSL_CTX_get_ex_data(
413*1c60b9acSAndroid Build Coastguard Worker 					SSL_get_SSL_CTX((SSL*) ssl),
414*1c60b9acSAndroid Build Coastguard Worker 					openssl_SSL_CTX_private_data_index);
415*1c60b9acSAndroid Build Coastguard Worker #endif
416*1c60b9acSAndroid Build Coastguard Worker 	if (!context)
417*1c60b9acSAndroid Build Coastguard Worker 		return;
418*1c60b9acSAndroid Build Coastguard Worker 
419*1c60b9acSAndroid Build Coastguard Worker 	fd = SSL_get_fd(ssl);
420*1c60b9acSAndroid Build Coastguard Worker 	if (fd < 0 || (fd - lws_plat_socket_offset()) < 0)
421*1c60b9acSAndroid Build Coastguard Worker 		return;
422*1c60b9acSAndroid Build Coastguard Worker 
423*1c60b9acSAndroid Build Coastguard Worker 	wsi = wsi_from_fd(context, fd);
424*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi)
425*1c60b9acSAndroid Build Coastguard Worker 		return;
426*1c60b9acSAndroid Build Coastguard Worker 
427*1c60b9acSAndroid Build Coastguard Worker 	if (!(where & wsi->a.vhost->tls.ssl_info_event_mask))
428*1c60b9acSAndroid Build Coastguard Worker 		return;
429*1c60b9acSAndroid Build Coastguard Worker 
430*1c60b9acSAndroid Build Coastguard Worker 	si.where = where;
431*1c60b9acSAndroid Build Coastguard Worker 	si.ret = ret;
432*1c60b9acSAndroid Build Coastguard Worker 
433*1c60b9acSAndroid Build Coastguard Worker 	if (user_callback_handle_rxflow(wsi->a.protocol->callback,
434*1c60b9acSAndroid Build Coastguard Worker 					wsi, LWS_CALLBACK_SSL_INFO,
435*1c60b9acSAndroid Build Coastguard Worker 					wsi->user_space, &si, 0))
436*1c60b9acSAndroid Build Coastguard Worker 		lws_set_timeout(wsi, PENDING_TIMEOUT_KILLED_BY_SSL_INFO, -1);
437*1c60b9acSAndroid Build Coastguard Worker }
438*1c60b9acSAndroid Build Coastguard Worker 
439*1c60b9acSAndroid Build Coastguard Worker 
440*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_close(struct lws * wsi)441*1c60b9acSAndroid Build Coastguard Worker lws_ssl_close(struct lws *wsi)
442*1c60b9acSAndroid Build Coastguard Worker {
443*1c60b9acSAndroid Build Coastguard Worker 	lws_sockfd_type n;
444*1c60b9acSAndroid Build Coastguard Worker 
445*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->tls.ssl)
446*1c60b9acSAndroid Build Coastguard Worker 		return 0; /* not handled */
447*1c60b9acSAndroid Build Coastguard Worker 
448*1c60b9acSAndroid Build Coastguard Worker #if defined (LWS_HAVE_SSL_SET_INFO_CALLBACK)
449*1c60b9acSAndroid Build Coastguard Worker 	/* kill ssl callbacks, because we will remove the fd from the
450*1c60b9acSAndroid Build Coastguard Worker 	 * table linking it to the wsi
451*1c60b9acSAndroid Build Coastguard Worker 	 */
452*1c60b9acSAndroid Build Coastguard Worker 	if (wsi->a.vhost->tls.ssl_info_event_mask)
453*1c60b9acSAndroid Build Coastguard Worker 		SSL_set_info_callback(wsi->tls.ssl, NULL);
454*1c60b9acSAndroid Build Coastguard Worker #endif
455*1c60b9acSAndroid Build Coastguard Worker 
456*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_TLS_SYNTHESIZE_CB)
457*1c60b9acSAndroid Build Coastguard Worker 	lws_sul_cancel(&wsi->tls.sul_cb_synth);
458*1c60b9acSAndroid Build Coastguard Worker 	/*
459*1c60b9acSAndroid Build Coastguard Worker 	 * ... check the session in case it did not live long enough to get
460*1c60b9acSAndroid Build Coastguard Worker 	 * the scheduled callback to sample it
461*1c60b9acSAndroid Build Coastguard Worker 	 */
462*1c60b9acSAndroid Build Coastguard Worker 	lws_sess_cache_synth_cb(&wsi->tls.sul_cb_synth);
463*1c60b9acSAndroid Build Coastguard Worker #endif
464*1c60b9acSAndroid Build Coastguard Worker 
465*1c60b9acSAndroid Build Coastguard Worker 	n = SSL_get_fd(wsi->tls.ssl);
466*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->socket_is_permanently_unusable)
467*1c60b9acSAndroid Build Coastguard Worker 		SSL_shutdown(wsi->tls.ssl);
468*1c60b9acSAndroid Build Coastguard Worker 	compatible_close(n);
469*1c60b9acSAndroid Build Coastguard Worker 	SSL_free(wsi->tls.ssl);
470*1c60b9acSAndroid Build Coastguard Worker 	wsi->tls.ssl = NULL;
471*1c60b9acSAndroid Build Coastguard Worker 
472*1c60b9acSAndroid Build Coastguard Worker 	lws_tls_restrict_return(wsi);
473*1c60b9acSAndroid Build Coastguard Worker 
474*1c60b9acSAndroid Build Coastguard Worker 	// lwsl_notice("%s: ssl restr %d, simul %d\n", __func__,
475*1c60b9acSAndroid Build Coastguard Worker 	//		wsi->a.context->simultaneous_ssl_restriction,
476*1c60b9acSAndroid Build Coastguard Worker 	//		wsi->a.context->simultaneous_ssl);
477*1c60b9acSAndroid Build Coastguard Worker 
478*1c60b9acSAndroid Build Coastguard Worker 	return 1; /* handled */
479*1c60b9acSAndroid Build Coastguard Worker }
480*1c60b9acSAndroid Build Coastguard Worker 
481*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_SSL_CTX_destroy(struct lws_vhost * vhost)482*1c60b9acSAndroid Build Coastguard Worker lws_ssl_SSL_CTX_destroy(struct lws_vhost *vhost)
483*1c60b9acSAndroid Build Coastguard Worker {
484*1c60b9acSAndroid Build Coastguard Worker 	if (vhost->tls.ssl_ctx)
485*1c60b9acSAndroid Build Coastguard Worker 		SSL_CTX_free(vhost->tls.ssl_ctx);
486*1c60b9acSAndroid Build Coastguard Worker 
487*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_CLIENT)
488*1c60b9acSAndroid Build Coastguard Worker 	lws_ssl_destroy_client_ctx(vhost);
489*1c60b9acSAndroid Build Coastguard Worker #endif
490*1c60b9acSAndroid Build Coastguard Worker 
491*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_ACME)
492*1c60b9acSAndroid Build Coastguard Worker 	lws_tls_acme_sni_cert_destroy(vhost);
493*1c60b9acSAndroid Build Coastguard Worker #endif
494*1c60b9acSAndroid Build Coastguard Worker }
495*1c60b9acSAndroid Build Coastguard Worker 
496*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_context_destroy(struct lws_context * context)497*1c60b9acSAndroid Build Coastguard Worker lws_ssl_context_destroy(struct lws_context *context)
498*1c60b9acSAndroid Build Coastguard Worker {
499*1c60b9acSAndroid Build Coastguard Worker // after 1.1.0 no need
500*1c60b9acSAndroid Build Coastguard Worker #if (OPENSSL_VERSION_NUMBER <  0x10100000)
501*1c60b9acSAndroid Build Coastguard Worker // <= 1.0.1f = old api, 1.0.1g+ = new api
502*1c60b9acSAndroid Build Coastguard Worker #if (OPENSSL_VERSION_NUMBER <= 0x1000106f) || defined(USE_WOLFSSL)
503*1c60b9acSAndroid Build Coastguard Worker 	ERR_remove_state(0);
504*1c60b9acSAndroid Build Coastguard Worker #else
505*1c60b9acSAndroid Build Coastguard Worker #if OPENSSL_VERSION_NUMBER >= 0x1010005f && \
506*1c60b9acSAndroid Build Coastguard Worker     !defined(LIBRESSL_VERSION_NUMBER) && \
507*1c60b9acSAndroid Build Coastguard Worker     !defined(OPENSSL_IS_BORINGSSL)
508*1c60b9acSAndroid Build Coastguard Worker 	ERR_remove_thread_state();
509*1c60b9acSAndroid Build Coastguard Worker #else
510*1c60b9acSAndroid Build Coastguard Worker 	ERR_remove_thread_state(NULL);
511*1c60b9acSAndroid Build Coastguard Worker #endif
512*1c60b9acSAndroid Build Coastguard Worker #endif
513*1c60b9acSAndroid Build Coastguard Worker 	// after 1.1.0 no need
514*1c60b9acSAndroid Build Coastguard Worker #if  (OPENSSL_VERSION_NUMBER >= 0x10002000) && (OPENSSL_VERSION_NUMBER <= 0x10100000)
515*1c60b9acSAndroid Build Coastguard Worker 	SSL_COMP_free_compression_methods();
516*1c60b9acSAndroid Build Coastguard Worker #endif
517*1c60b9acSAndroid Build Coastguard Worker 	ERR_free_strings();
518*1c60b9acSAndroid Build Coastguard Worker 	EVP_cleanup();
519*1c60b9acSAndroid Build Coastguard Worker 	CRYPTO_cleanup_all_ex_data();
520*1c60b9acSAndroid Build Coastguard Worker #endif
521*1c60b9acSAndroid Build Coastguard Worker }
522*1c60b9acSAndroid Build Coastguard Worker 
523*1c60b9acSAndroid Build Coastguard Worker lws_tls_ctx *
lws_tls_ctx_from_wsi(struct lws * wsi)524*1c60b9acSAndroid Build Coastguard Worker lws_tls_ctx_from_wsi(struct lws *wsi)
525*1c60b9acSAndroid Build Coastguard Worker {
526*1c60b9acSAndroid Build Coastguard Worker 	if (!wsi->tls.ssl)
527*1c60b9acSAndroid Build Coastguard Worker 		return NULL;
528*1c60b9acSAndroid Build Coastguard Worker 
529*1c60b9acSAndroid Build Coastguard Worker 	return SSL_get_SSL_CTX(wsi->tls.ssl);
530*1c60b9acSAndroid Build Coastguard Worker }
531*1c60b9acSAndroid Build Coastguard Worker 
532*1c60b9acSAndroid Build Coastguard Worker enum lws_ssl_capable_status
__lws_tls_shutdown(struct lws * wsi)533*1c60b9acSAndroid Build Coastguard Worker __lws_tls_shutdown(struct lws *wsi)
534*1c60b9acSAndroid Build Coastguard Worker {
535*1c60b9acSAndroid Build Coastguard Worker 	int n;
536*1c60b9acSAndroid Build Coastguard Worker 
537*1c60b9acSAndroid Build Coastguard Worker #ifndef WIN32
538*1c60b9acSAndroid Build Coastguard Worker 	errno = 0;
539*1c60b9acSAndroid Build Coastguard Worker #else
540*1c60b9acSAndroid Build Coastguard Worker   WSASetLastError(0);
541*1c60b9acSAndroid Build Coastguard Worker #endif
542*1c60b9acSAndroid Build Coastguard Worker 	ERR_clear_error();
543*1c60b9acSAndroid Build Coastguard Worker 	n = SSL_shutdown(wsi->tls.ssl);
544*1c60b9acSAndroid Build Coastguard Worker 	lwsl_debug("SSL_shutdown=%d for fd %d\n", n, wsi->desc.sockfd);
545*1c60b9acSAndroid Build Coastguard Worker 	switch (n) {
546*1c60b9acSAndroid Build Coastguard Worker 	case 1: /* successful completion */
547*1c60b9acSAndroid Build Coastguard Worker 		n = shutdown(wsi->desc.sockfd, SHUT_WR);
548*1c60b9acSAndroid Build Coastguard Worker 		return LWS_SSL_CAPABLE_DONE;
549*1c60b9acSAndroid Build Coastguard Worker 
550*1c60b9acSAndroid Build Coastguard Worker 	case 0: /* needs a retry */
551*1c60b9acSAndroid Build Coastguard Worker 		__lws_change_pollfd(wsi, 0, LWS_POLLIN);
552*1c60b9acSAndroid Build Coastguard Worker 		return LWS_SSL_CAPABLE_MORE_SERVICE;
553*1c60b9acSAndroid Build Coastguard Worker 
554*1c60b9acSAndroid Build Coastguard Worker 	default: /* fatal error, or WANT */
555*1c60b9acSAndroid Build Coastguard Worker 		n = SSL_get_error(wsi->tls.ssl, n);
556*1c60b9acSAndroid Build Coastguard Worker 		if (n != SSL_ERROR_SYSCALL && n != SSL_ERROR_SSL) {
557*1c60b9acSAndroid Build Coastguard Worker 			if (SSL_want_read(wsi->tls.ssl)) {
558*1c60b9acSAndroid Build Coastguard Worker 				lwsl_debug("(wants read)\n");
559*1c60b9acSAndroid Build Coastguard Worker 				__lws_change_pollfd(wsi, 0, LWS_POLLIN);
560*1c60b9acSAndroid Build Coastguard Worker 				return LWS_SSL_CAPABLE_MORE_SERVICE_READ;
561*1c60b9acSAndroid Build Coastguard Worker 			}
562*1c60b9acSAndroid Build Coastguard Worker 			if (SSL_want_write(wsi->tls.ssl)) {
563*1c60b9acSAndroid Build Coastguard Worker 				lwsl_debug("(wants write)\n");
564*1c60b9acSAndroid Build Coastguard Worker 				__lws_change_pollfd(wsi, 0, LWS_POLLOUT);
565*1c60b9acSAndroid Build Coastguard Worker 				return LWS_SSL_CAPABLE_MORE_SERVICE_WRITE;
566*1c60b9acSAndroid Build Coastguard Worker 			}
567*1c60b9acSAndroid Build Coastguard Worker 		}
568*1c60b9acSAndroid Build Coastguard Worker 		return LWS_SSL_CAPABLE_ERROR;
569*1c60b9acSAndroid Build Coastguard Worker 	}
570*1c60b9acSAndroid Build Coastguard Worker }
571*1c60b9acSAndroid Build Coastguard Worker 
572*1c60b9acSAndroid Build Coastguard Worker 
573*1c60b9acSAndroid Build Coastguard Worker static int
tops_fake_POLLIN_for_buffered_openssl(struct lws_context_per_thread * pt)574*1c60b9acSAndroid Build Coastguard Worker tops_fake_POLLIN_for_buffered_openssl(struct lws_context_per_thread *pt)
575*1c60b9acSAndroid Build Coastguard Worker {
576*1c60b9acSAndroid Build Coastguard Worker 	return lws_tls_fake_POLLIN_for_buffered(pt);
577*1c60b9acSAndroid Build Coastguard Worker }
578*1c60b9acSAndroid Build Coastguard Worker 
579*1c60b9acSAndroid Build Coastguard Worker const struct lws_tls_ops tls_ops_openssl = {
580*1c60b9acSAndroid Build Coastguard Worker 	/* fake_POLLIN_for_buffered */	tops_fake_POLLIN_for_buffered_openssl,
581*1c60b9acSAndroid Build Coastguard Worker };
582