# HG changeset patch # User Sergey Kandaurov # Date 1604957576 -10800 # Node ID e0947c952d43d46cff68d47ac2cf6fa2f934b2a7 # Parent 4416b7ab0a27d2bb4568595a88ca0fe6dc8f2289 QUIC: multiple versions support in ALPN. Previously, a version based on NGX_QUIC_DRAFT_VERSION was always set. Now it is taken from the negotiated QUIC version that may differ. diff --git a/src/event/ngx_event_quic.c b/src/event/ngx_event_quic.c --- a/src/event/ngx_event_quic.c +++ b/src/event/ngx_event_quic.c @@ -5813,3 +5813,14 @@ ngx_quic_free_frame(ngx_connection_t *c, "quic free frame n:%ui", qc->nframes); #endif } + + +uint32_t +ngx_quic_version(ngx_connection_t *c) +{ + uint32_t version; + + version = c->quic->version; + + return (version & 0xff000000) == 0xff000000 ? version & 0xff : version; +} diff --git a/src/event/ngx_event_quic.h b/src/event/ngx_event_quic.h --- a/src/event/ngx_event_quic.h +++ b/src/event/ngx_event_quic.h @@ -122,6 +122,7 @@ void ngx_quic_run(ngx_connection_t *c, n ngx_connection_t *ngx_quic_open_stream(ngx_connection_t *c, ngx_uint_t bidi); void ngx_quic_finalize_connection(ngx_connection_t *c, ngx_uint_t err, const char *reason); +uint32_t ngx_quic_version(ngx_connection_t *c); /********************************* DEBUG *************************************/ diff --git a/src/http/modules/ngx_http_quic_module.h b/src/http/modules/ngx_http_quic_module.h --- a/src/http/modules/ngx_http_quic_module.h +++ b/src/http/modules/ngx_http_quic_module.h @@ -14,9 +14,8 @@ #include -#define NGX_HTTP_QUIC_ALPN(s) NGX_HTTP_QUIC_ALPN_DRAFT(s) -#define NGX_HTTP_QUIC_ALPN_DRAFT(s) "\x05hq-" #s -#define NGX_HTTP_QUIC_ALPN_ADVERTISE NGX_HTTP_QUIC_ALPN(NGX_QUIC_DRAFT_VERSION) +#define NGX_HTTP_QUIC_ALPN_ADVERTISE "\x02hq" +#define NGX_HTTP_QUIC_ALPN_DRAFT_FMT "\x05hq-%02uD" extern ngx_module_t ngx_http_quic_module; diff --git a/src/http/modules/ngx_http_ssl_module.c b/src/http/modules/ngx_http_ssl_module.c --- a/src/http/modules/ngx_http_ssl_module.c +++ b/src/http/modules/ngx_http_ssl_module.c @@ -418,6 +418,9 @@ ngx_http_ssl_alpn_select(ngx_ssl_conn_t unsigned char *outlen, const unsigned char *in, unsigned int inlen, void *arg) { +#if (NGX_HTTP_QUIC) + const char *fmt; +#endif unsigned int srvlen; unsigned char *srv; #if (NGX_DEBUG) @@ -452,16 +455,32 @@ ngx_http_ssl_alpn_select(ngx_ssl_conn_t } else #endif -#if (NGX_HTTP_V3) - if (hc->addr_conf->http3) { - srv = (unsigned char *) NGX_HTTP_V3_ALPN_ADVERTISE; - srvlen = sizeof(NGX_HTTP_V3_ALPN_ADVERTISE) - 1; - } else -#endif #if (NGX_HTTP_QUIC) if (hc->addr_conf->quic) { - srv = (unsigned char *) NGX_HTTP_QUIC_ALPN_ADVERTISE; - srvlen = sizeof(NGX_HTTP_QUIC_ALPN_ADVERTISE) - 1; +#if (NGX_HTTP_V3) + if (hc->addr_conf->http3) { + srv = (unsigned char *) NGX_HTTP_V3_ALPN_ADVERTISE; + srvlen = sizeof(NGX_HTTP_V3_ALPN_ADVERTISE) - 1; + fmt = NGX_HTTP_V3_ALPN_DRAFT_FMT; + + } else +#endif + { + srv = (unsigned char *) NGX_HTTP_QUIC_ALPN_ADVERTISE; + srvlen = sizeof(NGX_HTTP_QUIC_ALPN_ADVERTISE) - 1; + fmt = NGX_HTTP_QUIC_ALPN_DRAFT_FMT; + } + + /* QUIC draft */ + + if (ngx_quic_version(c) > 1) { + srv = ngx_pnalloc(c->pool, sizeof("\x05h3-xx") - 1); + if (srv == NULL) { + return SSL_TLSEXT_ERR_NOACK; + } + srvlen = ngx_sprintf(srv, fmt, ngx_quic_version(c)) - srv; + } + } else #endif { diff --git a/src/http/v3/ngx_http_v3.h b/src/http/v3/ngx_http_v3.h --- a/src/http/v3/ngx_http_v3.h +++ b/src/http/v3/ngx_http_v3.h @@ -15,9 +15,8 @@ #include -#define NGX_HTTP_V3_ALPN(s) NGX_HTTP_V3_ALPN_DRAFT(s) -#define NGX_HTTP_V3_ALPN_DRAFT(s) "\x05h3-" #s -#define NGX_HTTP_V3_ALPN_ADVERTISE NGX_HTTP_V3_ALPN(NGX_QUIC_DRAFT_VERSION) +#define NGX_HTTP_V3_ALPN_ADVERTISE "\x02h3" +#define NGX_HTTP_V3_ALPN_DRAFT_FMT "\x05h3-%02uD" #define NGX_HTTP_V3_VARLEN_INT_LEN 4 #define NGX_HTTP_V3_PREFIX_INT_LEN 11