Skip to content

Commit 6ff9ff2

Browse files
catbro666zhuizhuhaomeng
authored andcommitted
feature: implemented the ssl_client_hello_by_lua_block and ssl_client_hello_by_lua_file directives for controlling the NGINX downstream SSL handshake dynamically with Lua.
1 parent ef1188d commit 6ff9ff2

18 files changed

+2656
-18
lines changed

README.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -147,6 +147,8 @@ behavior.
147147
* [balancer_by_lua_file](https://github.com/openresty/lua-nginx-module#balancer_by_lua_file)
148148
* [log_by_lua_block](#log_by_lua_block)
149149
* [log_by_lua_file](#log_by_lua_file)
150+
* [ssl_client_hello_by_lua_block](https://github.com/openresty/lua-nginx-module#ssl_client_hello_by_lua_block)
151+
* [ssl_client_hello_by_lua_file](https://github.com/openresty/lua-nginx-module#ssl_client_hello_by_lua_file)
150152
* [ssl_certificate_by_lua_block](https://github.com/openresty/lua-nginx-module#ssl_certificate_by_lua_block)
151153
* [ssl_certificate_by_lua_file](https://github.com/openresty/lua-nginx-module#ssl_certificate_by_lua_file)
152154
* [lua_shared_dict](https://github.com/openresty/lua-nginx-module#lua_shared_dict)

config

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -276,6 +276,7 @@ STREAM_LUA_SRCS=" \
276276
$ngx_addon_dir/src/ngx_stream_lua_logby.c \
277277
$ngx_addon_dir/src/ngx_stream_lua_prereadby.c \
278278
$ngx_addon_dir/src/ngx_stream_lua_semaphore.c \
279+
$ngx_addon_dir/src/ngx_stream_lua_ssl_client_helloby.c \
279280
$ngx_addon_dir/src/ngx_stream_lua_ssl_certby.c \
280281
$ngx_addon_dir/src/ngx_stream_lua_log_ringbuf.c \
281282
$ngx_addon_dir/src/ngx_stream_lua_input_filters.c \
@@ -319,6 +320,7 @@ STREAM_LUA_DEPS=" \
319320
$ngx_addon_dir/src/ngx_stream_lua_logby.h \
320321
$ngx_addon_dir/src/ngx_stream_lua_prereadby.h \
321322
$ngx_addon_dir/src/ngx_stream_lua_semaphore.h \
323+
$ngx_addon_dir/src/ngx_stream_lua_ssl_client_helloby.h \
322324
$ngx_addon_dir/src/ngx_stream_lua_ssl_certby.h \
323325
$ngx_addon_dir/src/ngx_stream_lua_log_ringbuf.h \
324326
$ngx_addon_dir/src/ngx_stream_lua_input_filters.h \

src/ngx_stream_lua_common.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -131,6 +131,7 @@
131131
#define NGX_STREAM_LUA_CONTEXT_BALANCER 0x0010
132132
#define NGX_STREAM_LUA_CONTEXT_PREREAD 0x0020
133133
#define NGX_STREAM_LUA_CONTEXT_SSL_CERT 0x0040
134+
#define NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO 0x0080
134135

135136

136137
#define NGX_STREAM_LUA_FFI_NO_REQ_CTX -100
@@ -257,6 +258,10 @@ struct ngx_stream_lua_srv_conf_s {
257258
ngx_stream_lua_srv_conf_handler_pt ssl_cert_handler;
258259
ngx_str_t ssl_cert_src;
259260
u_char *ssl_cert_src_key;
261+
262+
ngx_stream_lua_srv_conf_handler_pt ssl_client_hello_handler;
263+
ngx_str_t ssl_client_hello_src;
264+
u_char *ssl_client_hello_src_key;
260265
} srv;
261266
#endif
262267

src/ngx_stream_lua_control.c

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -114,17 +114,18 @@ ngx_stream_lua_ffi_exit(ngx_stream_lua_request_t *r, int status, u_char *err,
114114

115115

116116
if (ngx_stream_lua_ffi_check_context(ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
117-
| NGX_STREAM_LUA_CONTEXT_TIMER
118-
| NGX_STREAM_LUA_CONTEXT_BALANCER
119-
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
120-
| NGX_STREAM_LUA_CONTEXT_PREREAD,
121-
err, errlen)
122-
!= NGX_OK)
117+
| NGX_STREAM_LUA_CONTEXT_TIMER
118+
| NGX_STREAM_LUA_CONTEXT_BALANCER
119+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
120+
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
121+
| NGX_STREAM_LUA_CONTEXT_PREREAD,
122+
err, errlen) != NGX_OK)
123123
{
124124
return NGX_ERROR;
125125
}
126126

127-
if (ctx->context & NGX_STREAM_LUA_CONTEXT_SSL_CERT)
127+
if (ctx->context & (NGX_STREAM_LUA_CONTEXT_SSL_CERT
128+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO ))
128129
{
129130

130131
#if (NGX_STREAM_SSL)

src/ngx_stream_lua_coroutine.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -126,6 +126,7 @@ ngx_stream_lua_coroutine_create_helper(lua_State *L,
126126

127127
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
128128
| NGX_STREAM_LUA_CONTEXT_TIMER
129+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
129130
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
130131
| NGX_STREAM_LUA_CONTEXT_PREREAD
131132
);
@@ -206,6 +207,7 @@ ngx_stream_lua_coroutine_resume(lua_State *L)
206207

207208
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
208209
| NGX_STREAM_LUA_CONTEXT_TIMER
210+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
209211
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
210212
| NGX_STREAM_LUA_CONTEXT_PREREAD
211213
);
@@ -266,6 +268,7 @@ ngx_stream_lua_coroutine_yield(lua_State *L)
266268

267269
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
268270
| NGX_STREAM_LUA_CONTEXT_TIMER
271+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
269272
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
270273
| NGX_STREAM_LUA_CONTEXT_PREREAD
271274
);
@@ -425,6 +428,7 @@ ngx_stream_lua_coroutine_status(lua_State *L)
425428

426429
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
427430
| NGX_STREAM_LUA_CONTEXT_TIMER
431+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
428432
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
429433
| NGX_STREAM_LUA_CONTEXT_PREREAD
430434
);

src/ngx_stream_lua_ctx.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -95,7 +95,8 @@ ngx_stream_lua_ffi_get_ctx_ref(ngx_stream_lua_request_t *r, int *in_ssl_phase,
9595
return ctx->ctx_ref;
9696
}
9797

98-
*in_ssl_phase = ctx->context & NGX_STREAM_LUA_CONTEXT_SSL_CERT;
98+
*in_ssl_phase = ctx->context & (NGX_STREAM_LUA_CONTEXT_SSL_CERT
99+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO);
99100
*ssl_ctx_ref = LUA_NOREF;
100101

101102
#if (NGX_STREAM_SSL)

src/ngx_stream_lua_module.c

Lines changed: 59 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
#include "ngx_stream_lua_balancer.h"
2929
#include "ngx_stream_lua_logby.h"
3030
#include "ngx_stream_lua_semaphore.h"
31+
#include "ngx_stream_lua_ssl_client_helloby.h"
3132
#include "ngx_stream_lua_ssl_certby.h"
3233

3334

@@ -385,6 +386,20 @@ static ngx_command_t ngx_stream_lua_cmds[] = {
385386
offsetof(ngx_stream_lua_srv_conf_t, ssl_ciphers),
386387
NULL },
387388

389+
{ ngx_string("ssl_client_hello_by_lua_block"),
390+
NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_BLOCK|NGX_CONF_NOARGS,
391+
ngx_stream_lua_ssl_client_hello_by_lua_block,
392+
NGX_STREAM_SRV_CONF_OFFSET,
393+
0,
394+
(void *) ngx_stream_lua_ssl_client_hello_handler_inline },
395+
396+
{ ngx_string("ssl_client_hello_by_lua_file"),
397+
NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1,
398+
ngx_stream_lua_ssl_client_hello_by_lua,
399+
NGX_STREAM_SRV_CONF_OFFSET,
400+
0,
401+
(void *) ngx_stream_lua_ssl_client_hello_handler_file },
402+
388403
{ ngx_string("ssl_certificate_by_lua_block"),
389404
NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_BLOCK|NGX_CONF_NOARGS,
390405
ngx_stream_lua_ssl_cert_by_lua_block,
@@ -763,6 +778,10 @@ ngx_stream_lua_create_srv_conf(ngx_conf_t *cf)
763778
}
764779

765780
/* set by ngx_pcalloc:
781+
* lscf->srv.ssl_client_hello_handler = NULL;
782+
* lscf->srv.ssl_client_hello_src = { 0, NULL };
783+
* lscf->srv.ssl_client_hello_src_key = NULL;
784+
*
766785
* lscf->srv.ssl_cert_handler = NULL;
767786
* lscf->srv.ssl_cert_src = { 0, NULL };
768787
* lscf->srv.ssl_cert_src_key = NULL;
@@ -814,14 +833,53 @@ ngx_stream_lua_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child)
814833

815834
sscf = ngx_stream_conf_get_module_srv_conf(cf, ngx_stream_ssl_module);
816835
if (sscf && sscf->listen) {
836+
if (conf->srv.ssl_client_hello_src.len == 0) {
837+
conf->srv.ssl_client_hello_src = prev->srv.ssl_client_hello_src;
838+
conf->srv.ssl_client_hello_src_key =
839+
prev->srv.ssl_client_hello_src_key;
840+
conf->srv.ssl_client_hello_handler =
841+
prev->srv.ssl_client_hello_handler;
842+
}
843+
844+
if (conf->srv.ssl_client_hello_src.len) {
845+
if (sscf->ssl.ctx == NULL) {
846+
ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
847+
"no ssl configured for the server");
848+
849+
return NGX_CONF_ERROR;
850+
}
851+
#ifdef LIBRESSL_VERSION_NUMBER
852+
ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
853+
"LibreSSL does not support by "
854+
"ssl_client_hello_by_lua*");
855+
return NGX_CONF_ERROR;
856+
857+
#else
858+
859+
# ifdef SSL_ERROR_WANT_CLIENT_HELLO_CB
860+
861+
SSL_CTX_set_client_hello_cb(sscf->ssl.ctx,
862+
ngx_stream_lua_ssl_client_hello_handler,
863+
NULL);
864+
865+
# else
866+
867+
ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
868+
"OpenSSL too old to support "
869+
"ssl_client_hello_by_lua*");
870+
return NGX_CONF_ERROR;
871+
872+
# endif
873+
#endif
874+
}
875+
817876
if (conf->srv.ssl_cert_src.len == 0) {
818877
conf->srv.ssl_cert_src = prev->srv.ssl_cert_src;
819878
conf->srv.ssl_cert_src_key = prev->srv.ssl_cert_src_key;
820879
conf->srv.ssl_cert_handler = prev->srv.ssl_cert_handler;
821880
}
822881

823882
if (conf->srv.ssl_cert_src.len) {
824-
sscf = ngx_stream_conf_get_module_srv_conf(cf, ngx_stream_ssl_module);
825883
if (sscf->ssl.ctx == NULL) {
826884
ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
827885
"no ssl configured for the server");

src/ngx_stream_lua_phase.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,10 @@ ngx_stream_lua_ngx_get_phase(lua_State *L)
5050
lua_pushliteral(L, "init_worker");
5151
break;
5252

53+
case NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO:
54+
lua_pushliteral(L, "ssl_client_hello");
55+
break;
56+
5357
case NGX_STREAM_LUA_CONTEXT_SSL_CERT:
5458
lua_pushliteral(L, "ssl_cert");
5559
break;

src/ngx_stream_lua_semaphore.c

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -388,10 +388,11 @@ ngx_stream_lua_ffi_sema_wait(ngx_stream_lua_request_t *r,
388388
}
389389

390390
rc = ngx_stream_lua_ffi_check_context(ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
391-
| NGX_STREAM_LUA_CONTEXT_PREREAD
392-
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
393-
| NGX_STREAM_LUA_CONTEXT_TIMER,
394-
err, errlen);
391+
| NGX_STREAM_LUA_CONTEXT_PREREAD
392+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
393+
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
394+
| NGX_STREAM_LUA_CONTEXT_TIMER,
395+
err, errlen);
395396

396397
if (rc != NGX_OK) {
397398
return NGX_ERROR;

src/ngx_stream_lua_sleep.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ ngx_stream_lua_ngx_sleep(lua_State *L)
6464
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
6565

6666
| NGX_STREAM_LUA_CONTEXT_PREREAD
67-
67+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
6868
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
6969
| NGX_STREAM_LUA_CONTEXT_TIMER);
7070

src/ngx_stream_lua_socket_tcp.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -445,6 +445,7 @@ ngx_stream_lua_socket_tcp(lua_State *L)
445445

446446
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
447447
| NGX_STREAM_LUA_CONTEXT_PREREAD
448+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
448449
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
449450
| NGX_STREAM_LUA_CONTEXT_TIMER);
450451

@@ -900,7 +901,7 @@ ngx_stream_lua_socket_tcp_connect(lua_State *L)
900901
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
901902

902903
| NGX_STREAM_LUA_CONTEXT_PREREAD
903-
904+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
904905
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
905906
| NGX_STREAM_LUA_CONTEXT_TIMER);
906907

src/ngx_stream_lua_socket_udp.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -189,6 +189,7 @@ ngx_stream_lua_socket_udp(lua_State *L)
189189
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
190190

191191
| NGX_STREAM_LUA_CONTEXT_PREREAD
192+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
192193
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
193194
| NGX_STREAM_LUA_CONTEXT_TIMER);
194195

@@ -251,7 +252,7 @@ ngx_stream_lua_socket_udp_setpeername(lua_State *L)
251252
ngx_stream_lua_check_context(L, ctx, NGX_STREAM_LUA_CONTEXT_CONTENT
252253

253254
| NGX_STREAM_LUA_CONTEXT_PREREAD
254-
255+
| NGX_STREAM_LUA_CONTEXT_SSL_CLIENT_HELLO
255256
| NGX_STREAM_LUA_CONTEXT_SSL_CERT
256257
| NGX_STREAM_LUA_CONTEXT_TIMER);
257258

src/ngx_stream_lua_ssl.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ typedef struct {
3333
ngx_str_t session_id;
3434

3535
int exit_code; /* exit code for openssl's
36+
set_client_hello_cb or
3637
set_cert_cb callback */
3738

3839
int ctx_ref; /* reference to anchor
@@ -42,6 +43,7 @@ typedef struct {
4243
unsigned done:1;
4344
unsigned aborted:1;
4445

46+
unsigned entered_client_hello_handler:1;
4547
unsigned entered_cert_handler:1;
4648
unsigned entered_sess_fetch_handler:1;
4749
} ngx_stream_lua_ssl_ctx_t;

0 commit comments

Comments
 (0)