1 /*--------------------------------------------------------------------------
2  * LuaSec 1.0.2
3  *
4  * Copyright (C) 2014-2021 Kim Alvefur, Paul Aurich, Tobias Markmann,
5  *                         Matthew Wild.
6  * Copyright (C) 2006-2021 Bruno Silvestre.
7  *
8  *--------------------------------------------------------------------------*/
9 
10 #include <string.h>
11 
12 #if defined(WIN32)
13 #include <windows.h>
14 #endif
15 
16 #include <openssl/ssl.h>
17 #include <openssl/err.h>
18 #include <openssl/x509.h>
19 #include <openssl/x509v3.h>
20 #include <openssl/dh.h>
21 
22 #include <lua.h>
23 #include <lauxlib.h>
24 
25 #include "compat.h"
26 #include "context.h"
27 #include "options.h"
28 
29 #ifndef OPENSSL_NO_EC
30 #include <openssl/ec.h>
31 #include "ec.h"
32 #endif
33 
34 /*--------------------------- Auxiliary Functions ----------------------------*/
35 
36 /**
37  * Return the context.
38  */
checkctx(lua_State * L,int idx)39 static p_context checkctx(lua_State *L, int idx)
40 {
41   return (p_context)luaL_checkudata(L, idx, "SSL:Context");
42 }
43 
testctx(lua_State * L,int idx)44 static p_context testctx(lua_State *L, int idx)
45 {
46   return (p_context)luaL_testudata(L, idx, "SSL:Context");
47 }
48 
49 /**
50  * Prepare the SSL options flag.
51  */
set_option_flag(const char * opt,unsigned long * flag)52 static int set_option_flag(const char *opt, unsigned long *flag)
53 {
54   lsec_ssl_option_t *p;
55   for (p = lsec_get_ssl_options(); p->name; p++) {
56     if (!strcmp(opt, p->name)) {
57       *flag |= p->code;
58       return 1;
59     }
60   }
61   return 0;
62 }
63 
64 #ifndef LSEC_API_OPENSSL_1_1_0
65 /**
66  * Find the protocol.
67  */
str2method(const char * method,int * vmin,int * vmax)68 static const SSL_METHOD* str2method(const char *method, int *vmin, int *vmax)
69 {
70   (void)vmin;
71   (void)vmax;
72   if (!strcmp(method, "any"))     return SSLv23_method();
73   if (!strcmp(method, "sslv23"))  return SSLv23_method();  // deprecated
74   if (!strcmp(method, "tlsv1"))   return TLSv1_method();
75   if (!strcmp(method, "tlsv1_1")) return TLSv1_1_method();
76   if (!strcmp(method, "tlsv1_2")) return TLSv1_2_method();
77   return NULL;
78 }
79 
80 #else
81 
82 /**
83  * Find the protocol.
84  */
str2method(const char * method,int * vmin,int * vmax)85 static const SSL_METHOD* str2method(const char *method, int *vmin, int *vmax)
86 {
87   if (!strcmp(method, "any") || !strcmp(method, "sslv23")) { // 'sslv23' is deprecated
88     *vmin = 0;
89     *vmax = 0;
90     return TLS_method();
91   }
92   else if (!strcmp(method, "tlsv1")) {
93     *vmin = TLS1_VERSION;
94     *vmax = TLS1_VERSION;
95     return TLS_method();
96   }
97   else if (!strcmp(method, "tlsv1_1")) {
98     *vmin = TLS1_1_VERSION;
99     *vmax = TLS1_1_VERSION;
100     return TLS_method();
101   }
102   else if (!strcmp(method, "tlsv1_2")) {
103     *vmin = TLS1_2_VERSION;
104     *vmax = TLS1_2_VERSION;
105     return TLS_method();
106   }
107 #if defined(TLS1_3_VERSION)
108   else if (!strcmp(method, "tlsv1_3")) {
109     *vmin = TLS1_3_VERSION;
110     *vmax = TLS1_3_VERSION;
111     return TLS_method();
112   }
113 #endif
114   return NULL;
115 }
116 #endif
117 
118 /**
119  * Prepare the SSL handshake verify flag.
120  */
set_verify_flag(const char * str,int * flag)121 static int set_verify_flag(const char *str, int *flag)
122 {
123   if (!strcmp(str, "none")) {
124     *flag |= SSL_VERIFY_NONE;
125     return 1;
126   }
127   if (!strcmp(str, "peer")) {
128     *flag |= SSL_VERIFY_PEER;
129     return 1;
130   }
131   if (!strcmp(str, "client_once")) {
132     *flag |= SSL_VERIFY_CLIENT_ONCE;
133     return 1;
134   }
135   if (!strcmp(str, "fail_if_no_peer_cert")) {
136     *flag |= SSL_VERIFY_FAIL_IF_NO_PEER_CERT;
137     return 1;
138   }
139   return 0;
140 }
141 
142 /**
143  * Password callback for reading the private key.
144  */
passwd_cb(char * buf,int size,int flag,void * udata)145 static int passwd_cb(char *buf, int size, int flag, void *udata)
146 {
147   lua_State *L = (lua_State*)udata;
148   switch (lua_type(L, 3)) {
149   case LUA_TFUNCTION:
150     lua_pushvalue(L, 3);
151     lua_call(L, 0, 1);
152     if (lua_type(L, -1) != LUA_TSTRING) {
153        lua_pop(L, 1);  /* Remove the result from the stack */
154        return 0;
155     }
156     /* fallback */
157   case LUA_TSTRING:
158     strncpy(buf, lua_tostring(L, -1), size);
159     lua_pop(L, 1);  /* Remove the result from the stack */
160     buf[size-1] = '\0';
161     return (int)strlen(buf);
162   }
163   return 0;
164 }
165 
166 /**
167  * Add an error related to a depth certificate of the chain.
168  */
add_cert_error(lua_State * L,SSL * ssl,int err,int depth)169 static void add_cert_error(lua_State *L, SSL *ssl, int err, int depth)
170 {
171   luaL_getmetatable(L, "SSL:Verify:Registry");
172   lua_pushlightuserdata(L, (void*)ssl);
173   lua_gettable(L, -2);
174   if (lua_isnil(L, -1)) {
175     lua_pop(L, 1);
176     /* Create an error table for this connection */
177     lua_newtable(L);
178     lua_pushlightuserdata(L, (void*)ssl);
179     lua_pushvalue(L, -2);  /* keep the table on stack */
180     lua_settable(L, -4);
181   }
182   lua_rawgeti(L, -1, depth+1);
183   /* If the table doesn't exist, create it */
184   if (lua_isnil(L, -1)) {
185     lua_pop(L, 1);               /* remove 'nil' from stack */
186     lua_newtable(L);
187     lua_pushvalue(L, -1);        /* keep the table on stack */
188     lua_rawseti(L, -3, depth+1);
189   }
190   lua_pushstring(L, X509_verify_cert_error_string(err));
191   lua_rawseti(L, -2, lua_rawlen(L, -2) + 1);
192   /* Clear the stack */
193   lua_pop(L, 3);
194 }
195 
196 /**
197  * Call Lua user function to get the DH key.
198  */
dhparam_cb(SSL * ssl,int is_export,int keylength)199 static DH *dhparam_cb(SSL *ssl, int is_export, int keylength)
200 {
201   BIO *bio;
202   lua_State *L;
203   SSL_CTX *ctx = SSL_get_SSL_CTX(ssl);
204   p_context pctx = (p_context)SSL_CTX_get_app_data(ctx);
205 
206   L = pctx->L;
207 
208   /* Get the callback */
209   luaL_getmetatable(L, "SSL:DH:Registry");
210   lua_pushlightuserdata(L, (void*)ctx);
211   lua_gettable(L, -2);
212 
213   /* Invoke the callback */
214   lua_pushboolean(L, is_export);
215   lua_pushnumber(L, keylength);
216   lua_call(L, 2, 1);
217 
218   /* Load parameters from returned value */
219   if (lua_type(L, -1) != LUA_TSTRING) {
220     lua_pop(L, 2);  /* Remove values from stack */
221     return NULL;
222   }
223 
224   bio = BIO_new_mem_buf((void*)lua_tostring(L, -1), lua_rawlen(L, -1));
225   if (bio) {
226     pctx->dh_param = PEM_read_bio_DHparams(bio, NULL, NULL, NULL);
227     BIO_free(bio);
228   }
229 
230   lua_pop(L, 2);    /* Remove values from stack */
231   return pctx->dh_param;
232 }
233 
234 /**
235  * Set the "ignore purpose" before to start verifing the certificate chain.
236  */
cert_verify_cb(X509_STORE_CTX * x509_ctx,void * ptr)237 static int cert_verify_cb(X509_STORE_CTX *x509_ctx, void *ptr)
238 {
239   int verify;
240   lua_State *L;
241   SSL_CTX *ctx = (SSL_CTX*)ptr;
242   p_context pctx = (p_context)SSL_CTX_get_app_data(ctx);
243 
244   L = pctx->L;
245 
246   /* Get verify flags */
247   luaL_getmetatable(L, "SSL:Verify:Registry");
248   lua_pushlightuserdata(L, (void*)ctx);
249   lua_gettable(L, -2);
250   verify = (int)lua_tonumber(L, -1);
251 
252   lua_pop(L, 2); /* Remove values from stack */
253 
254   if (verify & LSEC_VERIFY_IGNORE_PURPOSE) {
255     /* Set parameters to ignore the server purpose */
256     X509_VERIFY_PARAM *param = X509_STORE_CTX_get0_param(x509_ctx);
257     if (param) {
258       X509_VERIFY_PARAM_set_purpose(param, X509_PURPOSE_SSL_SERVER);
259       X509_VERIFY_PARAM_set_trust(param, X509_TRUST_SSL_SERVER);
260     }
261   }
262   /* Call OpenSSL standard verification function */
263   return X509_verify_cert(x509_ctx);
264 }
265 
266 /**
267  * This callback implements the "continue on error" flag and log the errors.
268  */
verify_cb(int preverify_ok,X509_STORE_CTX * x509_ctx)269 static int verify_cb(int preverify_ok, X509_STORE_CTX *x509_ctx)
270 {
271   int err;
272   int verify;
273   SSL *ssl;
274   SSL_CTX *ctx;
275   p_context pctx;
276   lua_State *L;
277 
278   /* Short-circuit optimization */
279   if (preverify_ok)
280     return 1;
281 
282   ssl = X509_STORE_CTX_get_ex_data(x509_ctx,
283     SSL_get_ex_data_X509_STORE_CTX_idx());
284   ctx = SSL_get_SSL_CTX(ssl);
285   pctx = (p_context)SSL_CTX_get_app_data(ctx);
286   L = pctx->L;
287 
288   /* Get verify flags */
289   luaL_getmetatable(L, "SSL:Verify:Registry");
290   lua_pushlightuserdata(L, (void*)ctx);
291   lua_gettable(L, -2);
292   verify = (int)lua_tonumber(L, -1);
293 
294   lua_pop(L, 2); /* Remove values from stack */
295 
296   err = X509_STORE_CTX_get_error(x509_ctx);
297   if (err != X509_V_OK)
298     add_cert_error(L, ssl, err, X509_STORE_CTX_get_error_depth(x509_ctx));
299 
300   return (verify & LSEC_VERIFY_CONTINUE ? 1 : preverify_ok);
301 }
302 
303 /*------------------------------ Lua Functions -------------------------------*/
304 
305 /**
306  * Create a SSL context.
307  */
create(lua_State * L)308 static int create(lua_State *L)
309 {
310   p_context ctx;
311   const char *str_method;
312   const SSL_METHOD *method;
313   int vmin, vmax;
314 
315   str_method = luaL_checkstring(L, 1);
316   method = str2method(str_method, &vmin, &vmax);
317   if (!method) {
318     lua_pushnil(L);
319     lua_pushfstring(L, "invalid protocol (%s)", str_method);
320     return 2;
321   }
322   ctx = (p_context) lua_newuserdata(L, sizeof(t_context));
323   if (!ctx) {
324     lua_pushnil(L);
325     lua_pushstring(L, "error creating context");
326     return 2;
327   }
328   memset(ctx, 0, sizeof(t_context));
329   ctx->context = SSL_CTX_new(method);
330   if (!ctx->context) {
331     lua_pushnil(L);
332     lua_pushfstring(L, "error creating context (%s)",
333       ERR_reason_error_string(ERR_get_error()));
334     return 2;
335   }
336 #ifdef LSEC_API_OPENSSL_1_1_0
337   SSL_CTX_set_min_proto_version(ctx->context, vmin);
338   SSL_CTX_set_max_proto_version(ctx->context, vmax);
339 #endif
340   ctx->mode = LSEC_MODE_INVALID;
341   ctx->L = L;
342   luaL_getmetatable(L, "SSL:Context");
343   lua_setmetatable(L, -2);
344 
345   /* No session support */
346   SSL_CTX_set_session_cache_mode(ctx->context, SSL_SESS_CACHE_OFF);
347   /* Link LuaSec context with the OpenSSL context */
348   SSL_CTX_set_app_data(ctx->context, ctx);
349 
350   return 1;
351 }
352 
353 /**
354  * Load the trusting certificates.
355  */
load_locations(lua_State * L)356 static int load_locations(lua_State *L)
357 {
358   SSL_CTX *ctx = lsec_checkcontext(L, 1);
359   const char *cafile = luaL_optstring(L, 2, NULL);
360   const char *capath = luaL_optstring(L, 3, NULL);
361   if (SSL_CTX_load_verify_locations(ctx, cafile, capath) != 1) {
362     lua_pushboolean(L, 0);
363     lua_pushfstring(L, "error loading CA locations (%s)",
364       ERR_reason_error_string(ERR_get_error()));
365     return 2;
366   }
367   lua_pushboolean(L, 1);
368   return 1;
369 }
370 
371 /**
372  * Load the certificate file.
373  */
load_cert(lua_State * L)374 static int load_cert(lua_State *L)
375 {
376   SSL_CTX *ctx = lsec_checkcontext(L, 1);
377   const char *filename = luaL_checkstring(L, 2);
378   if (SSL_CTX_use_certificate_chain_file(ctx, filename) != 1) {
379     lua_pushboolean(L, 0);
380     lua_pushfstring(L, "error loading certificate (%s)",
381       ERR_reason_error_string(ERR_get_error()));
382     return 2;
383   }
384   lua_pushboolean(L, 1);
385   return 1;
386 }
387 
388 /**
389  * Load the key file -- only in PEM format.
390  */
load_key(lua_State * L)391 static int load_key(lua_State *L)
392 {
393   int ret = 1;
394   SSL_CTX *ctx = lsec_checkcontext(L, 1);
395   const char *filename = luaL_checkstring(L, 2);
396   switch (lua_type(L, 3)) {
397   case LUA_TSTRING:
398   case LUA_TFUNCTION:
399     SSL_CTX_set_default_passwd_cb(ctx, passwd_cb);
400     SSL_CTX_set_default_passwd_cb_userdata(ctx, L);
401     /* fallback */
402   case LUA_TNIL:
403     if (SSL_CTX_use_PrivateKey_file(ctx, filename, SSL_FILETYPE_PEM) == 1)
404       lua_pushboolean(L, 1);
405     else {
406       ret = 2;
407       lua_pushboolean(L, 0);
408       lua_pushfstring(L, "error loading private key (%s)",
409         ERR_reason_error_string(ERR_get_error()));
410     }
411     SSL_CTX_set_default_passwd_cb(ctx, NULL);
412     SSL_CTX_set_default_passwd_cb_userdata(ctx, NULL);
413     break;
414   default:
415     lua_pushstring(L, "invalid callback value");
416     lua_error(L);
417   }
418   return ret;
419 }
420 
421 /**
422  * Check that the certificate public key matches the private key
423  */
424 
check_key(lua_State * L)425 static int check_key(lua_State *L)
426 {
427   SSL_CTX *ctx = lsec_checkcontext(L, 1);
428   lua_pushboolean(L, SSL_CTX_check_private_key(ctx));
429   return 1;
430 }
431 
432 /**
433  * Set the cipher list.
434  */
set_cipher(lua_State * L)435 static int set_cipher(lua_State *L)
436 {
437   SSL_CTX *ctx = lsec_checkcontext(L, 1);
438   const char *list = luaL_checkstring(L, 2);
439   if (SSL_CTX_set_cipher_list(ctx, list) != 1) {
440     lua_pushboolean(L, 0);
441     lua_pushfstring(L, "error setting cipher list (%s)", ERR_reason_error_string(ERR_get_error()));
442     return 2;
443   }
444   lua_pushboolean(L, 1);
445   return 1;
446 }
447 
448 /**
449  * Set the cipher suites.
450  */
set_ciphersuites(lua_State * L)451 static int set_ciphersuites(lua_State *L)
452 {
453 #if defined(TLS1_3_VERSION)
454   SSL_CTX *ctx = lsec_checkcontext(L, 1);
455   const char *list = luaL_checkstring(L, 2);
456   if (SSL_CTX_set_ciphersuites(ctx, list) != 1) {
457     lua_pushboolean(L, 0);
458     lua_pushfstring(L, "error setting cipher list (%s)", ERR_reason_error_string(ERR_get_error()));
459     return 2;
460   }
461 #endif
462   lua_pushboolean(L, 1);
463   return 1;
464 }
465 
466 /**
467  * Set the depth for certificate checking.
468  */
set_depth(lua_State * L)469 static int set_depth(lua_State *L)
470 {
471   SSL_CTX *ctx = lsec_checkcontext(L, 1);
472   SSL_CTX_set_verify_depth(ctx, (int)luaL_checkinteger(L, 2));
473   lua_pushboolean(L, 1);
474   return 1;
475 }
476 
477 /**
478  * Set the handshake verify options.
479  */
set_verify(lua_State * L)480 static int set_verify(lua_State *L)
481 {
482   int i;
483   const char *str;
484   int flag = 0;
485   SSL_CTX *ctx = lsec_checkcontext(L, 1);
486   int max = lua_gettop(L);
487   for (i = 2; i <= max; i++) {
488     str = luaL_checkstring(L, i);
489     if (!set_verify_flag(str, &flag)) {
490       lua_pushboolean(L, 0);
491       lua_pushfstring(L, "invalid verify option (%s)", str);
492       return 2;
493     }
494   }
495   if (flag) SSL_CTX_set_verify(ctx, flag, NULL);
496   lua_pushboolean(L, 1);
497   return 1;
498 }
499 
500 /**
501  * Set the protocol options.
502  */
set_options(lua_State * L)503 static int set_options(lua_State *L)
504 {
505   int i;
506   const char *str;
507   unsigned long flag = 0L;
508   SSL_CTX *ctx = lsec_checkcontext(L, 1);
509   int max = lua_gettop(L);
510   /* any option? */
511   if (max > 1) {
512     for (i = 2; i <= max; i++) {
513       str = luaL_checkstring(L, i);
514       if (!set_option_flag(str, &flag)) {
515         lua_pushboolean(L, 0);
516         lua_pushfstring(L, "invalid option (%s)", str);
517         return 2;
518       }
519     }
520     SSL_CTX_set_options(ctx, flag);
521   }
522   lua_pushboolean(L, 1);
523   return 1;
524 }
525 
526 /**
527  * Set the context mode.
528  */
set_mode(lua_State * L)529 static int set_mode(lua_State *L)
530 {
531   p_context ctx = checkctx(L, 1);
532   const char *str = luaL_checkstring(L, 2);
533   if (!strcmp("server", str)) {
534     ctx->mode = LSEC_MODE_SERVER;
535     lua_pushboolean(L, 1);
536     return 1;
537   }
538   if (!strcmp("client", str)) {
539     ctx->mode = LSEC_MODE_CLIENT;
540     lua_pushboolean(L, 1);
541     return 1;
542   }
543   lua_pushboolean(L, 0);
544   lua_pushfstring(L, "invalid mode (%s)", str);
545   return 1;
546 }
547 
548 /**
549  * Configure DH parameters.
550  */
set_dhparam(lua_State * L)551 static int set_dhparam(lua_State *L)
552 {
553   SSL_CTX *ctx = lsec_checkcontext(L, 1);
554   SSL_CTX_set_tmp_dh_callback(ctx, dhparam_cb);
555 
556   /* Save callback */
557   luaL_getmetatable(L, "SSL:DH:Registry");
558   lua_pushlightuserdata(L, (void*)ctx);
559   lua_pushvalue(L, 2);
560   lua_settable(L, -3);
561 
562   return 0;
563 }
564 
565 #if !defined(OPENSSL_NO_EC)
566 /**
567  * Set elliptic curve.
568  */
set_curve(lua_State * L)569 static int set_curve(lua_State *L)
570 {
571   long ret;
572   EC_KEY *key = NULL;
573   SSL_CTX *ctx = lsec_checkcontext(L, 1);
574   const char *str = luaL_checkstring(L, 2);
575 
576   SSL_CTX_set_options(ctx, SSL_OP_SINGLE_ECDH_USE);
577 
578   key = lsec_find_ec_key(L, str);
579 
580   if (!key) {
581     lua_pushboolean(L, 0);
582     lua_pushfstring(L, "elliptic curve '%s' not supported", str);
583     return 2;
584   }
585 
586   ret = SSL_CTX_set_tmp_ecdh(ctx, key);
587   /* SSL_CTX_set_tmp_ecdh takes its own reference */
588   EC_KEY_free(key);
589 
590   if (!ret) {
591     lua_pushboolean(L, 0);
592     lua_pushfstring(L, "error setting elliptic curve (%s)",
593       ERR_reason_error_string(ERR_get_error()));
594     return 2;
595   }
596 
597   lua_pushboolean(L, 1);
598   return 1;
599 }
600 
601 /**
602  * Set elliptic curves list.
603  */
set_curves_list(lua_State * L)604 static int set_curves_list(lua_State *L)
605 {
606   SSL_CTX *ctx = lsec_checkcontext(L, 1);
607   const char *str = luaL_checkstring(L, 2);
608 
609   SSL_CTX_set_options(ctx, SSL_OP_SINGLE_ECDH_USE);
610 
611   if (SSL_CTX_set1_curves_list(ctx, str) != 1) {
612     lua_pushboolean(L, 0);
613     lua_pushfstring(L, "unknown elliptic curve in \"%s\"", str);
614     return 2;
615   }
616 
617 #if defined(LIBRESSL_VERSION_NUMBER) || !defined(LSEC_API_OPENSSL_1_1_0)
618   (void)SSL_CTX_set_ecdh_auto(ctx, 1);
619 #endif
620 
621   lua_pushboolean(L, 1);
622   return 1;
623 }
624 #endif
625 
626 /**
627  * Set the protocols a client should send for ALPN.
628  */
set_alpn(lua_State * L)629 static int set_alpn(lua_State *L)
630 {
631   long ret;
632   size_t len;
633   p_context ctx = checkctx(L, 1);
634   const char *str = luaL_checklstring(L, 2, &len);
635 
636   ret = SSL_CTX_set_alpn_protos(ctx->context, (const unsigned char*)str, len);
637   if (ret) {
638     lua_pushboolean(L, 0);
639     lua_pushfstring(L, "error setting ALPN (%s)", ERR_reason_error_string(ERR_get_error()));
640     return 2;
641   }
642   lua_pushboolean(L, 1);
643   return 1;
644 }
645 
646 /**
647  * This standard callback calls the server's callback in Lua sapce.
648  * The server has to return a list in wire-format strings.
649  * This function uses a helper function to match server and client lists.
650  */
alpn_cb(SSL * s,const unsigned char ** out,unsigned char * outlen,const unsigned char * in,unsigned int inlen,void * arg)651 static int alpn_cb(SSL *s, const unsigned char **out, unsigned char *outlen,
652                    const unsigned char *in, unsigned int inlen, void *arg)
653 {
654   int ret;
655   size_t server_len;
656   const char *server;
657   p_context ctx = (p_context)arg;
658   lua_State *L = ctx->L;
659 
660   luaL_getmetatable(L, "SSL:ALPN:Registry");
661   lua_pushlightuserdata(L, (void*)ctx->context);
662   lua_gettable(L, -2);
663 
664   lua_pushlstring(L, (const char*)in, inlen);
665 
666   lua_call(L, 1, 1);
667 
668   if (!lua_isstring(L, -1)) {
669     lua_pop(L, 2);
670     return SSL_TLSEXT_ERR_NOACK;
671   }
672 
673   // Protocol list from server in wire-format string
674   server = luaL_checklstring(L, -1, &server_len);
675   ret  = SSL_select_next_proto((unsigned char**)out, outlen, (const unsigned char*)server,
676                                server_len, in, inlen);
677   if (ret != OPENSSL_NPN_NEGOTIATED) {
678     lua_pop(L, 2);
679     return SSL_TLSEXT_ERR_NOACK;
680   }
681 
682   // Copy the result because lua_pop() can collect the pointer
683   ctx->alpn = malloc(*outlen);
684   memcpy(ctx->alpn, (void*)*out, *outlen);
685   *out = (const unsigned char*)ctx->alpn;
686 
687   lua_pop(L, 2);
688 
689   return SSL_TLSEXT_ERR_OK;
690 }
691 
692 /**
693  * Set a callback a server can use to select the next protocol with ALPN.
694  */
set_alpn_cb(lua_State * L)695 static int set_alpn_cb(lua_State *L)
696 {
697   p_context ctx = checkctx(L, 1);
698 
699   luaL_getmetatable(L, "SSL:ALPN:Registry");
700   lua_pushlightuserdata(L, (void*)ctx->context);
701   lua_pushvalue(L, 2);
702   lua_settable(L, -3);
703 
704   SSL_CTX_set_alpn_select_cb(ctx->context, alpn_cb, ctx);
705 
706   lua_pushboolean(L, 1);
707   return 1;
708 }
709 
710 #if defined(LSEC_ENABLE_DANE)
711 /*
712  * DANE
713  */
set_dane(lua_State * L)714 static int set_dane(lua_State *L)
715 {
716   int ret;
717   SSL_CTX *ctx = lsec_checkcontext(L, 1);
718   ret = SSL_CTX_dane_enable(ctx);
719   lua_pushboolean(L, (ret > 0));
720   return 1;
721 }
722 #endif
723 
724 /**
725  * Package functions
726  */
727 static luaL_Reg funcs[] = {
728   {"create",          create},
729   {"locations",       load_locations},
730   {"loadcert",        load_cert},
731   {"loadkey",         load_key},
732   {"checkkey",        check_key},
733   {"setalpn",         set_alpn},
734   {"setalpncb",       set_alpn_cb},
735   {"setcipher",       set_cipher},
736   {"setciphersuites", set_ciphersuites},
737   {"setdepth",        set_depth},
738   {"setdhparam",      set_dhparam},
739   {"setverify",       set_verify},
740   {"setoptions",      set_options},
741   {"setmode",         set_mode},
742 #if !defined(OPENSSL_NO_EC)
743   {"setcurve",        set_curve},
744   {"setcurveslist",   set_curves_list},
745 #endif
746 #if defined(LSEC_ENABLE_DANE)
747   {"setdane",         set_dane},
748 #endif
749   {NULL, NULL}
750 };
751 
752 /*-------------------------------- Metamethods -------------------------------*/
753 
754 /**
755  * Collect SSL context -- GC metamethod.
756  */
meth_destroy(lua_State * L)757 static int meth_destroy(lua_State *L)
758 {
759   p_context ctx = checkctx(L, 1);
760   if (ctx->context) {
761     /* Clear registries */
762     luaL_getmetatable(L, "SSL:DH:Registry");
763     lua_pushlightuserdata(L, (void*)ctx->context);
764     lua_pushnil(L);
765     lua_settable(L, -3);
766     luaL_getmetatable(L, "SSL:Verify:Registry");
767     lua_pushlightuserdata(L, (void*)ctx->context);
768     lua_pushnil(L);
769     lua_settable(L, -3);
770     luaL_getmetatable(L, "SSL:ALPN:Registry");
771     lua_pushlightuserdata(L, (void*)ctx->context);
772     lua_pushnil(L);
773     lua_settable(L, -3);
774 
775     SSL_CTX_free(ctx->context);
776     ctx->context = NULL;
777   }
778   return 0;
779 }
780 
781 /**
782  * Object information -- tostring metamethod.
783  */
meth_tostring(lua_State * L)784 static int meth_tostring(lua_State *L)
785 {
786   p_context ctx = checkctx(L, 1);
787   lua_pushfstring(L, "SSL context: %p", ctx);
788   return 1;
789 }
790 
791 /**
792  * Set extra flags for handshake verification.
793  */
meth_set_verify_ext(lua_State * L)794 static int meth_set_verify_ext(lua_State *L)
795 {
796   int i;
797   const char *str;
798   int crl_flag = 0;
799   int lsec_flag = 0;
800   SSL_CTX *ctx = lsec_checkcontext(L, 1);
801   int max = lua_gettop(L);
802   for (i = 2; i <= max; i++) {
803     str = luaL_checkstring(L, i);
804     if (!strcmp(str, "lsec_continue")) {
805       lsec_flag |= LSEC_VERIFY_CONTINUE;
806     } else if (!strcmp(str, "lsec_ignore_purpose")) {
807       lsec_flag |= LSEC_VERIFY_IGNORE_PURPOSE;
808     } else if (!strcmp(str, "crl_check")) {
809       crl_flag |= X509_V_FLAG_CRL_CHECK;
810     } else if (!strcmp(str, "crl_check_chain")) {
811       crl_flag |= X509_V_FLAG_CRL_CHECK_ALL;
812     } else {
813       lua_pushboolean(L, 0);
814       lua_pushfstring(L, "invalid verify option (%s)", str);
815       return 2;
816     }
817   }
818   /* Set callback? */
819   if (lsec_flag) {
820     SSL_CTX_set_verify(ctx, SSL_CTX_get_verify_mode(ctx), verify_cb);
821     SSL_CTX_set_cert_verify_callback(ctx, cert_verify_cb, (void*)ctx);
822     /* Save flag */
823     luaL_getmetatable(L, "SSL:Verify:Registry");
824     lua_pushlightuserdata(L, (void*)ctx);
825     lua_pushnumber(L, lsec_flag);
826     lua_settable(L, -3);
827   } else {
828     SSL_CTX_set_verify(ctx, SSL_CTX_get_verify_mode(ctx), NULL);
829     SSL_CTX_set_cert_verify_callback(ctx, NULL, NULL);
830     /* Remove flag */
831     luaL_getmetatable(L, "SSL:Verify:Registry");
832     lua_pushlightuserdata(L, (void*)ctx);
833     lua_pushnil(L);
834     lua_settable(L, -3);
835   }
836 
837   /* X509 flag */
838   X509_STORE_set_flags(SSL_CTX_get_cert_store(ctx), crl_flag);
839 
840   /* Ok */
841   lua_pushboolean(L, 1);
842   return 1;
843 }
844 
845 /**
846  * Context metamethods.
847  */
848 static luaL_Reg meta[] = {
849   {"__close",    meth_destroy},
850   {"__gc",       meth_destroy},
851   {"__tostring", meth_tostring},
852   {NULL, NULL}
853 };
854 
855 /**
856  * Index metamethods.
857  */
858 static luaL_Reg meta_index[] = {
859   {"setverifyext", meth_set_verify_ext},
860   {NULL, NULL}
861 };
862 
863 
864 /*----------------------------- Public Functions  ---------------------------*/
865 
866 /**
867  * Retrieve the SSL context from the Lua stack.
868  */
lsec_checkcontext(lua_State * L,int idx)869 SSL_CTX* lsec_checkcontext(lua_State *L, int idx)
870 {
871   p_context ctx = checkctx(L, idx);
872   return ctx->context;
873 }
874 
lsec_testcontext(lua_State * L,int idx)875 SSL_CTX* lsec_testcontext(lua_State *L, int idx)
876 {
877   p_context ctx = testctx(L, idx);
878   return (ctx) ? ctx->context : NULL;
879 }
880 
881 /**
882  * Retrieve the mode from the context in the Lua stack.
883  */
lsec_getmode(lua_State * L,int idx)884 int lsec_getmode(lua_State *L, int idx)
885 {
886   p_context ctx = checkctx(L, idx);
887   return ctx->mode;
888 }
889 
890 /*-- Compat - Lua 5.1 --*/
891 #if (LUA_VERSION_NUM == 501)
892 
lsec_testudata(lua_State * L,int ud,const char * tname)893 void *lsec_testudata (lua_State *L, int ud, const char *tname) {
894   void *p = lua_touserdata(L, ud);
895   if (p != NULL) {  /* value is a userdata? */
896     if (lua_getmetatable(L, ud)) {  /* does it have a metatable? */
897       luaL_getmetatable(L, tname);  /* get correct metatable */
898       if (!lua_rawequal(L, -1, -2))  /* not the same? */
899         p = NULL;  /* value is a userdata with wrong metatable */
900       lua_pop(L, 2);  /* remove both metatables */
901       return p;
902     }
903   }
904   return NULL;  /* value is not a userdata with a metatable */
905 }
906 
907 #endif
908 
909 /*------------------------------ Initialization ------------------------------*/
910 
911 /**
912  * Registre the module.
913  */
luaopen_ssl_context(lua_State * L)914 LSEC_API int luaopen_ssl_context(lua_State *L)
915 {
916   luaL_newmetatable(L, "SSL:DH:Registry");      /* Keep all DH callbacks   */
917   luaL_newmetatable(L, "SSL:ALPN:Registry");    /* Keep all ALPN callbacks */
918   luaL_newmetatable(L, "SSL:Verify:Registry");  /* Keep all verify flags   */
919   luaL_newmetatable(L, "SSL:Context");
920   setfuncs(L, meta);
921 
922   /* Create __index metamethods for context */
923   luaL_newlib(L, meta_index);
924   lua_setfield(L, -2, "__index");
925 
926   lsec_load_curves(L);
927 
928   /* Return the module */
929   luaL_newlib(L, funcs);
930 
931   return 1;
932 }
933