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-mbedtls.h"
27*1c60b9acSAndroid Build Coastguard Worker
28*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_destroy(struct lws_vhost * vhost)29*1c60b9acSAndroid Build Coastguard Worker lws_ssl_destroy(struct lws_vhost *vhost)
30*1c60b9acSAndroid Build Coastguard Worker {
31*1c60b9acSAndroid Build Coastguard Worker if (!lws_check_opt(vhost->context->options,
32*1c60b9acSAndroid Build Coastguard Worker LWS_SERVER_OPTION_DO_SSL_GLOBAL_INIT))
33*1c60b9acSAndroid Build Coastguard Worker return;
34*1c60b9acSAndroid Build Coastguard Worker
35*1c60b9acSAndroid Build Coastguard Worker if (vhost->tls.ssl_ctx)
36*1c60b9acSAndroid Build Coastguard Worker SSL_CTX_free(vhost->tls.ssl_ctx);
37*1c60b9acSAndroid Build Coastguard Worker if (!vhost->tls.user_supplied_ssl_ctx && vhost->tls.ssl_client_ctx)
38*1c60b9acSAndroid Build Coastguard Worker SSL_CTX_free(vhost->tls.ssl_client_ctx);
39*1c60b9acSAndroid Build Coastguard Worker
40*1c60b9acSAndroid Build Coastguard Worker if (vhost->tls.x509_client_CA)
41*1c60b9acSAndroid Build Coastguard Worker X509_free(vhost->tls.x509_client_CA);
42*1c60b9acSAndroid Build Coastguard Worker }
43*1c60b9acSAndroid Build Coastguard Worker
44*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_capable_read(struct lws * wsi,unsigned char * buf,size_t len)45*1c60b9acSAndroid Build Coastguard Worker lws_ssl_capable_read(struct lws *wsi, unsigned char *buf, size_t len)
46*1c60b9acSAndroid Build Coastguard Worker {
47*1c60b9acSAndroid Build Coastguard Worker struct lws_context *context = wsi->a.context;
48*1c60b9acSAndroid Build Coastguard Worker struct lws_context_per_thread *pt = &context->pt[(int)wsi->tsi];
49*1c60b9acSAndroid Build Coastguard Worker int n = 0, m;
50*1c60b9acSAndroid Build Coastguard Worker
51*1c60b9acSAndroid Build Coastguard Worker if (!wsi->tls.ssl)
52*1c60b9acSAndroid Build Coastguard Worker return lws_ssl_capable_read_no_ssl(wsi, buf, len);
53*1c60b9acSAndroid Build Coastguard Worker
54*1c60b9acSAndroid Build Coastguard Worker errno = 0;
55*1c60b9acSAndroid Build Coastguard Worker n = SSL_read(wsi->tls.ssl, buf, (int)len);
56*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_PLAT_FREERTOS)
57*1c60b9acSAndroid Build Coastguard Worker if (!n && errno == LWS_ENOTCONN) {
58*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s: SSL_read ENOTCONN\n", lws_wsi_tag(wsi));
59*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_ERROR;
60*1c60b9acSAndroid Build Coastguard Worker }
61*1c60b9acSAndroid Build Coastguard Worker #endif
62*1c60b9acSAndroid Build Coastguard Worker
63*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s: %s: SSL_read says %d\n", __func__, lws_wsi_tag(wsi), n);
64*1c60b9acSAndroid Build Coastguard Worker /* manpage: returning 0 means connection shut down */
65*1c60b9acSAndroid Build Coastguard Worker if (!n) {
66*1c60b9acSAndroid Build Coastguard Worker wsi->socket_is_permanently_unusable = 1;
67*1c60b9acSAndroid Build Coastguard Worker
68*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_ERROR;
69*1c60b9acSAndroid Build Coastguard Worker }
70*1c60b9acSAndroid Build Coastguard Worker
71*1c60b9acSAndroid Build Coastguard Worker if (n < 0) {
72*1c60b9acSAndroid Build Coastguard Worker m = SSL_get_error(wsi->tls.ssl, n);
73*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s: %s: ssl err %d errno %d\n", __func__, lws_wsi_tag(wsi), m, errno);
74*1c60b9acSAndroid Build Coastguard Worker if (errno == LWS_ENOTCONN)
75*1c60b9acSAndroid Build Coastguard Worker /* If the socket isn't connected anymore, bail out. */
76*1c60b9acSAndroid Build Coastguard Worker goto do_err1;
77*1c60b9acSAndroid Build Coastguard Worker
78*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_PLAT_FREERTOS)
79*1c60b9acSAndroid Build Coastguard Worker if (errno == LWS_ECONNABORTED)
80*1c60b9acSAndroid Build Coastguard Worker goto do_err1;
81*1c60b9acSAndroid Build Coastguard Worker #endif
82*1c60b9acSAndroid Build Coastguard Worker
83*1c60b9acSAndroid Build Coastguard Worker if (m == SSL_ERROR_ZERO_RETURN ||
84*1c60b9acSAndroid Build Coastguard Worker m == SSL_ERROR_SYSCALL)
85*1c60b9acSAndroid Build Coastguard Worker goto do_err;
86*1c60b9acSAndroid Build Coastguard Worker
87*1c60b9acSAndroid Build Coastguard Worker if (m == SSL_ERROR_WANT_READ || SSL_want_read(wsi->tls.ssl)) {
88*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s: WANT_READ\n", __func__);
89*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s: LWS_SSL_CAPABLE_MORE_SERVICE\n", lws_wsi_tag(wsi));
90*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_MORE_SERVICE;
91*1c60b9acSAndroid Build Coastguard Worker }
92*1c60b9acSAndroid Build Coastguard Worker if (m == SSL_ERROR_WANT_WRITE || SSL_want_write(wsi->tls.ssl)) {
93*1c60b9acSAndroid Build Coastguard Worker lwsl_info("%s: WANT_WRITE\n", __func__);
94*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s: LWS_SSL_CAPABLE_MORE_SERVICE\n", lws_wsi_tag(wsi));
95*1c60b9acSAndroid Build Coastguard Worker wsi->tls_read_wanted_write = 1;
96*1c60b9acSAndroid Build Coastguard Worker lws_callback_on_writable(wsi);
97*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_MORE_SERVICE;
98*1c60b9acSAndroid Build Coastguard Worker }
99*1c60b9acSAndroid Build Coastguard Worker
100*1c60b9acSAndroid Build Coastguard Worker do_err1:
101*1c60b9acSAndroid Build Coastguard Worker wsi->socket_is_permanently_unusable = 1;
102*1c60b9acSAndroid Build Coastguard Worker
103*1c60b9acSAndroid Build Coastguard Worker do_err:
104*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
105*1c60b9acSAndroid Build Coastguard Worker if (wsi->a.vhost)
106*1c60b9acSAndroid Build Coastguard Worker lws_metric_event(wsi->a.vhost->mt_traffic_rx, METRES_NOGO, 0);
107*1c60b9acSAndroid Build Coastguard Worker #endif
108*1c60b9acSAndroid Build Coastguard Worker
109*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_ERROR;
110*1c60b9acSAndroid Build Coastguard Worker }
111*1c60b9acSAndroid Build Coastguard Worker
112*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_TLS_LOG_PLAINTEXT_RX)
113*1c60b9acSAndroid Build Coastguard Worker /*
114*1c60b9acSAndroid Build Coastguard Worker * If using mbedtls type tls library, this is the earliest point for all
115*1c60b9acSAndroid Build Coastguard Worker * paths to dump what was received as decrypted data from the tls tunnel
116*1c60b9acSAndroid Build Coastguard Worker */
117*1c60b9acSAndroid Build Coastguard Worker lwsl_notice("%s: len %d\n", __func__, n);
118*1c60b9acSAndroid Build Coastguard Worker lwsl_hexdump_notice(buf, (size_t)n);
119*1c60b9acSAndroid Build Coastguard Worker #endif
120*1c60b9acSAndroid Build Coastguard Worker
121*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
122*1c60b9acSAndroid Build Coastguard Worker if (wsi->a.vhost)
123*1c60b9acSAndroid Build Coastguard Worker lws_metric_event(wsi->a.vhost->mt_traffic_rx,
124*1c60b9acSAndroid Build Coastguard Worker METRES_GO /* rx */, (u_mt_t)n);
125*1c60b9acSAndroid Build Coastguard Worker #endif
126*1c60b9acSAndroid Build Coastguard Worker
127*1c60b9acSAndroid Build Coastguard Worker /*
128*1c60b9acSAndroid Build Coastguard Worker * if it was our buffer that limited what we read,
129*1c60b9acSAndroid Build Coastguard Worker * check if SSL has additional data pending inside SSL buffers.
130*1c60b9acSAndroid Build Coastguard Worker *
131*1c60b9acSAndroid Build Coastguard Worker * Because these won't signal at the network layer with POLLIN
132*1c60b9acSAndroid Build Coastguard Worker * and if we don't realize, this data will sit there forever
133*1c60b9acSAndroid Build Coastguard Worker */
134*1c60b9acSAndroid Build Coastguard Worker if (n != (int)len)
135*1c60b9acSAndroid Build Coastguard Worker goto bail;
136*1c60b9acSAndroid Build Coastguard Worker if (!wsi->tls.ssl)
137*1c60b9acSAndroid Build Coastguard Worker goto bail;
138*1c60b9acSAndroid Build Coastguard Worker
139*1c60b9acSAndroid Build Coastguard Worker if (SSL_pending(wsi->tls.ssl)) {
140*1c60b9acSAndroid Build Coastguard Worker if (lws_dll2_is_detached(&wsi->tls.dll_pending_tls))
141*1c60b9acSAndroid Build Coastguard Worker lws_dll2_add_head(&wsi->tls.dll_pending_tls,
142*1c60b9acSAndroid Build Coastguard Worker &pt->tls.dll_pending_tls_owner);
143*1c60b9acSAndroid Build Coastguard Worker } else
144*1c60b9acSAndroid Build Coastguard Worker __lws_ssl_remove_wsi_from_buffered_list(wsi);
145*1c60b9acSAndroid Build Coastguard Worker
146*1c60b9acSAndroid Build Coastguard Worker return n;
147*1c60b9acSAndroid Build Coastguard Worker bail:
148*1c60b9acSAndroid Build Coastguard Worker lws_ssl_remove_wsi_from_buffered_list(wsi);
149*1c60b9acSAndroid Build Coastguard Worker
150*1c60b9acSAndroid Build Coastguard Worker return n;
151*1c60b9acSAndroid Build Coastguard Worker }
152*1c60b9acSAndroid Build Coastguard Worker
153*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_pending(struct lws * wsi)154*1c60b9acSAndroid Build Coastguard Worker lws_ssl_pending(struct lws *wsi)
155*1c60b9acSAndroid Build Coastguard Worker {
156*1c60b9acSAndroid Build Coastguard Worker if (!wsi->tls.ssl)
157*1c60b9acSAndroid Build Coastguard Worker return 0;
158*1c60b9acSAndroid Build Coastguard Worker
159*1c60b9acSAndroid Build Coastguard Worker return SSL_pending(wsi->tls.ssl);
160*1c60b9acSAndroid Build Coastguard Worker }
161*1c60b9acSAndroid Build Coastguard Worker
162*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_capable_write(struct lws * wsi,unsigned char * buf,size_t len)163*1c60b9acSAndroid Build Coastguard Worker lws_ssl_capable_write(struct lws *wsi, unsigned char *buf, size_t len)
164*1c60b9acSAndroid Build Coastguard Worker {
165*1c60b9acSAndroid Build Coastguard Worker int n, m;
166*1c60b9acSAndroid Build Coastguard Worker
167*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_TLS_LOG_PLAINTEXT_TX)
168*1c60b9acSAndroid Build Coastguard Worker /*
169*1c60b9acSAndroid Build Coastguard Worker * If using mbedtls type tls library, this is the last point for all
170*1c60b9acSAndroid Build Coastguard Worker * paths before sending data into the tls tunnel, where you can dump it
171*1c60b9acSAndroid Build Coastguard Worker * and see what is being sent.
172*1c60b9acSAndroid Build Coastguard Worker */
173*1c60b9acSAndroid Build Coastguard Worker lwsl_notice("%s: len %d\n", __func__, (int)len);
174*1c60b9acSAndroid Build Coastguard Worker lwsl_hexdump_notice(buf, len);
175*1c60b9acSAndroid Build Coastguard Worker #endif
176*1c60b9acSAndroid Build Coastguard Worker
177*1c60b9acSAndroid Build Coastguard Worker if (!wsi->tls.ssl)
178*1c60b9acSAndroid Build Coastguard Worker return lws_ssl_capable_write_no_ssl(wsi, buf, len);
179*1c60b9acSAndroid Build Coastguard Worker
180*1c60b9acSAndroid Build Coastguard Worker n = SSL_write(wsi->tls.ssl, buf, (int)len);
181*1c60b9acSAndroid Build Coastguard Worker if (n > 0) {
182*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
183*1c60b9acSAndroid Build Coastguard Worker if (wsi->a.vhost)
184*1c60b9acSAndroid Build Coastguard Worker lws_metric_event(wsi->a.vhost->mt_traffic_tx,
185*1c60b9acSAndroid Build Coastguard Worker METRES_GO, (u_mt_t)n);
186*1c60b9acSAndroid Build Coastguard Worker #endif
187*1c60b9acSAndroid Build Coastguard Worker return n;
188*1c60b9acSAndroid Build Coastguard Worker }
189*1c60b9acSAndroid Build Coastguard Worker
190*1c60b9acSAndroid Build Coastguard Worker m = SSL_get_error(wsi->tls.ssl, n);
191*1c60b9acSAndroid Build Coastguard Worker if (m != SSL_ERROR_SYSCALL) {
192*1c60b9acSAndroid Build Coastguard Worker if (m == SSL_ERROR_WANT_READ || SSL_want_read(wsi->tls.ssl)) {
193*1c60b9acSAndroid Build Coastguard Worker lwsl_notice("%s: want read\n", __func__);
194*1c60b9acSAndroid Build Coastguard Worker
195*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_MORE_SERVICE;
196*1c60b9acSAndroid Build Coastguard Worker }
197*1c60b9acSAndroid Build Coastguard Worker
198*1c60b9acSAndroid Build Coastguard Worker if (m == SSL_ERROR_WANT_WRITE || SSL_want_write(wsi->tls.ssl)) {
199*1c60b9acSAndroid Build Coastguard Worker lws_set_blocking_send(wsi);
200*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s: want write\n", __func__);
201*1c60b9acSAndroid Build Coastguard Worker
202*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_MORE_SERVICE;
203*1c60b9acSAndroid Build Coastguard Worker }
204*1c60b9acSAndroid Build Coastguard Worker }
205*1c60b9acSAndroid Build Coastguard Worker
206*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("%s failed: %d\n",__func__, m);
207*1c60b9acSAndroid Build Coastguard Worker wsi->socket_is_permanently_unusable = 1;
208*1c60b9acSAndroid Build Coastguard Worker
209*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_SYS_METRICS)
210*1c60b9acSAndroid Build Coastguard Worker if (wsi->a.vhost)
211*1c60b9acSAndroid Build Coastguard Worker lws_metric_event(wsi->a.vhost->mt_traffic_tx,
212*1c60b9acSAndroid Build Coastguard Worker METRES_NOGO, (u_mt_t)n);
213*1c60b9acSAndroid Build Coastguard Worker #endif
214*1c60b9acSAndroid Build Coastguard Worker
215*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_ERROR;
216*1c60b9acSAndroid Build Coastguard Worker }
217*1c60b9acSAndroid Build Coastguard Worker
218*1c60b9acSAndroid Build Coastguard Worker int openssl_SSL_CTX_private_data_index;
219*1c60b9acSAndroid Build Coastguard Worker
220*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_info_callback(const SSL * ssl,int where,int ret)221*1c60b9acSAndroid Build Coastguard Worker lws_ssl_info_callback(const SSL *ssl, int where, int ret)
222*1c60b9acSAndroid Build Coastguard Worker {
223*1c60b9acSAndroid Build Coastguard Worker struct lws *wsi;
224*1c60b9acSAndroid Build Coastguard Worker struct lws_context *context;
225*1c60b9acSAndroid Build Coastguard Worker struct lws_ssl_info si;
226*1c60b9acSAndroid Build Coastguard Worker
227*1c60b9acSAndroid Build Coastguard Worker context = (struct lws_context *)SSL_CTX_get_ex_data(
228*1c60b9acSAndroid Build Coastguard Worker SSL_get_SSL_CTX(ssl),
229*1c60b9acSAndroid Build Coastguard Worker openssl_SSL_CTX_private_data_index);
230*1c60b9acSAndroid Build Coastguard Worker if (!context)
231*1c60b9acSAndroid Build Coastguard Worker return;
232*1c60b9acSAndroid Build Coastguard Worker wsi = wsi_from_fd(context, SSL_get_fd(ssl));
233*1c60b9acSAndroid Build Coastguard Worker if (!wsi)
234*1c60b9acSAndroid Build Coastguard Worker return;
235*1c60b9acSAndroid Build Coastguard Worker
236*1c60b9acSAndroid Build Coastguard Worker if (!(where & wsi->a.vhost->tls.ssl_info_event_mask))
237*1c60b9acSAndroid Build Coastguard Worker return;
238*1c60b9acSAndroid Build Coastguard Worker
239*1c60b9acSAndroid Build Coastguard Worker si.where = where;
240*1c60b9acSAndroid Build Coastguard Worker si.ret = ret;
241*1c60b9acSAndroid Build Coastguard Worker
242*1c60b9acSAndroid Build Coastguard Worker if (user_callback_handle_rxflow(wsi->a.protocol->callback,
243*1c60b9acSAndroid Build Coastguard Worker wsi, LWS_CALLBACK_SSL_INFO,
244*1c60b9acSAndroid Build Coastguard Worker wsi->user_space, &si, 0))
245*1c60b9acSAndroid Build Coastguard Worker lws_set_timeout(wsi, PENDING_TIMEOUT_KILLED_BY_SSL_INFO, -1);
246*1c60b9acSAndroid Build Coastguard Worker }
247*1c60b9acSAndroid Build Coastguard Worker
248*1c60b9acSAndroid Build Coastguard Worker
249*1c60b9acSAndroid Build Coastguard Worker int
lws_ssl_close(struct lws * wsi)250*1c60b9acSAndroid Build Coastguard Worker lws_ssl_close(struct lws *wsi)
251*1c60b9acSAndroid Build Coastguard Worker {
252*1c60b9acSAndroid Build Coastguard Worker lws_sockfd_type n;
253*1c60b9acSAndroid Build Coastguard Worker
254*1c60b9acSAndroid Build Coastguard Worker if (!wsi->tls.ssl)
255*1c60b9acSAndroid Build Coastguard Worker return 0; /* not handled */
256*1c60b9acSAndroid Build Coastguard Worker
257*1c60b9acSAndroid Build Coastguard Worker #if defined (LWS_HAVE_SSL_SET_INFO_CALLBACK)
258*1c60b9acSAndroid Build Coastguard Worker /* kill ssl callbacks, becausse we will remove the fd from the
259*1c60b9acSAndroid Build Coastguard Worker * table linking it to the wsi
260*1c60b9acSAndroid Build Coastguard Worker */
261*1c60b9acSAndroid Build Coastguard Worker if (wsi->a.vhost->tls.ssl_info_event_mask)
262*1c60b9acSAndroid Build Coastguard Worker SSL_set_info_callback(wsi->tls.ssl, NULL);
263*1c60b9acSAndroid Build Coastguard Worker #endif
264*1c60b9acSAndroid Build Coastguard Worker
265*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_TLS_SYNTHESIZE_CB)
266*1c60b9acSAndroid Build Coastguard Worker lws_sul_cancel(&wsi->tls.sul_cb_synth);
267*1c60b9acSAndroid Build Coastguard Worker /*
268*1c60b9acSAndroid Build Coastguard Worker * ... check the session in case it did not live long enough to get
269*1c60b9acSAndroid Build Coastguard Worker * the scheduled callback to sample it
270*1c60b9acSAndroid Build Coastguard Worker */
271*1c60b9acSAndroid Build Coastguard Worker lws_sess_cache_synth_cb(&wsi->tls.sul_cb_synth);
272*1c60b9acSAndroid Build Coastguard Worker #endif
273*1c60b9acSAndroid Build Coastguard Worker
274*1c60b9acSAndroid Build Coastguard Worker n = SSL_get_fd(wsi->tls.ssl);
275*1c60b9acSAndroid Build Coastguard Worker if (!wsi->socket_is_permanently_unusable)
276*1c60b9acSAndroid Build Coastguard Worker SSL_shutdown(wsi->tls.ssl);
277*1c60b9acSAndroid Build Coastguard Worker compatible_close(n);
278*1c60b9acSAndroid Build Coastguard Worker SSL_free(wsi->tls.ssl);
279*1c60b9acSAndroid Build Coastguard Worker wsi->tls.ssl = NULL;
280*1c60b9acSAndroid Build Coastguard Worker
281*1c60b9acSAndroid Build Coastguard Worker lws_tls_restrict_return(wsi);
282*1c60b9acSAndroid Build Coastguard Worker
283*1c60b9acSAndroid Build Coastguard Worker return 1; /* handled */
284*1c60b9acSAndroid Build Coastguard Worker }
285*1c60b9acSAndroid Build Coastguard Worker
286*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_SSL_CTX_destroy(struct lws_vhost * vhost)287*1c60b9acSAndroid Build Coastguard Worker lws_ssl_SSL_CTX_destroy(struct lws_vhost *vhost)
288*1c60b9acSAndroid Build Coastguard Worker {
289*1c60b9acSAndroid Build Coastguard Worker if (vhost->tls.ssl_ctx)
290*1c60b9acSAndroid Build Coastguard Worker SSL_CTX_free(vhost->tls.ssl_ctx);
291*1c60b9acSAndroid Build Coastguard Worker
292*1c60b9acSAndroid Build Coastguard Worker if (!vhost->tls.user_supplied_ssl_ctx && vhost->tls.ssl_client_ctx)
293*1c60b9acSAndroid Build Coastguard Worker SSL_CTX_free(vhost->tls.ssl_client_ctx);
294*1c60b9acSAndroid Build Coastguard Worker #if defined(LWS_WITH_ACME)
295*1c60b9acSAndroid Build Coastguard Worker lws_tls_acme_sni_cert_destroy(vhost);
296*1c60b9acSAndroid Build Coastguard Worker #endif
297*1c60b9acSAndroid Build Coastguard Worker }
298*1c60b9acSAndroid Build Coastguard Worker
299*1c60b9acSAndroid Build Coastguard Worker void
lws_ssl_context_destroy(struct lws_context * context)300*1c60b9acSAndroid Build Coastguard Worker lws_ssl_context_destroy(struct lws_context *context)
301*1c60b9acSAndroid Build Coastguard Worker {
302*1c60b9acSAndroid Build Coastguard Worker }
303*1c60b9acSAndroid Build Coastguard Worker
304*1c60b9acSAndroid Build Coastguard Worker lws_tls_ctx *
lws_tls_ctx_from_wsi(struct lws * wsi)305*1c60b9acSAndroid Build Coastguard Worker lws_tls_ctx_from_wsi(struct lws *wsi)
306*1c60b9acSAndroid Build Coastguard Worker {
307*1c60b9acSAndroid Build Coastguard Worker if (!wsi->tls.ssl)
308*1c60b9acSAndroid Build Coastguard Worker return NULL;
309*1c60b9acSAndroid Build Coastguard Worker
310*1c60b9acSAndroid Build Coastguard Worker return SSL_get_SSL_CTX(wsi->tls.ssl);
311*1c60b9acSAndroid Build Coastguard Worker }
312*1c60b9acSAndroid Build Coastguard Worker
313*1c60b9acSAndroid Build Coastguard Worker enum lws_ssl_capable_status
__lws_tls_shutdown(struct lws * wsi)314*1c60b9acSAndroid Build Coastguard Worker __lws_tls_shutdown(struct lws *wsi)
315*1c60b9acSAndroid Build Coastguard Worker {
316*1c60b9acSAndroid Build Coastguard Worker int n = SSL_shutdown(wsi->tls.ssl);
317*1c60b9acSAndroid Build Coastguard Worker
318*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("SSL_shutdown=%d for fd %d\n", n, wsi->desc.sockfd);
319*1c60b9acSAndroid Build Coastguard Worker
320*1c60b9acSAndroid Build Coastguard Worker switch (n) {
321*1c60b9acSAndroid Build Coastguard Worker case 1: /* successful completion */
322*1c60b9acSAndroid Build Coastguard Worker (void)shutdown(wsi->desc.sockfd, SHUT_WR);
323*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_DONE;
324*1c60b9acSAndroid Build Coastguard Worker
325*1c60b9acSAndroid Build Coastguard Worker case 0: /* needs a retry */
326*1c60b9acSAndroid Build Coastguard Worker __lws_change_pollfd(wsi, 0, LWS_POLLIN);
327*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_MORE_SERVICE;
328*1c60b9acSAndroid Build Coastguard Worker
329*1c60b9acSAndroid Build Coastguard Worker default: /* fatal error, or WANT */
330*1c60b9acSAndroid Build Coastguard Worker n = SSL_get_error(wsi->tls.ssl, n);
331*1c60b9acSAndroid Build Coastguard Worker if (n != SSL_ERROR_SYSCALL && n != SSL_ERROR_SSL) {
332*1c60b9acSAndroid Build Coastguard Worker if (SSL_want_read(wsi->tls.ssl)) {
333*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("(wants read)\n");
334*1c60b9acSAndroid Build Coastguard Worker __lws_change_pollfd(wsi, 0, LWS_POLLIN);
335*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_MORE_SERVICE_READ;
336*1c60b9acSAndroid Build Coastguard Worker }
337*1c60b9acSAndroid Build Coastguard Worker if (SSL_want_write(wsi->tls.ssl)) {
338*1c60b9acSAndroid Build Coastguard Worker lwsl_debug("(wants write)\n");
339*1c60b9acSAndroid Build Coastguard Worker __lws_change_pollfd(wsi, 0, LWS_POLLOUT);
340*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_MORE_SERVICE_WRITE;
341*1c60b9acSAndroid Build Coastguard Worker }
342*1c60b9acSAndroid Build Coastguard Worker }
343*1c60b9acSAndroid Build Coastguard Worker return LWS_SSL_CAPABLE_ERROR;
344*1c60b9acSAndroid Build Coastguard Worker }
345*1c60b9acSAndroid Build Coastguard Worker }
346*1c60b9acSAndroid Build Coastguard Worker
347*1c60b9acSAndroid Build Coastguard Worker
348*1c60b9acSAndroid Build Coastguard Worker static int
tops_fake_POLLIN_for_buffered_mbedtls(struct lws_context_per_thread * pt)349*1c60b9acSAndroid Build Coastguard Worker tops_fake_POLLIN_for_buffered_mbedtls(struct lws_context_per_thread *pt)
350*1c60b9acSAndroid Build Coastguard Worker {
351*1c60b9acSAndroid Build Coastguard Worker return lws_tls_fake_POLLIN_for_buffered(pt);
352*1c60b9acSAndroid Build Coastguard Worker }
353*1c60b9acSAndroid Build Coastguard Worker
354*1c60b9acSAndroid Build Coastguard Worker const struct lws_tls_ops tls_ops_mbedtls = {
355*1c60b9acSAndroid Build Coastguard Worker /* fake_POLLIN_for_buffered */ tops_fake_POLLIN_for_buffered_mbedtls,
356*1c60b9acSAndroid Build Coastguard Worker };
357