• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

zhaozg / lua-openssl / 14788361818

02 May 2025 03:43AM UTC coverage: 88.812% (-4.7%) from 93.466%
14788361818

push

travis-ci

zhaozg
ci: valgrind combine

8954 of 10082 relevant lines covered (88.81%)

1094.64 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

64.81
/src/ssl.c
1
/***
2
ssl modules to create SSL/TLS server or client, send and recv data over SSL channels.
3

4
@module ssl
5
@usage
6
  ssl = require('openssl').ssl
7
*/
8
#include <openssl/dh.h>
9
#include <openssl/ec.h>
10
#include <openssl/rsa.h>
11
#include <openssl/ssl.h>
12

13
#include "openssl.h"
14
#include "private.h"
15
#include "ssl_options.h"
16

17
#include <stdint.h>
18

19
#if OPENSSL_VERSION_NUMBER > 0x30000000
20
#ifndef SSL_get_peer_certificate
21
#define SSL_get_peer_certificate SSL_get1_peer_certificate
22
#endif
23
#ifndef SSL_DEFAULT_CIPHER_LIST
24
#define SSL_DEFAULT_CIPHER_LIST OSSL_default_cipher_list()
25
#endif
26
#endif
27

28
/***
29
create ssl_ctx object, which mapping to SSL_CTX in openssl.
30
@function ctx_new
31
@tparam string protocol support 'SSLv3', 'SSLv23', 'SSLv2', 'TSLv1', 'TSLv1_1','TSLv1_2','TLS',
32
'DTLSv1','DTLSv1_2', and can be follow by '_server' or '_client', in general you should use 'TLS' to
33
negotiate highest available SSL/TLS version
34
@tparam[opt] string support_ciphers, if not given, default of openssl will be used
35
@treturn ssl_ctx
36
*/
37
#if OPENSSL_VERSION_NUMBER > 0x10100000L
38
#define TLS_PROTOCOL_TIPS                                                                          \
39
  "only support TLS, DTLS to negotiate highest available SSL/TLS or DTLS "                         \
40
  "version above openssl v1.1.0\n"                                                                 \
41
  "optional followed by _client or _server\n"                                                      \
42
  "default is TLS\n"
43
#define DEFAULT_PROTOCOL "TLS"
44
#else
45
#define TLS_PROTOCOL_TIPS                                                                          \
46
  "SSLv23, TLSv1_2, TLSv1_1, TLSv1, DTLSv1_2 or DTLSv1, optional followed by _client or _server\n" \
47
  "optional followed by _client or _server\n"                                                      \
48
  "default is SSLv23 to negotiate highest available SSL/TLS\n"
49
#define DEFAULT_PROTOCOL "SSLv23"
50
#endif
51

52
typedef enum
53
{
54
  SSL_CTX_SESSION_ADD = 0,
55
  SSL_CTX_SESSION_GET,
56
  SSL_CTX_SESSION_DEL,
57
#if OPENSSL_VERSION_NUMBER < 0x10100000L
58

59
  SSL_CTX_TEMP_DH,
60
  SSL_CTX_TEMP_RSA,
61
  SSL_CTX_TEMP_ECDH,
62
#endif
63
  SSL_CTX_MAX_IDX
64
} SSL_CTX_INDEX;
65

66
static int
67
openssl_ssl_ctx_new(lua_State *L)
37✔
68
{
69
  const char *meth = luaL_optstring(L, 1, DEFAULT_PROTOCOL);
37✔
70
#if OPENSSL_VERSION_NUMBER >= 0x01000000L
71
  const
72
#endif
73
    SSL_METHOD *method
37✔
74
    = NULL;
75
  const char *ciphers;
76
  SSL_CTX    *ctx;
77

78
  if (strcmp(meth, "SSLv23") == 0)
37✔
79
    method = SSLv23_method();
3✔
80
  else if (strcmp(meth, "SSLv23_server") == 0)
34✔
81
    method = SSLv23_server_method();
6✔
82
  else if (strcmp(meth, "SSLv23_client") == 0)
28✔
83
    method = SSLv23_client_method();
2✔
84

85
#if OPENSSL_VERSION_NUMBER > 0x10100000L
86
  else if (strcmp(meth, "TLS") == 0)
87
    method = TLS_method();
88
  else if (strcmp(meth, "TLS_server") == 0)
89
    method = TLS_server_method();
90
  else if (strcmp(meth, "TLS_client") == 0)
91
    method = TLS_client_method();
92

93
  else if (strcmp(meth, "DTLS") == 0)
94
    method = DTLS_method();
95
  else if (strcmp(meth, "DTLS_server") == 0)
96
    method = DTLS_server_method();
97
  else if (strcmp(meth, "DTLS_client") == 0)
98
    method = DTLS_client_method();
99
#endif
100

101
#if !defined(OPENSSL_NO_DEPRECATED) && !defined(OPENSSL_NO_DTLS1_2_METHOD)
102
  else if (strcmp(meth, "DTLSv1_2") == 0)
26✔
103
    method = DTLSv1_2_method();
×
104
  else if (strcmp(meth, "DTLSv1_2_server") == 0)
26✔
105
    method = DTLSv1_2_server_method();
×
106
  else if (strcmp(meth, "DTLSv1_2_client") == 0)
26✔
107
    method = DTLSv1_2_client_method();
1✔
108
#endif
109

110
#if !defined(OPENSSL_NO_DEPRECATED) && !defined(OPENSSL_NO_DTLS1_METHOD)
111
  else if (strcmp(meth, "DTLSv1") == 0)
25✔
112
    method = DTLSv1_method();
×
113
  else if (strcmp(meth, "DTLSv1_server") == 0)
25✔
114
    method = DTLSv1_server_method();
×
115
  else if (strcmp(meth, "DTLSv1_client") == 0)
25✔
116
    method = DTLSv1_client_method();
1✔
117
#endif
118

119
#if !defined(OPENSSL_NO_DEPRECATED) && !defined(OPENSSL_NO_TLS1_2_METHOD)
120
  else if (strcmp(meth, "TLSv1_2") == 0)
24✔
121
    method = TLSv1_2_method();
×
122
  else if (strcmp(meth, "TLSv1_2_server") == 0)
24✔
123
    method = TLSv1_2_server_method();
×
124
  else if (strcmp(meth, "TLSv1_2_client") == 0)
24✔
125
    method = TLSv1_2_client_method();
1✔
126
#endif
127

128
#if !defined(OPENSSL_NO_DEPRECATED) && !defined(OPENSSL_NO_TLS1_1_METHOD)
129
  else if (strcmp(meth, "TLSv1_1") == 0)
23✔
130
    method = TLSv1_1_method();
×
131
  else if (strcmp(meth, "TLSv1_1_server") == 0)
23✔
132
    method = TLSv1_1_server_method();
×
133
  else if (strcmp(meth, "TLSv1_1_client") == 0)
23✔
134
    method = TLSv1_1_client_method();
1✔
135
#endif
136

137
#if !defined(OPENSSL_NO_DEPRECATED) && !defined(OPENSSL_NO_TLS1_METHOD)
138
  else if (strcmp(meth, "TLSv1") == 0)
22✔
139
    method = TLSv1_method();
×
140
  else if (strcmp(meth, "TLSv1_server") == 0)
22✔
141
    method = TLSv1_server_method();
×
142
  else if (strcmp(meth, "TLSv1_client") == 0)
22✔
143
    method = TLSv1_client_method();
1✔
144
#endif
145

146
#ifndef OPENSSL_NO_SSL3_METHOD
147
  else if (strcmp(meth, "SSLv3") == 0)
21✔
148
    method = SSLv3_method();
×
149
  else if (strcmp(meth, "SSLv3_server") == 0)
21✔
150
    method = SSLv3_server_method();
×
151
  else if (strcmp(meth, "SSLv3_client") == 0)
21✔
152
    method = SSLv3_client_method();
1✔
153
#endif
154

155
#ifdef LOAD_SSL_CUSTOM
156
  LOAD_SSL_CUSTOM
157
#endif
158
  else luaL_argerror(L, 1, TLS_PROTOCOL_TIPS);
20✔
159

160
  ctx = SSL_CTX_new(method);
17✔
161
  if (!ctx) luaL_argerror(L, 1, TLS_PROTOCOL_TIPS);
17✔
162

163
  ciphers = luaL_optstring(L, 2, SSL_DEFAULT_CIPHER_LIST);
17✔
164
#if OPENSSL_VERSION_NUMBER > 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
165
  if (!SSL_CTX_set_ciphersuites(ctx, ciphers) && !SSL_CTX_set_cipher_list(ctx, ciphers))
166
#else
167
  if (!SSL_CTX_set_cipher_list(ctx, ciphers))
17✔
168
#endif
169
    luaL_argerror(L, 2, "Error to set cipher list");
×
170

171
  PUSH_OBJECT(ctx, "openssl.ssl_ctx");
17✔
172
  SSL_CTX_set_app_data(ctx, openssl_mainthread(L));
17✔
173
  openssl_newvalue(L, ctx);
17✔
174

175
  return 1;
17✔
176
}
177

178
/***
179
get alert_type for ssl state
180
@function alert_type
181
@tparam number alert
182
@tparam[opt=false] boolean long
183
@treturn string alert type
184
*/
185
static int
186
openssl_ssl_alert_type(lua_State *L)
6✔
187
{
188
  int         v = luaL_checkint(L, 1);
6✔
189
  int         _long = lua_isnone(L, 2) ? 0 : auxiliar_checkboolean(L, 2);
6✔
190
  const char *val;
191

192
  if (_long)
6✔
193
    val = SSL_alert_type_string_long(v << 8);
3✔
194
  else
195
    val = SSL_alert_type_string(v << 8);
3✔
196
  lua_pushstring(L, val);
6✔
197

198
  return 1;
6✔
199
}
200

201
/***
202
get alert_desc for ssl state
203
@function alert_desc
204
@tparam number alert
205
@tparam[opt=false] boolean long
206
@treturn string alert type
207
@treturn string desc string, if long set true will return long info
208
*/
209
static int
210
openssl_ssl_alert_desc(lua_State *L)
24✔
211
{
212
  int         v = luaL_checkint(L, 1);
24✔
213
  int         _long = lua_isnone(L, 2) ? 0 : auxiliar_checkboolean(L, 2);
24✔
214
  const char *val;
215

216
  if (_long)
24✔
217
    val = SSL_alert_desc_string_long(v);
12✔
218
  else
219
    val = SSL_alert_desc_string(v);
12✔
220
  lua_pushstring(L, val);
24✔
221

222
  return 1;
24✔
223
}
224

225
static int
226
openssl_ssl_session_new(lua_State *L)
1✔
227
{
228
  SSL_SESSION *ss = SSL_SESSION_new();
1✔
229
  PUSH_OBJECT(ss, "openssl.ssl_session");
1✔
230
  return 1;
1✔
231
}
232

233
static int
234
openssl_ssl_session_read(lua_State *L)
1✔
235
{
236
  BIO         *in = load_bio_object(L, 1);
1✔
237
  SSL_SESSION *ss = PEM_read_bio_SSL_SESSION(in, NULL, NULL, NULL);
1✔
238
  if (!ss) {
1✔
239
    (void)BIO_reset(in);
×
240
    ss = d2i_SSL_SESSION_bio(in, NULL);
×
241
  }
242
  BIO_free(in);
1✔
243
  if (ss) {
1✔
244
    PUSH_OBJECT(ss, "openssl.ssl_session");
1✔
245
    return 1;
1✔
246
  }
247
  return openssl_pushresult(L, 0);
×
248
}
249

250
static luaL_Reg R[] = {
251
  { "ctx_new",      openssl_ssl_ctx_new      },
252
  { "alert_type",   openssl_ssl_alert_type   },
253
  { "alert_desc",   openssl_ssl_alert_desc   },
254

255
  { "session_new",  openssl_ssl_session_new  },
256
  { "session_read", openssl_ssl_session_read },
257
  { NULL,           NULL                     }
258
};
259

260
/****************************SSL CTX********************************/
261
/***
262
openssl.ssl_ctx object
263
@type ssl_ctx
264
*/
265

266
/***
267
tell ssl_ctx use private key and certificate, and check private key
268
@function use
269
@tparam evp_pkey pkey
270
@tparam x509 cert
271
@treturn boolean result return true for ok, or nil followed by errmsg and errval
272
*/
273
static int
274
openssl_ssl_ctx_use(lua_State *L)
6✔
275
{
276
  int       ret;
277
  SSL_CTX  *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
6✔
278
  EVP_PKEY *pkey = CHECK_OBJECT(2, EVP_PKEY, "openssl.evp_pkey");
6✔
279

280
  if (lua_isstring(L, 3)) {
6✔
281
    ret = SSL_CTX_use_certificate_chain_file(ctx, luaL_checkstring(L, 3));
×
282
  } else {
283
    X509 *cert = CHECK_OBJECT(3, X509, "openssl.x509");
6✔
284
    ret = SSL_CTX_use_certificate(ctx, cert);
6✔
285
  }
286
  if (ret == 1) {
6✔
287
    ret = SSL_CTX_use_PrivateKey(ctx, pkey);
6✔
288
    if (ret == 1) {
6✔
289
      ret = SSL_CTX_check_private_key(ctx);
6✔
290
    }
291
  }
292
  return openssl_pushresult(L, ret);
6✔
293
}
294

295
/***
296
add client ca cert and option extra chain cert
297
@function add
298
@tparam x509 clientca
299
@tparam[opt] table extra_chain_cert_array
300
@treturn boolean result
301
*/
302
static int
303
openssl_ssl_ctx_add(lua_State *L)
1✔
304
{
305
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
1✔
306
  X509    *x = CHECK_OBJECT(2, X509, "openssl.x509");
1✔
307
  int      ret = SSL_CTX_add_client_CA(ctx, x);
1✔
308
  if (ret == 1 && !lua_isnone(L, 3)) {
1✔
309
    size_t i;
310
    luaL_checktable(L, 3);
1✔
311

312
    for (i = 1; ret == 1 && i <= lua_rawlen(L, 3); i++) {
4✔
313
      lua_rawgeti(L, 3, i);
3✔
314
      x = CHECK_OBJECT(2, X509, "openssl.x509");
3✔
315
      lua_pop(L, 1);
3✔
316
      X509_up_ref(x);
3✔
317
      ret = SSL_CTX_add_extra_chain_cert(ctx, x);
3✔
318
    }
319
  }
320
  return openssl_pushresult(L, ret);
1✔
321
}
322

323
static int
324
openssl_ssl_ctx_gc(lua_State *L)
17✔
325
{
326
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
17✔
327
  SSL_CTX_free(ctx);
17✔
328
  openssl_freevalue(L, ctx);
17✔
329

330
  return 0;
17✔
331
}
332

333
/***
334
get timeout
335
@function timeout
336
@return number
337
*/
338
/***
339
set timeout
340
@function timeout
341
@tparam number timeout
342
@treturn number previous timeout
343
*/
344
static int
345
openssl_ssl_ctx_timeout(lua_State *L)
2✔
346
{
347
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
2✔
348
  long     t;
349
  if (!lua_isnone(L, 2)) {
2✔
350
    t = SSL_CTX_set_timeout(ctx, luaL_checkint(L, 2));
1✔
351
    lua_pushinteger(L, t);
1✔
352
    return 1;
1✔
353
  }
354
  t = SSL_CTX_get_timeout(ctx);
1✔
355
  lua_pushinteger(L, t);
1✔
356
  return 1;
1✔
357
}
358

359
static const int iMode_options[] = { SSL_MODE_ENABLE_PARTIAL_WRITE,
360
                                     SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER,
361
                                     SSL_MODE_AUTO_RETRY,
362
                                     SSL_MODE_NO_AUTO_CHAIN,
363
#ifdef SSL_MODE_RELEASE_BUFFERS
364
                                     SSL_MODE_RELEASE_BUFFERS,
365
#endif
366
                                     0 };
367

368
static const char *sMode_options[] = { "enable_partial_write",
369
                                       "accept_moving_write_buffer",
370
                                       "auto_retry",
371
                                       "no_auto_chain",
372
#ifdef SSL_MODE_RELEASE_BUFFERS
373
                                       "release_buffers",
374
#endif
375
                                       NULL };
376

377
/***
378
clean given mode
379
mode support
380
'enable_partial_write','accept_moving_write_buffer','auto_retry','no_auto_chain','release_buffers'
381
@function mode
382
@tparam boolean clear must be true
383
@tparam string mode
384
@param[opt] ...
385
@treturn string
386
@treturn ...
387
@usage
388
 modes = { ssl_ctx:mode('enable_partial_write','accept_moving_write_buffer','auto_retry') },
389

390
  for  i, v in ipairs(modes)
391
    print(v)
392
 end
393
 --output 'enable_partial_write','accept_moving_write_buffer','auto_retry'
394
*/
395
static int
396
openssl_ssl_ctx_mode(lua_State *L)
2✔
397
{
398
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
2✔
399
  int      mode = 0;
2✔
400
  int      ret;
401
  int      i;
402
  if (!lua_isnoneornil(L, 2)) {
2✔
403
    int clear = 0;
2✔
404
    if (lua_isboolean(L, 2)) {
2✔
405
      clear = lua_toboolean(L, 2);
2✔
406
      i = 3;
2✔
407
    } else
408
      i = 2;
×
409
    while (i <= lua_gettop(L)) {
10✔
410
      mode = mode | auxiliar_checkoption(L, i++, NULL, sMode_options, iMode_options);
8✔
411
    }
412
    if (clear != 0)
2✔
413
      mode = SSL_CTX_set_mode(ctx, mode);
1✔
414
    else
415
      mode = SSL_CTX_clear_mode(ctx, mode);
1✔
416
  } else
417
    mode = SSL_CTX_get_mode(ctx);
×
418
  ret = 0;
2✔
419
  for (i = 0; i < sizeof(iMode_options) / sizeof(int); i++) {
14✔
420
    if (mode & iMode_options[i]) {
12✔
421
      lua_pushstring(L, sMode_options[i]);
4✔
422
      ret++;
4✔
423
    }
424
  }
425
  return ret;
2✔
426
};
427

428
/***
429
get options
430
@function options
431
@treturn table string list of current options
432
*/
433

434
/***
435
set options
436
@function options
437
@tparam string option, support "microsoft_sess_id_bug", "netscape_challenge_bug",
438
"netscape_reuse_cipher_change_bug", "sslref2_reuse_cert_type_bug", "microsoft_big_sslv3_buffer",
439
"msie_sslv3_rsa_padding","ssleay_080_client_dh_bug",
440
"tls_d5_bug","tls_block_padding_bug","dont_insert_empty_fragments","all", please to see
441
ssl_options.h
442
@treturn table string list of current options after set new option
443
*/
444

445
/***
446
clear options
447
@function options
448
@tparam boolean clear set true to clear options
449
@tparam string option, support "microsoft_sess_id_bug", "netscape_challenge_bug",
450
"netscape_reuse_cipher_change_bug", "sslref2_reuse_cert_type_bug", "microsoft_big_sslv3_buffer",
451
"msie_sslv3_rsa_padding","ssleay_080_client_dh_bug",
452
"tls_d5_bug","tls_block_padding_bug","dont_insert_empty_fragments","all",  please to see
453
ssl_options.h
454
@treturn table string list of current options after clear some option
455
*/
456
static int
457
openssl_ssl_ctx_options(lua_State *L)
12✔
458
{
459
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
12✔
460
  long     options = 0;
12✔
461
  int      ret;
462
  int      i;
463
  if (!lua_isnone(L, 2)) {
12✔
464
    int top = lua_gettop(L);
10✔
465
    int clear = 0;
10✔
466
    if (lua_isboolean(L, 2)) {
10✔
467
      clear = lua_toboolean(L, 2);
2✔
468
      i = 3;
2✔
469
    } else
470
      i = 2;
8✔
471
    for (; i <= top; i++) {
21✔
472
      if (lua_isnumber(L, i))
12✔
473
        options |= (long)luaL_checkinteger(L, i);
9✔
474
      else {
475
        const char *s = luaL_checkstring(L, i);
3✔
476
        int         j;
477
        for (j = 0; ssl_options[j].name; j++) {
44✔
478
          LuaL_Enumeration e = ssl_options[j];
44✔
479
          if (strcasecmp(s, e.name) == 0) {
44✔
480
            options |= e.val;
2✔
481
            break;
2✔
482
          }
483
        }
484
      }
485
    }
486

487
    if (clear != 0)
9✔
488
      options = SSL_CTX_clear_options(ctx, options);
1✔
489
    else
490
      options = SSL_CTX_set_options(ctx, options);
8✔
491
  } else
492
    options = SSL_CTX_get_options(ctx);
2✔
493

494
  lua_newtable(L);
11✔
495
  ret = 0;
11✔
496
  for (i = 0; ssl_options[i].name; i++) {
385✔
497
    LuaL_Enumeration e = ssl_options[i];
374✔
498
    if (options & e.val) {
374✔
499
      lua_pushstring(L, e.name);
42✔
500
      ret++;
42✔
501
      lua_rawseti(L, -2, ret);
42✔
502
    }
503
  }
504
  return 1;
11✔
505
}
506

507
/***
508
get min_proto_version and max_proto_version
509
@function version
510
@treturn[1] integer min_proto_version
511
@treturn[2] integer man_proto_version
512
*/
513

514
/***
515
set min_proto_version and max_proto_version
516
@function options
517
@tparam integer min
518
@tparam integer max
519
@treturn boolean result or fail
520
*/
521
#if OPENSSL_VERSION_NUMBER > 0x10100000L
522
static int
523
openssl_ssl_ctx_version(lua_State *L)
524
{
525
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
526
  int      ret;
527
  int      minv = SSL_CTX_get_min_proto_version(ctx);
528
  int      maxv = SSL_CTX_get_max_proto_version(ctx);
529

530
  if (lua_isnone(L, 2)) {
531
    lua_pushinteger(L, minv);
532
    lua_pushinteger(L, maxv);
533
    return 2;
534
  }
535

536
  minv = luaL_optinteger(L, 2, minv);
537
  maxv = luaL_optinteger(L, 3, maxv);
538
  luaL_argcheck(L, minv <= maxv, 3, "max version can't less than min");
539

540
  ret = SSL_CTX_set_min_proto_version(ctx, minv);
541
  if (ret == 1) ret = SSL_CTX_set_min_proto_version(ctx, maxv);
542

543
  if (ret == 1) {
544
    lua_pushvalue(L, 1);
545
    return 1;
546
  }
547
  return openssl_pushresult(L, ret);
548
}
549
#endif
550

551
/***
552
get quit_shutdown is set or not
553
Normally when a SSL connection is finished, the parties must send out
554
"close notify" alert messages using ***SSL:shutdown"*** for a clean shutdown.
555
@function quiet_shutdown
556
@treturn boolean result
557
*/
558
/***
559
set quiet_shutdown
560
@function quiet_shutdown
561
@tparam boolean quiet
562
When setting the "quiet shutdown" flag to 1, ***SSL:shutdown*** will set the internal flags
563
to SSL_SENT_SHUTDOWN|SSL_RECEIVED_SHUTDOWN. ***SSL:shutdown*** then behaves like
564
***SSL:set_shutdown*** called with SSL_SENT_SHUTDOWN|SSL_RECEIVED_SHUTDOWN.
565
The session is thus considered to be shutdown, but no "close notify" alert
566
is sent to the peer. This behaviour violates the TLS standard.
567
The default is normal shutdown behaviour as described by the TLS standard.
568
@treturn boolean result
569
*/
570
static int
571
openssl_ssl_ctx_quiet_shutdown(lua_State *L)
2✔
572
{
573
  SSL_CTX *s = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
2✔
574
  if (lua_isnone(L, 2)) {
2✔
575
    int m = SSL_CTX_get_quiet_shutdown(s);
1✔
576
    lua_pushinteger(L, m);
1✔
577
    return 1;
1✔
578
  } else {
579
    int m = luaL_checkint(L, 2);
1✔
580
    SSL_CTX_set_quiet_shutdown(s, m);
1✔
581
    return 0;
1✔
582
  }
583
};
584

585
/***
586
set verify locations with cafile and capath
587
ssl_ctx:verify_locations specifies the locations for *ctx*, at
588
which CA certificates for verification purposes are located. The certificates
589
available via *CAfile* and *CApath* are trusted.
590
@function verify_locations
591
@tparam string cafile
592
@tparam string capath
593
@treturn boolean result
594
*/
595
static int
596
openssl_ssl_ctx_load_verify_locations(lua_State *L)
1✔
597
{
598
  SSL_CTX    *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
1✔
599
  const char *CAfile = luaL_checkstring(L, 2);
1✔
600
  const char *CApath = luaL_optstring(L, 3, NULL);
1✔
601
#if (OPENSSL_VERSION_NUMBER >= 0x30000000L)
602
  int ret = !(CAfile == NULL && CApath == NULL);
603
  if (CAfile != NULL) ret = SSL_CTX_load_verify_file(ctx, CAfile);
604
  if (ret == 1 && CApath != NULL) ret = SSL_CTX_load_verify_dir(ctx, CApath);
605
#else
606
  int ret = SSL_CTX_load_verify_locations(ctx, CAfile, CApath);
1✔
607
#endif
608
  return openssl_pushresult(L, ret);
1✔
609
}
610

611
/***
612
get certificate verification store of ssl_ctx
613
@function cert_store
614
@treturn x509_store store
615
*/
616
/***
617
set or replaces then certificate verification store of ssl_ctx
618
@function cert_store
619
@tparam x509_store store
620
@treturn x509_store store
621
*/
622
static int
623
openssl_ssl_ctx_cert_store(lua_State *L)
4✔
624
{
625
#if OPENSSL_VERSION_NUMBER > 0x10002000L
626
  SSL_CTX    *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
4✔
627
  X509_STORE *store = NULL;
4✔
628
  if (lua_isnone(L, 2)) {
4✔
629
    store = SSL_CTX_get_cert_store(ctx);
1✔
630
    X509_STORE_up_ref(store);
1✔
631
    PUSH_OBJECT(store, "openssl.x509_store");
1✔
632
    return 1;
1✔
633
  } else {
634
    store = CHECK_OBJECT(2, X509_STORE, "openssl.x509_store");
3✔
635
    X509_STORE_up_ref(store);
3✔
636
    SSL_CTX_set_cert_store(ctx, store);
3✔
637
    X509_STORE_set_trust(store, 1);
3✔
638
    return 0;
3✔
639
  }
640
#else
641
  luaL_error(L, "NYI, openssl below 1.0.2 not fully support this feature");
642
  return 0;
643
#endif
644
}
645

646
#ifndef OPENSSL_NO_ENGINE
647
static int
648
openssl_ssl_ctx_set_engine(lua_State *L)
1✔
649
{
650
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
1✔
651
  ENGINE  *eng = CHECK_OBJECT(2, ENGINE, "openssl.engine");
1✔
652
  int      ret = SSL_CTX_set_client_cert_engine(ctx, eng);
1✔
653
  return openssl_pushresult(L, ret);
1✔
654
}
655
#endif
656

657
/****************************************************************************/
658
/***
659
create ssl object
660
@function ssl
661
@tparam number fd
662
@tparam[opt=false] boolean server, true will make ssl server
663
@treturn ssl
664
*/
665
/***
666
create ssl object
667
@function ssl
668
@tparam bio input
669
@tparam[opt=input] bio ouput, default will use input as output
670
@tparam[opt=false] boolean server, true will make ssl server
671
@treturn ssl
672
*/
673
static int
674
openssl_ssl_ctx_new_ssl(lua_State *L)
11✔
675
{
676
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
11✔
677
  int      server = 0;
11✔
678
  int      mode_idx = 2;
11✔
679
  SSL     *ssl = SSL_new(ctx);
11✔
680
  int      ret = 1;
11✔
681

682
  if (auxiliar_getclassudata(L, "openssl.bio", 2)) {
11✔
683
    BIO *bi = CHECK_OBJECT(2, BIO, "openssl.bio");
10✔
684
    BIO *bo = bi;
10✔
685

686
    /* avoid bi be gc */
687
    BIO_up_ref(bi);
10✔
688

689
    if (auxiliar_getclassudata(L, "openssl.bio", 3)) {
10✔
690
      bo = CHECK_OBJECT(3, BIO, "openssl.bio");
2✔
691
      mode_idx = 4;
2✔
692
    } else
693
      mode_idx = 3;
8✔
694

695
    /* avoid bo be gc */
696
    BIO_up_ref(bo);
10✔
697

698
#if OPENSSL_VERSION_NUMBER > 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
699
    SSL_set0_rbio(ssl, bi);
700
    SSL_set0_wbio(ssl, bo);
701
#else
702
    SSL_set_bio(ssl, bi, bo);
10✔
703
#endif
704
    ret = 1;
10✔
705
  } else if (lua_isnumber(L, 2)) {
1✔
706
    ret = SSL_set_fd(ssl, luaL_checkint(L, 2));
×
707
    mode_idx = 3;
×
708
  }
709

710
  if (ret == 1 && !lua_isnone(L, mode_idx)) {
11✔
711
    server = lua_isnil(L, mode_idx) ? 0 : auxiliar_checkboolean(L, mode_idx);
6✔
712
  }
713

714
  if (ret == 1) {
11✔
715
    if (server)
11✔
716
      SSL_set_accept_state(ssl);
3✔
717
    else
718
      SSL_set_connect_state(ssl);
8✔
719

720
    PUSH_OBJECT(ssl, "openssl.ssl");
11✔
721
    openssl_newvalue(L, ssl);
11✔
722

723
    /* ref to ctx */
724
    lua_pushvalue(L, 1);
11✔
725
    openssl_valueset(L, ssl, "ctx");
11✔
726
  } else {
727
    SSL_free(ssl);
×
728
    openssl_freevalue(L, ssl);
×
729
    return openssl_pushresult(L, ret);
×
730
  }
731
  return 1;
11✔
732
}
733

734
/***
735
create bio object
736
@function bio
737
@tparam string host_addr format like 'host:port'
738
@tparam[opt=false] boolean server, true listen at host_addr,false connect to host_addr
739
@tparam[opt=true] boolean autoretry ssl operation autoretry mode
740
@treturn bio bio object
741
*/
742
static int
743
openssl_ssl_ctx_new_bio(lua_State *L)
×
744
{
745
  SSL_CTX    *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
×
746
  const char *host_addr = luaL_checkstring(L, 2);
×
747
  int         server = lua_isnone(L, 3) ? 0 : auxiliar_checkboolean(L, 3);
×
748
  int         autoretry = lua_isnone(L, 4) ? 1 : auxiliar_checkboolean(L, 4);
×
749

750
  BIO *bio = server ? BIO_new_ssl(ctx, 0) : BIO_new_ssl_connect(ctx);
×
751
  if (bio) {
×
752
    int ret = 0;
×
753
    if (autoretry) {
×
754
      SSL *ssl = NULL;
×
755
      ret = BIO_get_ssl(bio, &ssl);
×
756
      if (ret == 1) SSL_set_mode(ssl, SSL_MODE_AUTO_RETRY);
×
757
    }
758
    if (server) {
×
759
      BIO *acpt = BIO_new_accept((char *)host_addr);
×
760
      BIO_set_accept_bios(acpt, bio);
×
761
      bio = acpt;
×
762
    } else {
763
      ret = BIO_set_conn_hostname(bio, host_addr);
×
764
    }
765
    if (ret == 1) {
×
766
      PUSH_OBJECT(bio, "openssl.bio");
×
767
      return 1;
×
768
    } else
769
      return openssl_pushresult(L, ret);
×
770
  } else {
771
    BIO_free(bio);
×
772
    bio = NULL;
×
773
    return 0;
×
774
  }
775
}
776

777
/***
778
get verify depth when cert chain veirition
779
@function verify_depth
780
@treturn number depth
781
*/
782
/***
783
set verify depth when cert chain veirition
784
@function verify_depth
785
@tparam number depth
786
@treturn number depth
787
*/
788
static int
789
openssl_ssl_ctx_verify_depth(lua_State *L)
1✔
790
{
791
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
1✔
792
  int      depth;
793
  if (!lua_isnone(L, 2)) {
1✔
794
    depth = luaL_checkint(L, 2);
1✔
795
    SSL_CTX_set_verify_depth(ctx, depth);
1✔
796
  }
797
  depth = SSL_CTX_get_verify_depth(ctx);
1✔
798
  lua_pushinteger(L, depth);
1✔
799
  return 1;
1✔
800
}
801

802
static const int iVerifyMode_Options[] = { SSL_VERIFY_NONE,
803
                                           SSL_VERIFY_PEER,
804
                                           SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
805
                                           SSL_VERIFY_CLIENT_ONCE,
806
                                           0 };
807

808
static const char *sVerifyMode_Options[] = { "none",
809
                                             "peer",
810
                                             "fail", /* fail_if_no_peer_cert */
811
                                             "once",
812
                                             NULL };
813

814
/***
815
get verify_mode, return number mode and all string modes list
816
@function verify_mode
817
@treturn number mode_code
818
@return ...
819
  none: not verify client cert
820
  peer: verify client cert
821
  fail: if client not have cert, will failure
822
  once: verify client only once.
823
@usage
824
  mode = {ctx:verify_mode()}
825
  print('integer mode',mode[1])
826
  for i=2, #mode then
827
    print('string mode:'..mode[i])
828
  end
829
*/
830
/***
831
set ssl verify mode and callback
832
@function verify_mode
833
@tparam number mode, mode set to ctx, must be ssl.none or ssl.peer, and ssl.peer support combine
834
with ssl.fail or ssl.once
835
@tparam[opt=nil] function ssl verify callback in lua function, not give will use default openssl
836
callback, when mode is 'none', will be ignore this verify_cb must be boolean function(verifyarg)
837
prototype, return true to continue or false to end ssl handshake verifyarg has field 'error',
838
'error_string','error_depth','current_cert', and 'preverify_ok'
839
@treturn boolean result
840
*/
841
static int
842
openssl_ssl_ctx_verify_mode(lua_State *L)
2✔
843
{
844
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
2✔
845
  if (lua_gettop(L) > 1) {
2✔
846
    int mode = luaL_checkint(L, 2);
1✔
847
    luaL_argcheck(
1✔
848
      L,
849
      mode == SSL_VERIFY_NONE
850
        || (mode & ~(SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT | SSL_VERIFY_CLIENT_ONCE))
851
             == 0,
852
      2,
853
      "must be none or peer(combined with fail, once or none");
854

855
    luaL_argcheck(L, lua_isnone(L, 3) || lua_isfunction(L, 3), 3, "must be callback function");
1✔
856

857
    if (lua_isfunction(L, 3)) {
1✔
858
      lua_pushvalue(L, 3);
1✔
859
      openssl_valueset(L, ctx, "verify_cb");
1✔
860
      SSL_CTX_set_verify(ctx, mode, openssl_verify_cb);
1✔
861
    } else {
862
      lua_pushnil(L);
×
863
      openssl_valueset(L, ctx, "verify_cb");
×
864
      SSL_CTX_set_verify(ctx, mode, openssl_verify_cb);
×
865
    }
866
    return 0;
1✔
867
  } else {
868
    int i = 0;
1✔
869
    int mode = SSL_CTX_get_verify_mode(ctx);
1✔
870
    lua_pushinteger(L, mode);
1✔
871
    i += 1;
1✔
872

873
    if (mode == SSL_VERIFY_NONE) {
1✔
874
      lua_pushstring(L, "none");
1✔
875
      i += 1;
1✔
876
    } else {
877
      if (mode & SSL_VERIFY_PEER) {
×
878
        lua_pushstring(L, "peer");
×
879
        i += 1;
×
880

881
        if (mode & SSL_VERIFY_FAIL_IF_NO_PEER_CERT) {
×
882
          lua_pushstring(L, "fail");
×
883
          i += 1;
×
884
        }
885
        if (mode & SSL_VERIFY_CLIENT_ONCE) {
×
886
          lua_pushstring(L, "once");
×
887
          i += 1;
×
888
        }
889
      }
890
    }
891
    return i;
1✔
892
  }
893
}
894

895
/***
896
set certificate verify callback function
897
@function set_cert_verify
898
@tparam[opt] function cert_verify_cb with boolean function(verifyargs) prototype, if nil or none
899
will use openssl default callback verifyargs has field 'error',
900
'error_string','error_depth','current_cert'
901
*/
902
/***
903
set certificate verify options
904
@function set_cert_verify
905
@tparam table verify_cb_flag support field always_continue with boolean value and verify_depth with
906
number value.
907
*/
908
static int
909
openssl_ssl_ctx_set_cert_verify(lua_State *L)
5✔
910
{
911
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
5✔
912
  luaL_argcheck(L,
5✔
913
                lua_isnone(L, 2) || lua_isfunction(L, 2) || lua_istable(L, 2),
914
                2,
915
                "need function or table contains flags");
916
  if (lua_istable(L, 2)) {
5✔
917
    lua_pushvalue(L, 2);
3✔
918
    openssl_valueset(L, ctx, "verify_cb_flags");
3✔
919
    SSL_CTX_set_cert_verify_callback(ctx, openssl_cert_verify_cb, openssl_mainthread(L));
3✔
920
  } else if (lua_isfunction(L, 2)) {
2✔
921
    lua_pushvalue(L, 2);
×
922
    openssl_valueset(L, ctx, "cert_verify_cb");
×
923
    SSL_CTX_set_cert_verify_callback(ctx, openssl_cert_verify_cb, openssl_mainthread(L));
×
924
  } else
925
    SSL_CTX_set_cert_verify_callback(ctx, NULL, NULL);
2✔
926
  return 0;
5✔
927
}
928

929
#if OPENSSL_VERSION_NUMBER >= 0x10002000L
930
/***
931
set the list of client ALPN protocols available to be negotiated by the server
932
@function set_alpn_protos
933
@tparam table protos the protocol list
934
*/
935
static int
936
openssl_ssl_ctx_set_alpn_protos(lua_State *L)
×
937
{
938
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
×
939

940
  if (lua_istable(L, 2)) {
×
941
    size_t         proto_list_len = 0;
×
942
    size_t         proto_list_size = 256;
×
943
    unsigned char *proto_list = malloc(proto_list_size);
×
944
    size_t         proto_len;
945
    const char    *proto;
946
    int            i;
947
    int            l = lua_rawlen(L, 2);
×
948
    char          *err = NULL;
×
949

950
    for (i = 1; i <= l; i++) {
×
951
      lua_rawgeti(L, 2, i);
×
952
      proto = lua_tolstring(L, -1, &proto_len);
×
953
      lua_pop(L, 1);
×
954
      if (proto == NULL) {
×
955
        err = "invalid protocol value";
×
956
        break;
×
957
      }
958
      if (proto_len > 255) {
×
959
        err = "too long protocol value";
×
960
        break;
×
961
      }
962
      if (proto_list_len + proto_len >= proto_list_size) {
×
963
        do {
964
          proto_list_size = proto_list_size * 2;
×
965
        } while (proto_list_len + proto_len >= proto_list_size);
×
966
        proto_list = realloc(proto_list, proto_list_size);
×
967
      }
968
      if (proto_list == NULL) {
×
969
        err = "fail to allocate protocol list";
×
970
        break;
×
971
      }
972
      proto_list[proto_list_len++] = proto_len;
×
973
      memcpy(proto_list + proto_list_len, proto, proto_len);
×
974
      proto_list_len += proto_len;
×
975
    }
976
    if (err == NULL) {
×
977
      if (SSL_CTX_set_alpn_protos(ctx, proto_list, proto_list_len) != 0) {
×
978
        err = "fail to set ALPN protocols";
×
979
      }
980
    }
981
    free(proto_list);
×
982
    if (err != NULL) return luaL_error(L, err);
×
983
  } else
984
    return luaL_error(L, "table expected");
×
985

986
  return 0;
×
987
}
988

989
static int
990
openssl_mem_search(const unsigned char *mem, int memsize, const unsigned char *part, int partsize)
×
991
{
992
  int mempos, partpos;
993
  for (mempos = 0; mempos <= memsize - partsize; mempos++) {
×
994
    for (partpos = 0; partpos < partsize; partpos++)
×
995
      if (mem[mempos + partpos] != part[partpos]) break;
×
996
    if (partpos == partsize) return mempos;
×
997
  }
998
  return -1;
×
999
}
1000

1001
static int
1002
openssl_alpn_select_cb(SSL                  *ssl,
×
1003
                       const unsigned char **out,
1004
                       unsigned char        *outlen,
1005
                       const unsigned char  *in,
1006
                       unsigned int          inlen,
1007
                       void                 *arg)
1008
{
1009
  lua_State *L = (lua_State *)arg;
×
1010
  int        result = SSL_TLSEXT_ERR_ALERT_FATAL;
×
1011
  SSL_CTX   *ctx = SSL_get_SSL_CTX(ssl);
×
1012

1013
  if (L) {
×
1014
    openssl_valueget(L, ctx, "alpn_select_cb");
×
1015
    if (lua_isfunction(L, -1)) {
×
1016
      int index = 1;
×
1017
      int pos = 0;
×
1018
      // the function is on the stack, adding the table of protocols to be selected
1019
      lua_newtable(L);
×
1020
      while (pos < inlen) {
×
1021
        int len = in[pos++];
×
1022
        lua_pushlstring(L, (const char *)in + pos, len);
×
1023
        lua_rawseti(L, -2, index++);
×
1024
        pos += len;
×
1025
      }
1026
      if (lua_pcall(L, 1, 1, 0) == 0) {
×
1027
        size_t      sellen;
1028
        const char *selected = lua_tolstring(L, -1, &sellen);
×
1029
        if (selected) {
×
1030
          pos = openssl_mem_search(in, inlen, (const unsigned char *)selected, sellen);
×
1031
          if (pos != -1) {
×
1032
            *out = in + pos;
×
1033
            *outlen = sellen;
×
1034
            result = SSL_TLSEXT_ERR_OK;
×
1035
          }
1036
        }
1037
      } else {
1038
        fprintf(stderr, "alpn select callback error: %s\n", lua_tostring(L, -1));
×
1039
      }
1040
      lua_pop(L, 1);
×
1041
    }
1042
  }
1043
  return result;
×
1044
}
1045

1046
/***
1047
set ALPN server protocol selection callback to select which protocol to use for the incoming
1048
connection
1049
@function set_alpn_select_cb
1050
@tparam[opt] function alpn_select_cb callback that receive the prototype list as a table and return
1051
the one selected as a string
1052
*/
1053
static int
1054
openssl_ssl_ctx_set_alpn_select_cb(lua_State *L)
×
1055
{
1056
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
×
1057

1058
  if (lua_isfunction(L, 2)) {
×
1059
    lua_pushvalue(L, 2);
×
1060
    openssl_valueset(L, ctx, "alpn_select_cb");
×
1061
    SSL_CTX_set_alpn_select_cb(ctx, openssl_alpn_select_cb, openssl_mainthread(L));
×
1062
  } else
1063
    SSL_CTX_set_alpn_select_cb(ctx, NULL, NULL);
×
1064

1065
  return 0;
×
1066
}
1067
#endif
1068

1069
#if OPENSSL_VERSION_NUMBER < 0x10100000L
1070
static DH *
1071
tmp_dh_callback(SSL *ssl, int is_export, int keylength)
×
1072
{
1073
  DH        *dh_tmp = NULL;
×
1074
  SSL_CTX   *ctx = SSL_get_SSL_CTX(ssl);
×
1075
  lua_State *L = SSL_CTX_get_app_data(ctx);
×
1076

1077
  int type = openssl_valuegeti(L, ctx, SSL_CTX_TEMP_DH);
×
1078
  if (type == LUA_TFUNCTION) {
×
1079
    int ret;
1080
    /* top is callback function */
1081
    /* Invoke the callback */
1082
    lua_pushboolean(L, is_export);
×
1083
    lua_pushnumber(L, keylength);
×
1084
    ret = lua_pcall(L, 2, 1, 0);
×
1085
    if (ret == 0) {
×
1086
      BIO *bio;
1087
      /* Load parameters from returned value */
1088
      if (lua_type(L, -1) != LUA_TSTRING) {
×
1089
        lua_pop(L, 2); /* Remove values from stack */
×
1090
        return NULL;
×
1091
      }
1092
      bio = BIO_new_mem_buf((void *)lua_tostring(L, -1), lua_rawlen(L, -1));
×
1093
      if (bio) {
×
1094
        dh_tmp = PEM_read_bio_DHparams(bio, NULL, NULL, NULL);
×
1095
        BIO_free(bio);
×
1096
      }
1097
    } else {
1098
      lua_error(L);
×
1099
    }
1100

1101
    lua_pop(L, 2); /* Remove values from stack */
×
1102
    return dh_tmp;
×
1103
  }
1104
  lua_pop(L, 1);
×
1105
  return NULL;
×
1106
}
1107

1108
static RSA *
1109
tmp_rsa_callback(SSL *ssl, int is_export, int keylength)
×
1110
{
1111
  RSA       *rsa_tmp = NULL;
×
1112
  SSL_CTX   *ctx = SSL_get_SSL_CTX(ssl);
×
1113
  lua_State *L = SSL_CTX_get_app_data(ctx);
×
1114
  int        type = openssl_valuegeti(L, ctx, SSL_CTX_TEMP_RSA);
×
1115
  if (type == LUA_TFUNCTION) {
×
1116
    int ret;
1117
    /* top is callback function */
1118
    /* Invoke the callback */
1119
    lua_pushboolean(L, is_export);
×
1120
    lua_pushnumber(L, keylength);
×
1121
    ret = lua_pcall(L, 2, 1, 0);
×
1122
    if (ret == 0) {
×
1123
      BIO *bio;
1124
      /* Load parameters from returned value */
1125
      if (lua_type(L, -1) != LUA_TSTRING) {
×
1126
        lua_pop(L, 2); /* Remove values from stack */
×
1127
        return NULL;
×
1128
      }
1129
      bio = BIO_new_mem_buf((void *)lua_tostring(L, -1), lua_rawlen(L, -1));
×
1130
      if (bio) {
×
1131
        rsa_tmp = PEM_read_bio_RSAPrivateKey(bio, NULL, NULL, NULL);
×
1132
        BIO_free(bio);
×
1133
      }
1134
    } else {
1135
      lua_error(L);
×
1136
    }
1137

1138
    lua_pop(L, 2); /* Remove values from stack */
×
1139
    return rsa_tmp;
×
1140
  }
1141
  lua_pop(L, 1);
×
1142
  return NULL;
×
1143
}
1144

1145
static EC_KEY *
1146
tmp_ecdh_callback(SSL *ssl, int is_export, int keylength)
×
1147
{
1148
  EC_KEY    *ec_tmp = NULL;
×
1149
  SSL_CTX   *ctx = SSL_get_SSL_CTX(ssl);
×
1150
  lua_State *L = SSL_CTX_get_app_data(ctx);
×
1151
  int        type = openssl_valuegeti(L, ctx, SSL_CTX_TEMP_ECDH);
×
1152
  if (type == LUA_TFUNCTION) {
×
1153
    int ret;
1154
    /* top is callback function */
1155
    /* Invoke the callback */
1156
    lua_pushboolean(L, is_export);
×
1157
    lua_pushnumber(L, keylength);
×
1158
    ret = lua_pcall(L, 2, 1, 0);
×
1159
    if (ret == 0) {
×
1160
      BIO *bio;
1161
      /* Load parameters from returned value */
1162
      if (lua_type(L, -1) != LUA_TSTRING) {
×
1163
        lua_pop(L, 2); /* Remove values from stack */
×
1164
        return NULL;
×
1165
      }
1166
      bio = BIO_new_mem_buf((void *)lua_tostring(L, -1), lua_rawlen(L, -1));
×
1167
      if (bio) {
×
1168
        ec_tmp = PEM_read_bio_ECPrivateKey(bio, NULL, NULL, NULL);
×
1169
        BIO_free(bio);
×
1170
      }
1171
    } else {
1172
      lua_error(L);
×
1173
    }
1174

1175
    lua_pop(L, 2); /* Remove values from stack */
×
1176
    return ec_tmp;
×
1177
  }
1178
  lua_pop(L, 1);
×
1179
  return NULL;
×
1180
}
1181

1182
/***
1183
set temp callback
1184
@function set_tmp
1185
@tparam string keytype, 'dh','ecdh',or 'rsa'
1186
@tparam function tmp_cb
1187
@param[opt] vararg
1188
*/
1189
/***
1190
set tmp key content pem format
1191
@function set_tmp
1192
@tparam string keytype, 'dh','ecdh',or 'rsa'
1193
@tparam[opt] string private key file
1194
*/
1195

1196
static int
1197
openssl_ssl_ctx_set_tmp(lua_State *L)
×
1198
{
1199
  SSL_CTX           *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
×
1200
  static const char *which[] = { "dh", "rsa", "ecdh", NULL };
1201

1202
  int nwhich = luaL_checkoption(L, 2, "rsa", which);
×
1203

1204
  if (lua_isfunction(L, 3)) {
×
1205
    lua_pushvalue(L, 3);
×
1206
    /* set callback function */
1207
    switch (nwhich) {
×
1208
    case 0:
×
1209
      openssl_valueseti(L, ctx, SSL_CTX_TEMP_DH);
×
1210
      SSL_CTX_set_tmp_dh_callback(ctx, tmp_dh_callback);
×
1211
      break;
×
1212
    case 1:
×
1213
      openssl_valueseti(L, ctx, SSL_CTX_TEMP_RSA);
×
1214
      SSL_CTX_set_tmp_rsa_callback(ctx, tmp_rsa_callback);
×
1215
      break;
×
1216
    case 2:
×
1217
      openssl_valueseti(L, ctx, SSL_CTX_TEMP_ECDH);
×
1218
      SSL_CTX_set_tmp_ecdh_callback(ctx, tmp_ecdh_callback);
×
1219
      break;
×
1220
    }
1221
    lua_pushboolean(L, 1);
×
1222
    return 1;
×
1223
  } else if (lua_isuserdata(L, 3)) {
×
1224
    luaL_argerror(L, 3, "userdata arg NYI");
×
1225
  } else {
1226
    int  ret;
1227
    BIO *bio = lua_isstring(L, 3) ? load_bio_object(L, 3) : NULL;
×
1228
    switch (nwhich) {
×
1229
    case 0: {
×
1230
      DH *dh = NULL;
×
1231
      if (bio) {
×
1232
        dh = PEM_read_bio_DHparams(bio, NULL, NULL, NULL);
×
1233
        BIO_free(bio);
×
1234
      } else {
1235
        int bits = 1024;
×
1236
        int generator = 2;
×
1237
        dh = DH_new();
×
1238
        ret = DH_generate_parameters_ex(dh, bits, generator, NULL);
×
1239
        if (ret == 1) {
×
1240
          ret = DH_generate_key(dh);
×
1241
        }
1242
        if (ret != 1) {
×
1243
          DH_free(dh);
×
1244
          dh = NULL;
×
1245
        }
1246
      }
1247
      if (dh) {
×
1248
        ret = SSL_CTX_set_tmp_dh(ctx, dh);
×
1249
        if (ret)
×
1250
          PUSH_OBJECT(dh, "openssl.dh");
×
1251
        else {
1252
          DH_free(dh);
×
1253
          lua_pushnil(L);
×
1254
        }
1255
        return 1;
×
1256
      } else
1257
        luaL_error(L, "load or generate new tmp dh fail");
×
1258
    } break;
×
1259
    case 1: {
×
1260
      RSA *rsa = NULL;
×
1261
      if (bio) {
×
1262
        rsa = PEM_read_bio_RSAPrivateKey(bio, NULL, NULL, NULL);
×
1263
        BIO_free(bio);
×
1264
      } else {
1265
        BIGNUM *e = BN_new();
×
1266
        rsa = RSA_new();
×
1267
        BN_set_word(e, RSA_F4);
×
1268
        ret = RSA_generate_key_ex(rsa, 2048, e, NULL);
×
1269
        BN_free(e);
×
1270
        if (ret != 0) {
×
1271
          RSA_free(rsa);
×
1272
          rsa = NULL;
×
1273
        }
1274
      }
1275

1276
      if (rsa) {
×
1277
        ret = SSL_CTX_set_tmp_rsa(ctx, rsa);
×
1278
        if (ret) {
×
1279
          PUSH_OBJECT(rsa, "openssl.rsa");
×
1280
        } else {
1281
          RSA_free(rsa);
×
1282
          lua_pushnil(L);
×
1283
        }
1284
        return 1;
×
1285
      } else
1286
        luaL_error(L, "load or generate new tmp rsa fail");
×
1287
    } break;
×
1288
    case 2: {
×
1289
      int       nid = NID_undef;
×
1290
      EC_GROUP *g = NULL;
×
1291
      EC_KEY   *ec = NULL;
×
1292

1293
      if (lua_isstring(L, 3)) {
×
1294
        nid = OBJ_txt2nid(lua_tostring(L, 3));
×
1295
        if (nid != NID_undef) {
×
1296
          BIO_free(bio);
×
1297
          bio = NULL;
×
1298
        }
1299
      } else {
1300
        nid = OBJ_txt2nid("prime256v1");
×
1301
      }
1302
      if (nid != NID_undef) g = EC_GROUP_new_by_curve_name(nid);
×
1303

1304
      if (bio) {
×
1305
        ec = PEM_read_bio_ECPrivateKey(bio, NULL, NULL, NULL);
×
1306
        BIO_free(bio);
×
1307
      } else if (g) {
×
1308
        ec = EC_KEY_new();
×
1309
        EC_KEY_set_group(ec, g);
×
1310
        EC_GROUP_free(g);
×
1311
        ret = EC_KEY_generate_key(ec);
×
1312
        if (ret != 1) {
×
1313
          EC_KEY_free(ec);
×
1314
          ec = NULL;
×
1315
        }
1316
      }
1317

1318
      if (ec) {
×
1319
        ret = SSL_CTX_set_tmp_ecdh(ctx, ec);
×
1320
        if (ret) {
×
1321
          PUSH_OBJECT(ec, "openssl.ec_key");
×
1322
        } else {
1323
          EC_KEY_free(ec);
×
1324
          lua_pushnil(L);
×
1325
        }
1326
        return 1;
×
1327
      } else
1328
        luaL_error(L, "load or generate new tmp ec_key fail");
×
1329
    } break;
×
1330
    }
1331
  }
1332

1333
  return openssl_pushresult(L, 0);
×
1334
}
1335
#endif
1336

1337
static int
1338
tlsext_servername_callback(SSL *ssl, int *ad, void *arg)
6✔
1339
{
1340
  SSL_CTX    *newctx = NULL;
6✔
1341
  SSL_CTX    *ctx = arg;
6✔
1342
  lua_State  *L = SSL_CTX_get_app_data(ctx);
6✔
1343
  const char *name = SSL_get_servername(ssl, TLSEXT_NAMETYPE_host_name);
6✔
1344
  (void)ad;
1345

1346
  /* No name, use default context */
1347
  if (!name) return SSL_TLSEXT_ERR_NOACK;
6✔
1348

1349
  /* Search for the name in the map */
1350
  openssl_valueget(L, ctx, "tlsext_servername");
4✔
1351
  if (lua_istable(L, -1)) {
4✔
1352
    lua_getfield(L, -1, name);
4✔
1353
    newctx = GET_OBJECT(-1, SSL_CTX, "openssl.ssl_ctx");
4✔
1354
    lua_pop(L, 2);
4✔
1355
  } else {
1356
    lua_pushstring(L, name);
×
1357
    if (lua_pcall(L, 1, 1, 0) == 0) {
×
1358
      newctx = GET_OBJECT(-1, SSL_CTX, "openssl.ssl_ctx");
×
1359
    } else
1360
      return lua_error(L);
×
1361
  }
1362
  if (newctx) {
4✔
1363
    SSL_set_SSL_CTX(ssl, newctx);
4✔
1364
    return SSL_TLSEXT_ERR_OK;
4✔
1365
  }
1366

1367
  return SSL_TLSEXT_ERR_ALERT_FATAL;
×
1368
}
1369

1370
/***
1371
set servername callback
1372
@function set_servername_callback
1373
@tparam table|function info `function(name) return ctx end` or table
1374
@treturn ssl_ctx|fail
1375
*/
1376
static int
1377
openssl_ssl_ctx_set_servername_callback(lua_State *L)
2✔
1378
{
1379
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
2✔
1380
  luaL_argcheck(L, lua_istable(L, 2) || lua_isfunction(L, 2), 2, "must be table or function");
2✔
1381

1382
  lua_pushvalue(L, 2);
2✔
1383
  openssl_valueset(L, ctx, "tlsext_servername");
2✔
1384
  SSL_CTX_set_tlsext_servername_callback(ctx, tlsext_servername_callback);
2✔
1385
  SSL_CTX_set_tlsext_servername_arg(ctx, ctx);
2✔
1386

1387
  return 0;
2✔
1388
}
1389

1390
/***
1391
set session callback
1392
@function set_session_callback
1393
@tparam function new
1394
@tparam function get
1395
@tparam function remove
1396
*/
1397

1398
static int
1399
openssl_add_session(SSL *ssl, SSL_SESSION *session)
8✔
1400
{
1401
  int        ret;
1402
  SSL_CTX   *ctx = SSL_get_SSL_CTX(ssl);
8✔
1403
  lua_State *L = SSL_CTX_get_app_data(ctx);
8✔
1404

1405
  openssl_valuegeti(L, ctx, SSL_CTX_SESSION_ADD);
8✔
1406
  SSL_up_ref(ssl);
8✔
1407
  PUSH_OBJECT(ssl, "openssl.ssl");
8✔
1408
  openssl_newvalue(L, ssl);
8✔
1409
  PUSH_OBJECT(session, "openssl.ssl_session");
8✔
1410

1411
  ret = lua_pcall(L, 2, 1, 0);
8✔
1412
  if (ret != LUA_OK) {
8✔
1413
    fprintf(stderr, "add session callback error: %s\n", lua_tostring(L, -1));
×
1414
    ret = 0;
×
1415
  } else
1416
    ret = lua_isboolean(L, -1) ? lua_toboolean(L, -1) : lua_tointeger(L, -1);
8✔
1417

1418
  lua_pop(L, 1);
8✔
1419
  return ret;
8✔
1420
}
1421

1422
static SSL_SESSION *
1423
openssl_get_session(SSL *ssl, CONSTIFY_OPENSSL unsigned char *id, int idlen, int *do_copy)
1✔
1424
{
1425
  int          ret;
1426
  SSL_CTX     *ctx = SSL_get_SSL_CTX(ssl);
1✔
1427
  lua_State   *L = SSL_CTX_get_app_data(ctx);
1✔
1428
  SSL_SESSION *session = NULL;
1✔
1429

1430
  openssl_valuegeti(L, ctx, SSL_CTX_SESSION_GET);
1✔
1431
  SSL_up_ref(ssl);
1✔
1432
  PUSH_OBJECT(ssl, "openssl.ssl");
1✔
1433
  openssl_newvalue(L, ssl);
1✔
1434
  lua_pushlstring(L, (const char *)id, idlen);
1✔
1435

1436
  ret = lua_pcall(L, 2, 1, 0);
1✔
1437
  if (ret != LUA_OK) {
1✔
1438
    fprintf(stderr, "get session callback error: %s\n", lua_tostring(L, -1));
×
1439
    lua_pop(L, 1);
×
1440
    return NULL;
×
1441
  }
1442
  if (lua_isstring(L, -1)) {
1✔
1443
    size_t               size = 0;
×
1444
    const unsigned char *p = (const unsigned char *)lua_tolstring(L, -1, &size);
×
1445
    *do_copy = 0;
×
1446
    session = d2i_SSL_SESSION(NULL, &p, (int)size);
×
1447
  } else if ((session = GET_OBJECT(-1, SSL_SESSION, "openssl.ssl_session")) != NULL) {
1✔
1448
    *do_copy = 1;
1✔
1449
  } else if (lua_type(L, -1) != LUA_TNIL) {
×
1450
    fprintf(stderr,
×
1451
            "get session callback return unaccpet value: (type=%s)%s\n",
1452
            luaL_typename(L, -1),
1453
            lua_tostring(L, -1));
1454
  }
1455
  lua_pop(L, 1);
1✔
1456
  return session;
1✔
1457
}
1458

1459
static void
1460
openssl_del_session(SSL_CTX *ctx, SSL_SESSION *session)
1✔
1461
{
1462
  int          ret;
1463
  unsigned int len = 0;
1✔
1464
  ;
1465
  const unsigned char *id = NULL;
1✔
1466
  lua_State           *L = SSL_CTX_get_app_data(ctx);
1✔
1467

1468
  openssl_valuegeti(L, ctx, SSL_CTX_SESSION_DEL);
1✔
1469

1470
  id = SSL_SESSION_get_id(session, &len);
1✔
1471
  lua_pushlstring(L, (const char *)id, len);
1✔
1472

1473
  ret = lua_pcall(L, 1, 0, 0);
1✔
1474
  if (ret != LUA_OK) {
1✔
1475
    fprintf(stderr, "del session callback error: %s\n", lua_tostring(L, -1));
×
1476
    lua_pop(L, 1);
×
1477
  }
1478
}
1✔
1479

1480
static int
1481
openssl_ssl_ctx_set_session_callback(lua_State *L)
7✔
1482
{
1483
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
7✔
1484
  if (!lua_isnoneornil(L, 2)) {
7✔
1485
    luaL_checktype(L, 2, LUA_TFUNCTION);
7✔
1486
    lua_pushvalue(L, 2);
7✔
1487
    openssl_valueseti(L, ctx, SSL_CTX_SESSION_ADD);
7✔
1488
    SSL_CTX_sess_set_new_cb(ctx, openssl_add_session);
7✔
1489
  }
1490
  if (!lua_isnoneornil(L, 3)) {
7✔
1491
    luaL_checktype(L, 3, LUA_TFUNCTION);
7✔
1492
    lua_pushvalue(L, 3);
7✔
1493
    openssl_valueseti(L, ctx, SSL_CTX_SESSION_GET);
7✔
1494
    SSL_CTX_sess_set_get_cb(ctx, openssl_get_session);
7✔
1495
  }
1496
  if (!lua_isnoneornil(L, 4)) {
7✔
1497
    luaL_checktype(L, 4, LUA_TFUNCTION);
7✔
1498
    lua_pushvalue(L, 4);
7✔
1499
    openssl_valueseti(L, ctx, SSL_CTX_SESSION_DEL);
7✔
1500
    SSL_CTX_sess_set_remove_cb(ctx, openssl_del_session);
7✔
1501
  }
1502
  lua_pushvalue(L, 1);
7✔
1503
  return 1;
7✔
1504
}
1505

1506
/***
1507
flush sessions
1508
@function flush
1509
*/
1510
static int
1511
openssl_ssl_ctx_flush_sessions(lua_State *L)
1✔
1512
{
1513
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
1✔
1514
  long     tm = luaL_checkinteger(L, 2);
1✔
1515
  SSL_CTX_flush_sessions(ctx, tm);
1✔
1516
  return 0;
1✔
1517
}
1518

1519
/***
1520
set ssl session
1521
@function sessions
1522
*/
1523
static int
1524
openssl_ssl_ctx_sessions(lua_State *L)
3✔
1525
{
1526
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
3✔
1527
  if (lua_isstring(L, 2)) {
3✔
1528
    size_t         s;
1529
    unsigned char *sid_ctx = (unsigned char *)luaL_checklstring(L, 2, &s);
1✔
1530
    int            ret = SSL_CTX_set_session_id_context(ctx, sid_ctx, s);
1✔
1531
    return openssl_pushresult(L, ret);
1✔
1532
  } else {
1533
    SSL_SESSION *s = CHECK_OBJECT(2, SSL_SESSION, "openssl.ssl_session");
2✔
1534
    int          add = lua_isnone(L, 3) ? 1 : auxiliar_checkboolean(L, 3);
2✔
1535

1536
    if (add)
2✔
1537
      add = SSL_CTX_add_session(ctx, s);
1✔
1538
    else
1539
      add = SSL_CTX_remove_session(ctx, s);
1✔
1540
    return openssl_pushresult(L, add);
2✔
1541
  }
1542
}
1543

1544
/***
1545
get current session cache mode
1546
@function session_cache_mode
1547
@treturn table modes as array, mode is 'no_auto_clear','server','client','both','off'
1548
*/
1549

1550
/***
1551
set session cache mode,and return old mode
1552
@function session_cache_mode
1553
@tparam string mode support 'no_auto_clear','server','client','both','off',
1554
'no_auto_clear' can be combine with others, so accept one or two param.
1555
*/
1556
static int
1557
openssl_session_cache_mode(lua_State *L)
19✔
1558
{
1559
  static const char *smode[] = { "off",
1560
                                 "client",
1561
                                 "server",
1562
                                 "both",
1563
                                 "no_auto_clear",
1564
                                 "no_internal_lookup",
1565
                                 "no_internal_store",
1566
                                 "no_internal",
1567
                                 NULL };
1568
  static const int   imode[] = { SSL_SESS_CACHE_OFF,
1569
                                 SSL_SESS_CACHE_CLIENT,
1570
                                 SSL_SESS_CACHE_SERVER,
1571
                                 SSL_SESS_CACHE_BOTH,
1572
                                 SSL_SESS_CACHE_NO_AUTO_CLEAR,
1573
                                 SSL_SESS_CACHE_NO_INTERNAL_LOOKUP,
1574
                                 SSL_SESS_CACHE_NO_INTERNAL_STORE,
1575
                                 SSL_SESS_CACHE_NO_INTERNAL,
1576
                                 -1 };
1577

1578
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
19✔
1579
  int      n = lua_gettop(L);
19✔
1580
  long     mode = 0;
19✔
1581
  int      i;
1582
  if (n > 1) {
19✔
1583
    if (lua_isnumber(L, 2)) {
12✔
1584
      mode = luaL_checkinteger(L, 2);
1✔
1585
      mode = SSL_CTX_set_session_cache_mode(ctx, mode);
1✔
1586
    } else {
1587
      for (i = 2; i <= n; i++) {
36✔
1588
        int j = auxiliar_checkoption(L, i, NULL, smode, imode);
25✔
1589
        mode |= j;
25✔
1590
      }
1591
      mode = SSL_CTX_set_session_cache_mode(ctx, mode);
11✔
1592
    }
1593
  } else {
1594
    mode = SSL_CTX_get_session_cache_mode(ctx);
7✔
1595
  };
1596

1597
  lua_newtable(L);
19✔
1598
  i = 0;
19✔
1599
  if (mode == SSL_SESS_CACHE_OFF) {
19✔
1600
    lua_pushstring(L, "off");
2✔
1601
    lua_rawseti(L, -2, ++i);
2✔
1602
  } else {
1603
    if (mode & SSL_SESS_CACHE_NO_AUTO_CLEAR) {
17✔
1604
      lua_pushstring(L, "no_auto_clear");
2✔
1605
      lua_rawseti(L, -2, ++i);
2✔
1606
    }
1607
    if ((mode & SSL_SESS_CACHE_BOTH) == SSL_SESS_CACHE_BOTH) {
17✔
1608
      lua_pushstring(L, "both");
6✔
1609
      lua_rawseti(L, -2, ++i);
6✔
1610
    } else if (mode & SSL_SESS_CACHE_SERVER) {
11✔
1611
      lua_pushstring(L, "server");
9✔
1612
      lua_rawseti(L, -2, ++i);
9✔
1613
    } else if (mode & SSL_SESS_CACHE_CLIENT) {
2✔
1614
      lua_pushstring(L, "client");
2✔
1615
      lua_rawseti(L, -2, ++i);
2✔
1616
    }
1617
    if ((mode & SSL_SESS_CACHE_NO_INTERNAL) == SSL_SESS_CACHE_NO_INTERNAL) {
17✔
1618
      lua_pushstring(L, "no_internal");
6✔
1619
      lua_rawseti(L, -2, ++i);
6✔
1620
    } else if (mode & SSL_SESS_CACHE_NO_INTERNAL_LOOKUP) {
11✔
1621
      lua_pushstring(L, "no_internal_lookup");
2✔
1622
      lua_rawseti(L, -2, ++i);
2✔
1623
    } else if (mode & SSL_SESS_CACHE_NO_INTERNAL_STORE) {
9✔
1624
      lua_pushstring(L, "no_internal_store");
2✔
1625
      lua_rawseti(L, -2, ++i);
2✔
1626
    }
1627
  }
1628

1629
  return 1;
19✔
1630
}
1631

1632
#if OPENSSL_VERSION_NUMBER > 0x1010100FL && !defined(LIBRESSL_VERSION_NUMBER)
1633
static int
1634
openssl_ssl_ctx_num_tickets(lua_State *L)
1635
{
1636
  SSL_CTX *ctx = CHECK_OBJECT(1, SSL_CTX, "openssl.ssl_ctx");
1637
  size_t   num;
1638
  if (!lua_isnone(L, 2)) {
1639
    num = luaL_checkinteger(L, 2);
1640
    SSL_CTX_set_num_tickets(ctx, num);
1641
  } else
1642
    num = SSL_CTX_get_num_tickets(ctx);
1643

1644
  lua_pushinteger(L, num);
1645
  return 1;
1646
}
1647
#endif
1648

1649
#ifdef SSL_CTX_EXT_DEFINE
1650
SSL_CTX_EXT_DEFINE
1651
#endif
1652

1653
static luaL_Reg ssl_ctx_funcs[] = {
1654
  { "ssl",                     openssl_ssl_ctx_new_ssl                 },
1655
  { "bio",                     openssl_ssl_ctx_new_bio                 },
1656
#ifndef SSL_CTX_USE_EXT
1657
  { "use",                     openssl_ssl_ctx_use                     },
1658
#else
1659
  SSL_CTX_USE_EXT
1660
#endif
1661
  { "add",                     openssl_ssl_ctx_add                     },
1662
  { "mode",                    openssl_ssl_ctx_mode                    },
1663
  { "timeout",                 openssl_ssl_ctx_timeout                 },
1664
  { "options",                 openssl_ssl_ctx_options                 },
1665
#if OPENSSL_VERSION_NUMBER > 0x10100000L
1666
  { "version",                 openssl_ssl_ctx_version                 },
1667
#endif
1668
#if OPENSSL_VERSION_NUMBER > 0x1010100FL && !defined(LIBRESSL_VERSION_NUMBER)
1669
  { "num_tickets",             openssl_ssl_ctx_num_tickets             },
1670
#endif
1671
  { "quiet_shutdown",          openssl_ssl_ctx_quiet_shutdown          },
1672
  { "verify_locations",        openssl_ssl_ctx_load_verify_locations   },
1673
  { "cert_store",              openssl_ssl_ctx_cert_store              },
1674
#ifndef OPENSSL_NO_ENGINE
1675
  { "set_engine",              openssl_ssl_ctx_set_engine              },
1676
#endif
1677
  { "verify_mode",             openssl_ssl_ctx_verify_mode             },
1678
  { "set_cert_verify",         openssl_ssl_ctx_set_cert_verify         },
1679
#if OPENSSL_VERSION_NUMBER >= 0x10002000L
1680
  { "set_alpn_protos",         openssl_ssl_ctx_set_alpn_protos         },
1681
  { "set_alpn_select_cb",      openssl_ssl_ctx_set_alpn_select_cb      },
1682
#endif
1683

1684
  { "verify_depth",            openssl_ssl_ctx_verify_depth            },
1685
#if OPENSSL_VERSION_NUMBER < 0x10100000L
1686
  { "set_tmp",                 openssl_ssl_ctx_set_tmp                 },
1687
#endif
1688
  { "flush_sessions",          openssl_ssl_ctx_flush_sessions          },
1689
  { "session",                 openssl_ssl_ctx_sessions                },
1690
  { "session_cache_mode",      openssl_session_cache_mode              },
1691
  { "set_session_callback",    openssl_ssl_ctx_set_session_callback    },
1692
  { "set_servername_callback", openssl_ssl_ctx_set_servername_callback },
1693

1694
  { "__gc",                    openssl_ssl_ctx_gc                      },
1695
  { "__tostring",              auxiliar_tostring                       },
1696

1697
  { NULL,                      NULL                                    },
1698
};
1699

1700
/****************************SSL SESSION********************************/
1701
/***
1702
get peer certificate verify result
1703
@function getpeerverification
1704
@treturn boolean true for success
1705
@treturn table all certificate in chains verify result
1706
 preverify_ok as boolean verify result
1707
 error as number error code
1708
 error_string as string error message
1709
 error_depth as number verify depth
1710
 current_cert as x509 certificate to verified
1711
*/
1712
static int
1713
openssl_ssl_getpeerverification(lua_State *L)
1✔
1714
{
1715
  long err;
1716
  SSL *ssl = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
1717

1718
  err = SSL_get_verify_result(ssl);
1✔
1719
  lua_pushboolean(L, err == X509_V_OK);
1✔
1720
  openssl_valueget(L, ssl, "verify_cert");
1✔
1721
  return 2;
1✔
1722
}
1723

1724
static int
1725
openssl_ssl_session_time(lua_State *L)
2✔
1726
{
1727
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
2✔
1728
  int          time;
1729
  if (!lua_isnone(L, 2)) {
2✔
1730
    time = luaL_checklong(L, 2);
1✔
1731
    time = SSL_SESSION_set_time(session, time);
1✔
1732
    lua_pushinteger(L, time);
1✔
1733
    return 1;
1✔
1734
  }
1735
  time = SSL_SESSION_get_time(session);
1✔
1736
  lua_pushinteger(L, time);
1✔
1737
  return 1;
1✔
1738
}
1739

1740
static int
1741
openssl_ssl_session_timeout(lua_State *L)
2✔
1742
{
1743
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
2✔
1744
  int          time;
1745
  if (!lua_isnone(L, 2)) {
2✔
1746
    time = luaL_checkint(L, 2);
1✔
1747
    time = SSL_SESSION_set_timeout(session, time);
1✔
1748
    lua_pushinteger(L, time);
1✔
1749
    return 1;
1✔
1750
  }
1751
  time = SSL_SESSION_get_timeout(session);
1✔
1752
  lua_pushinteger(L, time);
1✔
1753
  return 1;
1✔
1754
}
1755

1756
static int
1757
openssl_ssl_session_gc(lua_State *L)
12✔
1758
{
1759
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
12✔
1760
  SSL_SESSION_free(session);
12✔
1761
  return 0;
12✔
1762
}
1763

1764
static int
1765
openssl_ssl_session_peer(lua_State *L)
1✔
1766
{
1767
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
1✔
1768
  X509        *x = SSL_SESSION_get0_peer(session);
1✔
1769
  X509_up_ref(x);
1✔
1770
  PUSH_OBJECT(x, "openssl.x509");
1✔
1771
  return 1;
1✔
1772
}
1773

1774
static int
1775
openssl_ssl_session_id(lua_State *L)
13✔
1776
{
1777
  CONSTIFY_OPENSSL
1778
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
13✔
1779

1780
  if (lua_isnone(L, 2)) {
13✔
1781
    unsigned int         len;
1782
    const unsigned char *id = SSL_SESSION_get_id(session, &len);
11✔
1783
    lua_pushlstring(L, (const char *)id, len);
11✔
1784
    return 1;
11✔
1785
  } else {
1786
#if OPENSSL_VERSION_NUMBER > 0x10100000L
1787
    size_t      len;
1788
    const char *id = luaL_checklstring(L, 2, &len);
1789
    int         ret = SSL_SESSION_set1_id((SSL_SESSION *)session, (const unsigned char *)id, len);
1790
    lua_pushboolean(L, ret);
1791
#else
1792
    lua_pushnil(L);
2✔
1793
#endif
1794
    return 1;
2✔
1795
  }
1796
}
1797

1798
static int
1799
openssl_ssl_session_compress_id(lua_State *L)
1✔
1800
{
1801
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
1✔
1802
  unsigned int id = SSL_SESSION_get_compress_id(session);
1✔
1803
  lua_pushinteger(L, id);
1✔
1804
  return 1;
1✔
1805
}
1806

1807
static int
1808
openssl_ssl_session_export(lua_State *L)
1✔
1809
{
1810
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
1✔
1811
  int          pem = lua_isnone(L, 2) ? 1 : auxiliar_checkboolean(L, 2);
1✔
1812
  BIO         *bio = BIO_new(BIO_s_mem());
1✔
1813
  BUF_MEM     *bio_buf;
1814
  if (pem) {
1✔
1815
    PEM_write_bio_SSL_SESSION(bio, session);
1✔
1816
  } else {
1817
    i2d_SSL_SESSION_bio(bio, session);
×
1818
  }
1819

1820
  BIO_get_mem_ptr(bio, &bio_buf);
1✔
1821
  lua_pushlstring(L, bio_buf->data, bio_buf->length);
1✔
1822
  BIO_free(bio);
1✔
1823
  return 1;
1✔
1824
}
1825

1826
#if OPENSSL_VERSION_NUMBER > 0x10101000L && !defined(LIBRESSL_VERSION_NUMBER)
1827
static int
1828
openssl_ssl_session_is_resumable(lua_State *L)
1829
{
1830
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
1831
  int          ret = SSL_SESSION_is_resumable(session);
1832
  lua_pushboolean(L, ret);
1833
  return 1;
1834
}
1835
#endif
1836

1837
#if OPENSSL_VERSION_NUMBER > 0x10100000L
1838
static int
1839
openssl_ssl_session_has_ticket(lua_State *L)
1840
{
1841
  SSL_SESSION *session = CHECK_OBJECT(1, SSL_SESSION, "openssl.ssl_session");
1842
  int          ret = SSL_SESSION_has_ticket(session);
1843
  lua_pushboolean(L, ret);
1844
  return 1;
1845
}
1846
#endif
1847

1848
static luaL_Reg ssl_session_funcs[] = {
1849
  { "id",           openssl_ssl_session_id           },
1850
  { "time",         openssl_ssl_session_time         },
1851
  { "timeout",      openssl_ssl_session_timeout      },
1852
  { "compress_id",  openssl_ssl_session_compress_id  },
1853
  { "peer",         openssl_ssl_session_peer         },
1854
  { "export",       openssl_ssl_session_export       },
1855
#if OPENSSL_VERSION_NUMBER > 0x10101000L && !defined(LIBRESSL_VERSION_NUMBER)
1856
  { "is_resumable", openssl_ssl_session_is_resumable },
1857
#endif
1858
#if OPENSSL_VERSION_NUMBER > 0x10100000L
1859
  { "has_ticket",   openssl_ssl_session_has_ticket   },
1860
#endif
1861

1862
  { "__gc",         openssl_ssl_session_gc           },
1863
  { "__tostring",   auxiliar_tostring                },
1864

1865
  { NULL,           NULL                             },
1866
};
1867

1868
/***************************SSL**********************************/
1869
/***
1870
openssl.ssl object
1871
All SSL object IO operation methods(connect, accept, handshake, read,
1872
peek or write) return nil or false when fail or error.
1873
When nil returned, it followed by 'ssl' or 'syscall', means SSL layer or
1874
system layer error. When false returned, it followed by number 0,
1875
'want_read','want_write','want_x509_lookup','want_connect','want_accept'.
1876
Numnber 0 means SSL connection closed, others means you should do some
1877
SSL operation.
1878
@type ssl
1879
*/
1880

1881
/***
1882
reset ssl object to allow another connection
1883
@function clear
1884
@treturn boolean result true for success
1885
*/
1886
static int
1887
openssl_ssl_clear(lua_State *L)
2✔
1888
{
1889
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
2✔
1890
  lua_pushboolean(L, SSL_clear(s));
2✔
1891
  return 1;
2✔
1892
}
1893

1894
/***
1895
tell ssl use private key and certificate, and check private key
1896
@function use
1897
@tparam evp_pkey pkey
1898
@tparam[opt] x509 cert
1899
@treturn boolean result return true for ok, or nil followed by errmsg and errval
1900
*/
1901
static int
1902
openssl_ssl_use(lua_State *L)
2✔
1903
{
1904
  SSL      *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
2✔
1905
  X509     *x = CHECK_OBJECT(2, X509, "openssl.x509");
2✔
1906
  EVP_PKEY *pkey = CHECK_OBJECT(3, EVP_PKEY, "openssl.evp_pkey");
2✔
1907
  int       ret;
1908

1909
  ret = SSL_use_PrivateKey(s, pkey);
2✔
1910
  if (ret == 1) {
2✔
1911
    ret = SSL_use_certificate(s, x);
2✔
1912
    if (ret == 1) {
2✔
1913
      ret = SSL_check_private_key(s);
2✔
1914
    }
1915
  }
1916
  return openssl_pushresult(L, ret);
2✔
1917
}
1918

1919
/***
1920
get peer certificate and certificate chains
1921
@function peer
1922
@treturn[1] x509 certificate
1923
@treturn[1] sk_of_x509 chains of peer
1924
*/
1925
static int
1926
openssl_ssl_peer(lua_State *L)
5✔
1927
{
1928
  SSL  *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
5✔
1929
  X509 *x = SSL_get_peer_certificate(s);
5✔
1930
  STACK_OF(X509) *sk = SSL_get_peer_cert_chain(s);
5✔
1931
  PUSH_OBJECT(x, "openssl.x509");
5✔
1932
  if (sk) {
5✔
1933
    openssl_sk_x509_totable(L, sk);
5✔
1934
    return 2;
5✔
1935
  }
1936
  return 1;
×
1937
}
1938

1939
static int
1940
openssl_ssl_gc(lua_State *L)
21✔
1941
{
1942
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
21✔
1943
  SSL_free(s);
21✔
1944
  openssl_freevalue(L, s);
21✔
1945

1946
  return 0;
21✔
1947
}
1948

1949
/***
1950
get want to do
1951
@function want
1952
@treturn[1] string 'nothing', 'reading', 'writing', 'x509_lookup'
1953
@treturn[1] number state want
1954
*/
1955
static int
1956
openssl_ssl_want(lua_State *L)
5✔
1957
{
1958
  SSL        *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
5✔
1959
  int         st = SSL_want(s);
5✔
1960
  const char *state = NULL;
5✔
1961
  if (st == SSL_NOTHING)
5✔
1962
    state = "nothing";
3✔
1963
  else if (st == SSL_READING)
2✔
1964
    state = "reading";
2✔
1965
  else if (st == SSL_WRITING)
×
1966
    state = "writing";
×
1967
  else if (st == SSL_X509_LOOKUP)
×
1968
    state = "x509_lookup";
×
1969

1970
  lua_pushstring(L, state);
5✔
1971
  lua_pushinteger(L, st);
5✔
1972
  return 2;
5✔
1973
}
1974
#if !defined(OPENSSL_NO_COMP)
1975
/***
1976
get current compression name
1977
@function current_compression
1978
@treturn string
1979
*/
1980
static int
1981
openssl_ssl_current_compression(lua_State *L)
1✔
1982
{
1983
  SSL               *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
1984
  const COMP_METHOD *comp = SSL_get_current_compression(s);
1✔
1985
  if (comp)
1✔
1986
    lua_pushstring(L, SSL_COMP_get_name(comp));
1✔
1987
  else
1988
    lua_pushnil(L);
×
1989
  return 1;
1✔
1990
}
1991
#endif
1992

1993
/***
1994
get current cipher info
1995
@function current_cipher
1996
@treturn table include name,version,id,bits,algbits and description
1997
*/
1998
static int
1999
openssl_ssl_current_cipher(lua_State *L)
×
2000
{
2001
  SSL              *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
×
2002
  const SSL_CIPHER *c = SSL_get_current_cipher(s);
×
2003
  if (c) {
×
2004
    int  bits, algbits;
2005
    char err[LUAL_BUFFERSIZE] = { 0 };
×
2006

2007
    lua_newtable(L);
×
2008

2009
    AUXILIAR_SET(L, -1, "name", SSL_CIPHER_get_name(c), string);
×
2010
    AUXILIAR_SET(L, -1, "version", SSL_CIPHER_get_version(c), string);
×
2011

2012
    AUXILIAR_SET(L, -1, "id", SSL_CIPHER_get_id(c), integer);
×
2013
    bits = SSL_CIPHER_get_bits(c, &algbits);
×
2014
    AUXILIAR_SET(L, -1, "bits", bits, integer);
×
2015
    AUXILIAR_SET(L, -1, "algbits", algbits, integer);
×
2016

2017
    AUXILIAR_SET(
×
2018
      L, -1, "description", SSL_CIPHER_description((SSL_CIPHER *)c, err, sizeof(err)), string);
2019

2020
    return 1;
×
2021
  }
2022
  return 0;
×
2023
}
2024

2025
/***
2026
get number of bytes available inside SSL fro immediate read
2027
@function pending
2028
@treturn number
2029
*/
2030
static int
2031
openssl_ssl_pending(lua_State *L)
1✔
2032
{
2033
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
2034
  lua_pushinteger(L, SSL_pending(s));
1✔
2035
  return 1;
1✔
2036
}
2037

2038
/*********************************************/
2039
static int
2040
openssl_ssl_pushresult(lua_State *L, SSL *ssl, int ret_code)
41✔
2041
{
2042
  int err = SSL_get_error(ssl, ret_code);
41✔
2043
  switch (err) {
41✔
2044
  case SSL_ERROR_NONE:
17✔
2045
    lua_pushboolean(L, 1);
17✔
2046
    lua_pushinteger(L, ret_code);
17✔
2047
    break;
17✔
2048
  case SSL_ERROR_ZERO_RETURN:
×
2049
    lua_pushboolean(L, 0);
×
2050
    lua_pushinteger(L, 0);
×
2051
    break;
×
2052
  case SSL_ERROR_SSL:
3✔
2053
    lua_pushnil(L);
3✔
2054
    lua_pushstring(L, "ssl");
3✔
2055
    break;
3✔
2056
  case SSL_ERROR_WANT_READ:
17✔
2057
    lua_pushboolean(L, 0);
17✔
2058
    lua_pushstring(L, "want_read");
17✔
2059
    break;
17✔
2060
  case SSL_ERROR_WANT_WRITE:
×
2061
    lua_pushboolean(L, 0);
×
2062
    lua_pushstring(L, "want_write");
×
2063
    break;
×
2064
  case SSL_ERROR_WANT_X509_LOOKUP:
×
2065
    lua_pushboolean(L, 0);
×
2066
    lua_pushstring(L, "want_x509_lookup");
×
2067
    break;
×
2068
  case SSL_ERROR_SYSCALL:
4✔
2069
    lua_pushnil(L);
4✔
2070
    lua_pushstring(L, "syscall");
4✔
2071
    break;
4✔
2072
  case SSL_ERROR_WANT_CONNECT:
×
2073
    lua_pushboolean(L, 0);
×
2074
    lua_pushstring(L, "want_connect");
×
2075
    break;
×
2076
  case SSL_ERROR_WANT_ACCEPT:
×
2077
    lua_pushboolean(L, 0);
×
2078
    lua_pushstring(L, "want_accept");
×
2079
    break;
×
2080
  default:
×
2081
    return 0;
×
2082
  }
2083
  return 2;
41✔
2084
}
2085

2086
/***
2087
get socket fd of ssl
2088
@function getfd
2089
@treturn number fd
2090
*/
2091
static int
2092
openssl_ssl_getfd(lua_State *L)
×
2093
{
2094
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
×
2095
  lua_pushinteger(L, SSL_get_fd(s));
×
2096
  return 1;
×
2097
}
2098

2099
/***
2100
check SSL is a server
2101
@function is_server
2102
@treturn boolean is_server
2103
*/
2104
static int
2105
openssl_ssl_is_server(lua_State *L)
×
2106
{
2107
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
×
2108
  lua_pushboolean(L, SSL_is_server(s));
×
2109
  return 1;
×
2110
}
2111

2112
/***
2113
get value according to arg
2114
@function get
2115
@tparam string arg
2116
 <br/>certificate:  return SSL certificates
2117
 <br/>fd: return file or network connect fd
2118
 <br/>rfd:
2119
 <br/>wfd:
2120
 <br/>client_CA_list
2121
 <br/>read_ahead: -> boolean
2122
 <br/>shared_ciphers: string
2123
 <br/>cipher_list -> string
2124
 <br/>verify_mode: number
2125
 <br/>verify_depth
2126
 <br/>state_string
2127
 <br/>state_string_long
2128
 <br/>rstate_string
2129
 <br/>rstate_string_long
2130
 <br/>iversion
2131
 <br/>version
2132
 <br/>default_timeout,
2133
 <br/>certificate
2134
 <br/>verify_result
2135
 <br/>state
2136
 <br/>hostname
2137
 <br/>state_string
2138
 <br/>side
2139
@return according to arg
2140
*/
2141
static int
2142
openssl_ssl_get(lua_State *L)
24✔
2143
{
2144
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
24✔
2145
  int  i;
2146
  int  top = lua_gettop(L);
24✔
2147
  for (i = 2; i <= top; i++) {
48✔
2148
    const char *what = luaL_checklstring(L, i, NULL);
24✔
2149
    if (strcmp(what, "fd") == 0) {
24✔
2150
      lua_pushinteger(L, SSL_get_fd(s));
1✔
2151
    } else if (strcmp(what, "rfd") == 0) {
23✔
2152
      lua_pushinteger(L, SSL_get_rfd(s));
1✔
2153
    } else if (strcmp(what, "wfd") == 0) {
22✔
2154
      lua_pushinteger(L, SSL_get_wfd(s));
1✔
2155
    } else if (strcmp(what, "client_CA_list") == 0) {
21✔
2156
      STACK_OF(X509_NAME) *sn = SSL_get_client_CA_list(s);
1✔
2157
      openssl_sk_x509_name_totable(L, sn);
1✔
2158
    } else if (strcmp(what, "read_ahead") == 0) {
20✔
2159
      lua_pushboolean(L, SSL_get_read_ahead(s));
1✔
2160
    } else if (strcmp(what, "shared_ciphers") == 0) {
19✔
2161
      char buf[LUAL_BUFFERSIZE] = { 0 };
1✔
2162
      lua_pushstring(L, SSL_get_shared_ciphers(s, buf, sizeof(buf)));
1✔
2163
    } else if (strcmp(what, "cipher_list") == 0) {
18✔
2164
      lua_pushstring(L, SSL_get_cipher_list(s, 0));
1✔
2165
    } else if (strcmp(what, "verify_mode") == 0) {
17✔
2166
      lua_pushinteger(L, SSL_get_verify_mode(s));
1✔
2167
    } else if (strcmp(what, "verify_depth") == 0) {
16✔
2168
      lua_pushinteger(L, SSL_get_verify_depth(s));
1✔
2169
    } else if (strcmp(what, "state_string") == 0) {
15✔
2170
      lua_pushstring(L, SSL_state_string(s));
2✔
2171
    } else if (strcmp(what, "state_string_long") == 0) {
13✔
2172
      lua_pushstring(L, SSL_state_string_long(s));
1✔
2173
    } else if (strcmp(what, "rstate_string") == 0) {
12✔
2174
      lua_pushstring(L, SSL_rstate_string(s));
1✔
2175
    } else if (strcmp(what, "rstate_string_long") == 0) {
11✔
2176
      lua_pushstring(L, SSL_rstate_string_long(s));
1✔
2177
    } else if (strcmp(what, "version") == 0) {
10✔
2178
      lua_pushstring(L, SSL_get_version(s));
2✔
2179
    } else if (strcmp(what, "iversion") == 0) {
8✔
2180
      lua_pushinteger(L, SSL_version(s));
1✔
2181
    } else if (strcmp(what, "default_timeout") == 0) {
7✔
2182
      lua_pushinteger(L, SSL_get_default_timeout(s));
1✔
2183
    } else if (strcmp(what, "certificate") == 0) {
6✔
2184
      X509 *cert = SSL_get_certificate(s);
1✔
2185
      if (cert) {
1✔
2186
        X509_up_ref(cert);
1✔
2187
        PUSH_OBJECT(cert, "openssl.x509");
1✔
2188
      } else
2189
        lua_pushnil(L);
×
2190
    } else if (strcmp(what, "verify_result") == 0) {
5✔
2191
      long l = SSL_get_verify_result(s);
1✔
2192
      lua_pushinteger(L, l);
1✔
2193
    } else if (strcmp(what, "state") == 0) {
4✔
2194
      lua_pushinteger(L, SSL_get_state(s));
1✔
2195
    } else if (strcmp(what, "hostname") == 0) {
3✔
2196
      lua_pushstring(L, SSL_get_servername(s, TLSEXT_NAMETYPE_host_name));
2✔
2197
    } else if (strcmp(what, "side") == 0) {
1✔
2198
      lua_pushstring(L, SSL_is_server(s) ? "server" : "client");
1✔
2199
    } else
2200
      luaL_argerror(L, i, "can't understant");
×
2201
  }
2202
  return top - 1;
24✔
2203
}
2204

2205
/***
2206
set value according to arg
2207
@function set
2208
@tparam string arg
2209
 <br/>certificate:  return SSL certificates
2210
 <br/>fd: return file or network connect fd
2211
 <br/>rfd:
2212
 <br/>wfd:
2213
 <br/>client_CA:
2214
 <br/>read_ahead:
2215
 <br/>cipher_list:
2216
 <br/>verify_depth:
2217
 <br/>purpose:
2218
 <br/>trust:
2219
 <br/>verify_result:
2220
 <br/>hostname:
2221
@param value val type accroding to arg
2222
@return value
2223
*/
2224
static int
2225
openssl_ssl_set(lua_State *L)
15✔
2226
{
2227
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
15✔
2228
  int  i;
2229
  int  top = lua_gettop(L);
15✔
2230
  int  ret = 1;
15✔
2231
  for (i = 2; i <= top; i += 2) {
30✔
2232
    const char *what = luaL_checklstring(L, i, NULL);
15✔
2233
    if (strcmp(what, "fd") == 0) {
15✔
2234
      ret = SSL_set_fd(s, luaL_checkint(L, i + 1));
1✔
2235
    } else if (strcmp(what, "rfd") == 0) {
14✔
2236
      ret = SSL_set_wfd(s, luaL_checkint(L, i + 1));
1✔
2237
    } else if (strcmp(what, "wfd") == 0) {
13✔
2238
      ret = SSL_set_wfd(s, luaL_checkint(L, i + 1));
1✔
2239
    } else if (strcmp(what, "client_CA") == 0) {
12✔
2240
      X509 *x = CHECK_OBJECT(i + 1, X509, "openssl.x509");
1✔
2241
      ret = SSL_add_client_CA(s, x);
1✔
2242
    } else if (strcmp(what, "read_ahead") == 0) {
11✔
2243
      int yes = auxiliar_checkboolean(L, i + 1);
1✔
2244
      SSL_set_read_ahead(s, yes);
1✔
2245
    } else if (strcmp(what, "cipher_list") == 0) {
10✔
2246
      const char *list = lua_tostring(L, i + 1);
1✔
2247
      ret = SSL_set_cipher_list(s, list);
1✔
2248
    } else if (strcmp(what, "verify_depth") == 0) {
9✔
2249
      int depth = luaL_checkint(L, i + 1);
1✔
2250
      SSL_set_verify_depth(s, depth);
1✔
2251
    } else if (strcmp(what, "purpose") == 0) {
8✔
2252
      int purpose = luaL_checkint(L, i + 1);
1✔
2253
      ret = SSL_set_purpose(s, purpose);
1✔
2254
    } else if (strcmp(what, "trust") == 0) {
7✔
2255
      int trust = luaL_checkint(L, i + 1);
1✔
2256
      ret = SSL_set_trust(s, trust);
1✔
2257
    } else if (strcmp(what, "verify_result") == 0) {
6✔
2258
      int result = luaL_checkint(L, i + 1);
1✔
2259
      SSL_set_verify_result(s, result);
1✔
2260
    } else if (strcmp(what, "hostname") == 0) {
5✔
2261
      const char *hostname = luaL_checkstring(L, i + 1);
5✔
2262
      SSL_set_tlsext_host_name(s, hostname);
5✔
2263
    } else
2264
      luaL_argerror(L, i, "don't understand");
×
2265

2266
    if (ret != 1) return openssl_pushresult(L, ret);
15✔
2267
  }
2268
  return 0;
15✔
2269
}
2270

2271
/***
2272
do ssl server accept
2273
@function accept
2274
@treturn boolean true for success
2275
@treturn string fail reason
2276
*/
2277
static int
2278
openssl_ssl_accept(lua_State *L)
×
2279
{
2280
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
×
2281
  int  ret = SSL_accept(s);
×
2282
  return openssl_ssl_pushresult(L, s, ret);
×
2283
}
2284

2285
/***
2286
do ssl client connect
2287
@function connect
2288
@treturn boolean true for success
2289
@treturn string fail reasion
2290
*/
2291
static int
2292
openssl_ssl_connect(lua_State *L)
×
2293
{
2294
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
×
2295
  int  ret = SSL_connect(s);
×
2296
  return openssl_ssl_pushresult(L, s, ret);
×
2297
}
2298

2299
/***
2300
do ssl read
2301
@function read
2302
@tparam[opt=4096] number length to read
2303
@treturn string data, nil or false for fail
2304
@treturn string fail reason
2305
*/
2306
static int
2307
openssl_ssl_read(lua_State *L)
8✔
2308
{
2309
  SSL  *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
8✔
2310
  int   num = luaL_optint(L, 2, SSL_pending(s));
8✔
2311
  void *buf;
2312
  int   ret;
2313
  num = num ? num : 4096;
8✔
2314
  buf = malloc(num);
8✔
2315
  ret = SSL_read(s, buf, num);
8✔
2316
  if (ret > 0) {
8✔
2317
    lua_pushlstring(L, buf, ret);
6✔
2318
    ret = 1;
6✔
2319
  } else {
2320
    ret = openssl_ssl_pushresult(L, s, ret);
2✔
2321
  }
2322
  free(buf);
8✔
2323
  return ret;
8✔
2324
}
2325

2326
/***
2327
do ssl peak, data can be read again
2328
@function peek
2329
@tparam[opt=4096] number length to read
2330
@treturn string data, nil or false for fail
2331
@treturn string fail reason
2332
*/
2333
static int
2334
openssl_ssl_peek(lua_State *L)
1✔
2335
{
2336
  SSL  *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
2337
  int   num = luaL_optint(L, 2, SSL_pending(s));
1✔
2338
  void *buf;
2339
  int   ret;
2340

2341
  num = num ? num : 4096;
1✔
2342
  buf = malloc(num);
1✔
2343
  ret = SSL_peek(s, buf, num);
1✔
2344
  if (ret > 0) {
1✔
2345
    lua_pushlstring(L, buf, ret);
1✔
2346
    ret = 1;
1✔
2347
  } else {
2348
    ret = openssl_ssl_pushresult(L, s, ret);
×
2349
  }
2350
  free(buf);
1✔
2351
  return ret;
1✔
2352
}
2353

2354
/***
2355
do ssl write
2356
@function write
2357
@tparam string data
2358
@treturn number count of bytes write successfully
2359
@treturn string fail reason
2360
*/
2361
static int
2362
openssl_ssl_write(lua_State *L)
6✔
2363
{
2364
  SSL        *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
6✔
2365
  size_t      size;
2366
  const char *buf = luaL_checklstring(L, 2, &size);
6✔
2367
  int         ret = SSL_write(s, buf, size);
6✔
2368
  if (ret > 0) {
6✔
2369
    lua_pushinteger(L, ret);
6✔
2370
    return 1;
6✔
2371
  } else {
2372
    return openssl_ssl_pushresult(L, s, ret);
×
2373
  }
2374
}
2375

2376
/***
2377
do ssl handshake, support both server and client side
2378
@function handshake
2379
@treturn boolean true for success
2380
@treturn string fail reasion
2381
*/
2382
static int
2383
openssl_ssl_do_handshake(lua_State *L)
30✔
2384
{
2385
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
30✔
2386
  int  ret = SSL_do_handshake(s);
30✔
2387
  return openssl_ssl_pushresult(L, s, ret);
30✔
2388
}
2389

2390
/***
2391
do ssl renegotiate
2392
@function renegotiate
2393
@treturn boolean true for success
2394
@treturn string fail reasion
2395
*/
2396
static int
2397
openssl_ssl_renegotiate(lua_State *L)
1✔
2398
{
2399
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
2400
  int  ret = SSL_renegotiate(s);
1✔
2401
  return openssl_ssl_pushresult(L, s, ret);
1✔
2402
}
2403

2404
static int
2405
openssl_ssl_renegotiate_abbreviated(lua_State *L)
1✔
2406
{
2407
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
2408
  int  ret = SSL_renegotiate_abbreviated(s);
1✔
2409
  return openssl_ssl_pushresult(L, s, ret);
1✔
2410
}
2411

2412
/***
2413
get ssl renegotiate_pending
2414
@function renegotiate_pending
2415
@treturn boolean true for success
2416
@treturn string fail reasion
2417
*/
2418
/***
2419
do ssl renegotiate_pending
2420
@function renegotiate_pending
2421
@treturn boolean true for success
2422
@treturn string fail reasion
2423
*/
2424
static int
2425
openssl_ssl_renegotiate_pending(lua_State *L)
1✔
2426
{
2427
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
2428
  int  ret = SSL_renegotiate_pending(s);
1✔
2429
  return openssl_ssl_pushresult(L, s, ret);
1✔
2430
}
2431

2432
/***
2433
shutdown ssl connection with quite or noquite mode
2434
@function shutdown
2435
@tparam boolean mode
2436
@treturn boolean if mode is true, return true or false for quite
2437
@treturn string if mode is false, return 'read' or 'write' for shutdown direction
2438
*/
2439
/***
2440
shutdown SSL connection
2441
@function shutdown
2442
*/
2443
/***
2444
shutdown ssl connect with special mode, disable read or write,
2445
enable or disable quite shutdown
2446
@function shutdown
2447
@tparam string mode support 'read','write', 'quite', 'noquite'
2448
*/
2449
static int
2450
openssl_ssl_shutdown(lua_State *L)
12✔
2451
{
2452
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
12✔
2453
  if (lua_isnone(L, 2)) {
12✔
2454
    int ret = SSL_shutdown(s);
6✔
2455
    return openssl_ssl_pushresult(L, s, ret);
6✔
2456
  } else if (lua_isstring(L, 2)) {
6✔
2457
    const static char *sMode[] = { "read", "write", "quiet", "noquiet", NULL };
2458
    int                mode = luaL_checkoption(L, 2, NULL, sMode);
4✔
2459
    if (mode == 0)
4✔
2460
      SSL_set_shutdown(s, SSL_RECEIVED_SHUTDOWN);
1✔
2461
    else if (mode == 1)
3✔
2462
      SSL_set_shutdown(s, SSL_SENT_SHUTDOWN);
1✔
2463
    else if (mode == 2)
2✔
2464
      SSL_set_quiet_shutdown(s, 1);
1✔
2465
    else if (mode == 3)
1✔
2466
      SSL_set_quiet_shutdown(s, 0);
1✔
2467
  } else if (lua_isboolean(L, 2)) {
2✔
2468
    int quiet = lua_toboolean(L, 2);
2✔
2469
    if (quiet)
2✔
2470
      lua_pushboolean(L, SSL_get_quiet_shutdown(s));
1✔
2471
    else {
2472
      int shut = SSL_get_shutdown(s);
1✔
2473
      if (shut == SSL_RECEIVED_SHUTDOWN)
1✔
2474
        lua_pushstring(L, "read");
×
2475
      else if (shut == SSL_SENT_SHUTDOWN)
1✔
2476
        lua_pushstring(L, "write");
1✔
2477
      else if (shut == 0)
×
2478
        lua_pushnil(L);
×
2479
      else
2480
        luaL_error(L, "Can't understand SSL_get_shutdown result");
×
2481
    }
2482
    return 1;
2✔
2483
  } else
2484
    luaL_argerror(L, 2, "should be boolean or string[read|write|quiet|noquite]");
×
2485

2486
  return 0;
4✔
2487
};
2488

2489
/***
2490
make ssl to client mode
2491
@function set_connect_state
2492
*/
2493
static int
2494
openssl_ssl_set_connect_state(lua_State *L)
2✔
2495
{
2496
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
2✔
2497
  SSL_set_connect_state(s);
2✔
2498
  return 0;
2✔
2499
}
2500

2501
/***
2502
make ssl to server mode
2503
@function set_accept_state
2504
*/
2505
static int
2506
openssl_ssl_set_accept_state(lua_State *L)
2✔
2507
{
2508
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
2✔
2509
  SSL_set_accept_state(s);
2✔
2510
  return 0;
2✔
2511
}
2512

2513
/***
2514
duplicate ssl object
2515
@treturn ssl
2516
@function dup
2517
*/
2518
static int
2519
openssl_ssl_dup(lua_State *L)
2✔
2520
{
2521
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
2✔
2522
  BIO *rio = SSL_get_rbio(s);
2✔
2523
  BIO *wio = SSL_get_wbio(s);
2✔
2524
  if (rio != NULL || wio != NULL) {
2✔
2525
    lua_pushnil(L);
1✔
2526
    lua_pushliteral(L, "invalid state: rbio or wbio already set");
1✔
2527
    return 2;
1✔
2528
  }
2529

2530
  s = SSL_dup(s);
1✔
2531
  if (s) {
1✔
2532
    PUSH_OBJECT(s, "openssl.ssl");
1✔
2533
    openssl_newvalue(L, s);
1✔
2534
    return 1;
1✔
2535
  }
2536
  return openssl_pushresult(L, 0);
×
2537
}
2538

2539
/***
2540
get ssl session resused
2541
@function session_reused
2542
*/
2543
static int
2544
openssl_ssl_session_reused(lua_State *L)
1✔
2545
{
2546
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
2547
  int  ret = SSL_session_reused(s);
1✔
2548
  lua_pushboolean(L, ret);
1✔
2549
  return 1;
1✔
2550
}
2551

2552
static int
2553
openssl_ssl_cache_hit(lua_State *L)
1✔
2554
{
2555
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
1✔
2556
  int  ret = SSL_session_reused(s);
1✔
2557
  lua_pushboolean(L, ret == 0);
1✔
2558
  return 1;
1✔
2559
}
2560
#if OPENSSL_VERSION_NUMBER < 0x10100000L
2561
static int
2562
openssl_ssl_set_debug(lua_State *L)
×
2563
{
2564
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
×
2565
  int  debug = luaL_checkint(L, 2);
×
2566
  SSL_set_debug(s, debug);
×
2567
  return 0;
×
2568
}
2569
#endif
2570

2571
/***
2572
get ssl_ctx associate with current ssl
2573
@function ctx
2574
@treturn ssl_ctx
2575
*/
2576
/***
2577
set ssl_ctx associate to current ssl
2578
@function ctx
2579
@tparam ssl_ctx ctx
2580
@treturn ssl_ctx orgine ssl_ctx object
2581
*/
2582
static int
2583
openssl_ssl_ctx(lua_State *L)
2✔
2584
{
2585
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
2✔
2586
  if (!lua_isnone(L, 2)) {
2✔
2587
    SSL_CTX *ctx = CHECK_OBJECT(2, SSL_CTX, "openssl.ssl_ctx");
1✔
2588
    ctx = SSL_set_SSL_CTX(s, ctx);
1✔
2589
    lua_pushvalue(L, 2);
1✔
2590
    openssl_valueset(L, s, "ctx");
1✔
2591
  }
2592
  openssl_valueget(L, s, "ctx");
2✔
2593
  return 1;
2✔
2594
}
2595

2596
/***
2597
get ssl session
2598
@treturn ssl_session session object
2599
@function session
2600
*/
2601
/***
2602
set ssl session
2603
@function session
2604
@tparam string|ssl_session sesion
2605
 reuse session would speed up ssl handshake
2606
@treturn boolean result
2607
*/
2608
static int
2609
openssl_ssl_session(lua_State *L)
3✔
2610
{
2611
  SSL         *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
3✔
2612
  SSL_SESSION *ss;
2613

2614
  if (lua_isnone(L, 2)) {
3✔
2615
    ss = SSL_get1_session(s);
2✔
2616
    PUSH_OBJECT(ss, "openssl.ssl_session");
2✔
2617
  } else {
2618
    if (lua_isstring(L, 3)) {
1✔
2619
      size_t      sz;
2620
      const char *sid_ctx = luaL_checklstring(L, 2, &sz);
×
2621
      int         ret = SSL_set_session_id_context(s, (unsigned char *)sid_ctx, sz);
×
2622
      lua_pushboolean(L, ret);
×
2623
    } else {
2624
      ss = CHECK_OBJECT(2, SSL_SESSION, "openssl.ssl_session");
1✔
2625
      if (lua_isnone(L, 3)) {
1✔
2626
        int ret = SSL_set_session(s, ss);
1✔
2627
        lua_pushboolean(L, ret);
1✔
2628
      } else {
2629
#ifdef SSL_add_session
2630
        int add = auxiliar_checkboolean(L, 3);
2631
        if (add)
2632
          add = SSL_add_session(s, ss);
2633
        else
2634
          add = SSL_remove_session(s, ss);
2635
        lua_pushboolean(L, add);
2636
#endif
2637
      }
2638
    }
2639
  }
2640
  return 1;
3✔
2641
}
2642

2643
static int
2644
openssl_ssl_tostring(lua_State *L)
9✔
2645
{
2646
  SSL *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
9✔
2647
  lua_pushfstring(L, "openssl.ssl %p", s);
9✔
2648
  return 1;
9✔
2649
}
2650

2651
#if OPENSSL_VERSION_NUMBER >= 0x10002000L
2652
/***
2653
get the ALPN protocol selected
2654
@treturn the ALPN protocol selected or nil
2655
@function get_alpn_selected
2656
*/
2657
static int
2658
openssl_ssl_get_alpn_selected(lua_State *L)
×
2659
{
2660
  SSL                 *s = CHECK_OBJECT(1, SSL, "openssl.ssl");
×
2661
  const unsigned char *data;
2662
  unsigned             len = 0;
×
2663
  SSL_get0_alpn_selected(s, &data, &len);
×
2664
  if (len == 0)
×
2665
    lua_pushnil(L);
×
2666
  else
2667
    lua_pushlstring(L, (const char *)data, len);
×
2668
  return 1;
×
2669
}
2670
#endif
2671

2672
static luaL_Reg ssl_funcs[] = {
2673
  { "set",                     openssl_ssl_set                     },
2674
  { "get",                     openssl_ssl_get                     },
2675
  { "use",                     openssl_ssl_use                     },
2676
  { "peer",                    openssl_ssl_peer                    },
2677
  { "getfd",                   openssl_ssl_getfd                   },
2678
  { "is_server",               openssl_ssl_is_server               },
2679

2680
  { "current_cipher",          openssl_ssl_current_cipher          },
2681
#if !defined(OPENSSL_NO_COMP)
2682
  { "current_compression",     openssl_ssl_current_compression     },
2683
#endif
2684
  { "getpeerverification",     openssl_ssl_getpeerverification     },
2685

2686
  { "session",                 openssl_ssl_session                 },
2687

2688
  { "dup",                     openssl_ssl_dup                     },
2689
  { "ctx",                     openssl_ssl_ctx                     },
2690
  { "clear",                   openssl_ssl_clear                   },
2691
  { "want",                    openssl_ssl_want                    },
2692
  { "pending",                 openssl_ssl_pending                 },
2693
  { "accept",                  openssl_ssl_accept                  },
2694
  { "connect",                 openssl_ssl_connect                 },
2695
  { "read",                    openssl_ssl_read                    },
2696
  { "peek",                    openssl_ssl_peek                    },
2697
  { "write",                   openssl_ssl_write                   },
2698

2699
  { "renegotiate",             openssl_ssl_renegotiate             },
2700
  { "handshake",               openssl_ssl_do_handshake            },
2701
  { "shutdown",                openssl_ssl_shutdown                },
2702

2703
  { "session_reused",          openssl_ssl_session_reused          },
2704
#if OPENSSL_VERSION_NUMBER < 0x10100000L
2705
  { "set_debug",               openssl_ssl_set_debug               },
2706
#endif
2707
  { "cache_hit",               openssl_ssl_cache_hit               },
2708
  { "renegotiate_abbreviated", openssl_ssl_renegotiate_abbreviated },
2709
  { "renegotiate_pending",     openssl_ssl_renegotiate_pending     },
2710
  { "set_connect_state",       openssl_ssl_set_connect_state       },
2711
  { "set_accept_state",        openssl_ssl_set_accept_state        },
2712
#if OPENSSL_VERSION_NUMBER >= 0x10002000L
2713
  { "get_alpn_selected",       openssl_ssl_get_alpn_selected       },
2714
#endif
2715

2716
  { "__gc",                    openssl_ssl_gc                      },
2717
  { "__tostring",              openssl_ssl_tostring                },
2718

2719
  { NULL,                      NULL                                },
2720
};
2721

2722
int
2723
luaopen_ssl(lua_State *L)
1✔
2724
{
2725
  int i;
2726

2727
  auxiliar_newclass(L, "openssl.ssl_ctx", ssl_ctx_funcs);
1✔
2728
  auxiliar_newclass(L, "openssl.ssl_session", ssl_session_funcs);
1✔
2729
  auxiliar_newclass(L, "openssl.ssl", ssl_funcs);
1✔
2730

2731
  lua_newtable(L);
1✔
2732
  luaL_setfuncs(L, R, 0);
1✔
2733

2734
  auxiliar_enumerate(L, -1, ssl_options);
1✔
2735
  for (i = 0; sVerifyMode_Options[i]; i++) {
5✔
2736
    lua_pushinteger(L, iVerifyMode_Options[i]);
4✔
2737
    lua_setfield(L, -2, sVerifyMode_Options[i]);
4✔
2738
  }
2739
  lua_pushstring(L, DEFAULT_PROTOCOL);
1✔
2740
  lua_setfield(L, -2, "default");
1✔
2741

2742
  lua_pushstring(L, SSL_DEFAULT_CIPHER_LIST);
1✔
2743
  lua_setfield(L, -2, "DEFAULT_CIPHER_LIST");
1✔
2744

2745
  return 1;
1✔
2746
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc