Latest update - 9194

This commit is contained in:
2023-12-12 23:44:38 +09:00
parent 802d902f2d
commit b4745d7a71
9 changed files with 228 additions and 114 deletions
+80 -40
View File
@@ -36,16 +36,28 @@ ngx_int_t
ngx_quic_handle_path_challenge_frame(ngx_connection_t *c,
ngx_quic_header_t *pkt, ngx_quic_path_challenge_frame_t *f)
{
ngx_quic_frame_t frame, *fp;
size_t min;
ngx_quic_frame_t *fp;
ngx_quic_connection_t *qc;
if (pkt->level != ssl_encryption_application || pkt->path_challenged) {
ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0,
"quic ignoring PATH_CHALLENGE");
return NGX_OK;
}
pkt->path_challenged = 1;
qc = ngx_quic_get_connection(c);
ngx_memzero(&frame, sizeof(ngx_quic_frame_t));
fp = ngx_quic_alloc_frame(c);
if (fp == NULL) {
return NGX_ERROR;
}
frame.level = ssl_encryption_application;
frame.type = NGX_QUIC_FT_PATH_RESPONSE;
frame.u.path_response = *f;
fp->level = ssl_encryption_application;
fp->type = NGX_QUIC_FT_PATH_RESPONSE;
fp->u.path_response = *f;
/*
* RFC 9000, 8.2.2. Path Validation Responses
@@ -57,8 +69,14 @@ ngx_quic_handle_path_challenge_frame(ngx_connection_t *c,
/*
* An endpoint MUST expand datagrams that contain a PATH_RESPONSE frame
* to at least the smallest allowed maximum datagram size of 1200 bytes.
* ...
* However, an endpoint MUST NOT expand the datagram containing the
* PATH_RESPONSE if the resulting data exceeds the anti-amplification limit.
*/
if (ngx_quic_frame_sendto(c, &frame, 1200, pkt->path) == NGX_ERROR) {
min = (ngx_quic_path_limit(c, pkt->path, 1200) < 1200) ? 0 : 1200;
if (ngx_quic_frame_sendto(c, fp, min, pkt->path) == NGX_ERROR) {
return NGX_ERROR;
}
@@ -113,8 +131,8 @@ ngx_quic_handle_path_response_frame(ngx_connection_t *c,
continue;
}
if (ngx_memcmp(path->challenge1, f->data, sizeof(f->data)) == 0
|| ngx_memcmp(path->challenge2, f->data, sizeof(f->data)) == 0)
if (ngx_memcmp(path->challenge[0], f->data, sizeof(f->data)) == 0
|| ngx_memcmp(path->challenge[1], f->data, sizeof(f->data)) == 0)
{
goto valid;
}
@@ -151,6 +169,7 @@ valid:
path->mtu = prev->mtu;
path->max_mtu = prev->max_mtu;
path->mtu_unvalidated = 0;
}
}
@@ -164,6 +183,13 @@ valid:
qc->congestion.recovery_start = ngx_current_msec;
}
path->validated = 1;
if (path->mtu_unvalidated) {
path->mtu_unvalidated = 0;
return ngx_quic_validate_path(c, path);
}
/*
* RFC 9000, 9.3. Responding to Connection Migration
*
@@ -181,8 +207,6 @@ valid:
ngx_quic_path_dbg(c, "is validated", path);
path->validated = 1;
ngx_quic_discover_path_mtu(c, path);
return NGX_OK;
@@ -510,11 +534,7 @@ ngx_quic_validate_path(ngx_connection_t *c, ngx_quic_path_t *path)
path->tries = 0;
if (RAND_bytes(path->challenge1, 8) != 1) {
return NGX_ERROR;
}
if (RAND_bytes(path->challenge2, 8) != 1) {
if (RAND_bytes((u_char *) path->challenge, sizeof(path->challenge)) != 1) {
return NGX_ERROR;
}
@@ -535,37 +555,48 @@ ngx_quic_validate_path(ngx_connection_t *c, ngx_quic_path_t *path)
static ngx_int_t
ngx_quic_send_path_challenge(ngx_connection_t *c, ngx_quic_path_t *path)
{
ngx_quic_frame_t frame;
size_t min;
ngx_uint_t n;
ngx_quic_frame_t *frame;
ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0,
"quic path seq:%uL send path_challenge tries:%ui",
path->seqnum, path->tries);
ngx_memzero(&frame, sizeof(ngx_quic_frame_t));
for (n = 0; n < 2; n++) {
frame.level = ssl_encryption_application;
frame.type = NGX_QUIC_FT_PATH_CHALLENGE;
frame = ngx_quic_alloc_frame(c);
if (frame == NULL) {
return NGX_ERROR;
}
ngx_memcpy(frame.u.path_challenge.data, path->challenge1, 8);
frame->level = ssl_encryption_application;
frame->type = NGX_QUIC_FT_PATH_CHALLENGE;
/*
* RFC 9000, 8.2.1. Initiating Path Validation
*
* An endpoint MUST expand datagrams that contain a PATH_CHALLENGE frame
* to at least the smallest allowed maximum datagram size of 1200 bytes,
* unless the anti-amplification limit for the path does not permit
* sending a datagram of this size.
*/
ngx_memcpy(frame->u.path_challenge.data, path->challenge[n], 8);
/* same applies to PATH_RESPONSE frames */
if (ngx_quic_frame_sendto(c, &frame, 1200, path) == NGX_ERROR) {
return NGX_ERROR;
}
/*
* RFC 9000, 8.2.1. Initiating Path Validation
*
* An endpoint MUST expand datagrams that contain a PATH_CHALLENGE frame
* to at least the smallest allowed maximum datagram size of 1200 bytes,
* unless the anti-amplification limit for the path does not permit
* sending a datagram of this size.
*/
ngx_memcpy(frame.u.path_challenge.data, path->challenge2, 8);
if (path->mtu_unvalidated
|| ngx_quic_path_limit(c, path, 1200) < 1200)
{
min = 0;
path->mtu_unvalidated = 1;
if (ngx_quic_frame_sendto(c, &frame, 1200, path) == NGX_ERROR) {
return NGX_ERROR;
} else {
min = 1200;
}
if (ngx_quic_frame_sendto(c, frame, min, path) == NGX_ERROR) {
return NGX_ERROR;
}
}
return NGX_OK;
@@ -869,16 +900,20 @@ ngx_quic_expire_path_mtu_discovery(ngx_connection_t *c, ngx_quic_path_t *path)
static ngx_int_t
ngx_quic_send_path_mtu_probe(ngx_connection_t *c, ngx_quic_path_t *path)
{
size_t mtu;
ngx_int_t rc;
ngx_uint_t log_error;
ngx_quic_frame_t frame;
ngx_quic_frame_t *frame;
ngx_quic_send_ctx_t *ctx;
ngx_quic_connection_t *qc;
ngx_memzero(&frame, sizeof(ngx_quic_frame_t));
frame = ngx_quic_alloc_frame(c);
if (frame == NULL) {
return NGX_ERROR;
}
frame.level = ssl_encryption_application;
frame.type = NGX_QUIC_FT_PING;
frame->level = ssl_encryption_application;
frame->type = NGX_QUIC_FT_PING;
qc = ngx_quic_get_connection(c);
ctx = ngx_quic_get_send_ctx(qc, ssl_encryption_application);
@@ -892,7 +927,12 @@ ngx_quic_send_path_mtu_probe(ngx_connection_t *c, ngx_quic_path_t *path)
log_error = c->log_error;
c->log_error = NGX_ERROR_IGNORE_EMSGSIZE;
rc = ngx_quic_frame_sendto(c, &frame, path->mtud, path);
mtu = path->mtu;
path->mtu = path->mtud;
rc = ngx_quic_frame_sendto(c, frame, path->mtud, path);
path->mtu = mtu;
c->log_error = log_error;
if (rc == NGX_ERROR) {