summaryrefslogtreecommitdiffhomepage
path: root/src
diff options
context:
space:
mode:
authorVladimir Homutov <vl@nginx.com>2020-03-21 20:49:55 +0300
committerVladimir Homutov <vl@nginx.com>2020-03-21 20:49:55 +0300
commit63e6c9349e0e164ab2b7a368b473ed6e054e83c0 (patch)
tree8fbca4080de7c61e70d9111ca357b33871e4dbf8 /src
parent2af37e507db9648f1f11a7ad39c516445f126de2 (diff)
downloadnginx-63e6c9349e0e164ab2b7a368b473ed6e054e83c0.tar.gz
nginx-63e6c9349e0e164ab2b7a368b473ed6e054e83c0.tar.bz2
Implemented parsing of remaining frame types.
Diffstat (limited to 'src')
-rw-r--r--src/event/ngx_event_quic_transport.c128
-rw-r--r--src/event/ngx_event_quic_transport.h33
2 files changed, 158 insertions, 3 deletions
diff --git a/src/event/ngx_event_quic_transport.c b/src/event/ngx_event_quic_transport.c
index e03194b80..dadc4f197 100644
--- a/src/event/ngx_event_quic_transport.c
+++ b/src/event/ngx_event_quic_transport.c
@@ -856,7 +856,7 @@ ngx_quic_parse_frame(ngx_quic_header_t *pkt, u_char *start, u_char *end,
(f->type == NGX_QUIC_FT_STREAMS_BLOCKED) ? 1 : 0;
ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
- "STREAMS BLOCKED frame { limit %i bidi: %d }",
+ "STREAMS BLOCKED frame { limit %ui bidi: %d }",
f->u.streams_blocked.limit,
f->u.streams_blocked.bidi);
@@ -877,19 +877,141 @@ ngx_quic_parse_frame(ngx_quic_header_t *pkt, u_char *start, u_char *end,
case NGX_QUIC_FT_MAX_STREAMS:
case NGX_QUIC_FT_MAX_STREAMS2:
+
+ if (!(ngx_quic_short_pkt(flags) || ngx_quic_pkt_zrtt(flags))) {
+ goto not_allowed;
+ }
+
+ p = ngx_quic_parse_int(p, end, &f->u.max_streams.limit);
+ if (p == NULL) {
+ ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
+ "failed to parse max streams frame limit");
+ return NGX_ERROR;
+ }
+
+ f->u.max_streams.bidi = (f->type == NGX_QUIC_FT_MAX_STREAMS) ? 1 : 0;
+
+ ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
+ "MAX STREAMS frame { limit %ui bidi: %d }",
+ f->u.max_streams.limit,
+ f->u.max_streams.bidi);
+ break;
+
case NGX_QUIC_FT_MAX_STREAM_DATA:
+
+ if (!(ngx_quic_short_pkt(flags) || ngx_quic_pkt_zrtt(flags))) {
+ goto not_allowed;
+ }
+
+ p = ngx_quic_parse_int_multi(p, end, &f->u.max_stream_data.id,
+ &f->u.max_stream_data.limit, NULL);
+ if (p == NULL) {
+ ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
+ "failed to parse max stream data frame");
+ return NGX_ERROR;
+ }
+
+ ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
+ "MAX STREAM DATA frame { id: %ui limit: %ui }",
+ f->u.max_stream_data.id,
+ f->u.max_stream_data.limit);
+ break;
+
case NGX_QUIC_FT_DATA_BLOCKED:
+
+ if (!(ngx_quic_short_pkt(flags) || ngx_quic_pkt_zrtt(flags))) {
+ goto not_allowed;
+ }
+
+ p = ngx_quic_parse_int(p, end, &f->u.data_blocked.limit);
+ if (p == NULL) {
+ ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
+ "failed to parse data blocked frame limit");
+ return NGX_ERROR;
+ }
+
+ ngx_log_debug1(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
+ "DATA BLOCKED frame { limit %ui }",
+ f->u.data_blocked.limit);
+ break;
+
case NGX_QUIC_FT_STREAM_DATA_BLOCKED:
+
+ if (!(ngx_quic_short_pkt(flags) || ngx_quic_pkt_zrtt(flags))) {
+ goto not_allowed;
+ }
+
+ p = ngx_quic_parse_int_multi(p, end, &f->u.stream_data_blocked.id,
+ &f->u.stream_data_blocked.limit, NULL);
+ if (p == NULL) {
+ ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
+ "failed to parse tream data blocked frame");
+ return NGX_ERROR;
+ }
+
+ ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
+ "STREAM DATA BLOCKED frame { id: %ui limit: %ui }",
+ f->u.stream_data_blocked.id,
+ f->u.stream_data_blocked.limit);
+ break;
+
case NGX_QUIC_FT_RETIRE_CONNECTION_ID:
+
+ if (!(ngx_quic_short_pkt(flags) || ngx_quic_pkt_zrtt(flags))) {
+ goto not_allowed;
+ }
+
+ p = ngx_quic_parse_int(p, end, &f->u.retire_cid.sequence_number);
+ if (p == NULL) {
+ ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
+ "failed to parse retire connection id"
+ " frame sequence number");
+ return NGX_ERROR;
+ }
+
+ ngx_log_debug1(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
+ "RETIRE CONNECTION ID frame { sequence_number %ui }",
+ f->u.retire_cid.sequence_number);
+ break;
+
case NGX_QUIC_FT_PATH_CHALLENGE:
+
+ if (!(ngx_quic_short_pkt(flags) || ngx_quic_pkt_zrtt(flags))) {
+ goto not_allowed;
+ }
+
+ p = ngx_quic_copy_bytes(p, end, 8, f->u.path_challenge.data);
+ if (p == NULL) {
+ ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
+ "failed to get path challenge frame data");
+ return NGX_ERROR;
+ }
+
+ ngx_log_debug0(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
+ "PATH CHALLENGE frame");
+
+ ngx_quic_hexdump0(pkt->log, "path challenge data",
+ f->u.path_challenge.data, 8);
+ break;
+
case NGX_QUIC_FT_PATH_RESPONSE:
if (!(ngx_quic_short_pkt(flags) || ngx_quic_pkt_zrtt(flags))) {
goto not_allowed;
}
- ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
- "unimplemented frame type 0x%xi in packet", f->type);
+ p = ngx_quic_copy_bytes(p, end, 8, f->u.path_response.data);
+ if (p == NULL) {
+ ngx_log_error(NGX_LOG_ERR, pkt->log, 0,
+ "failed to get path response frame data");
+ return NGX_ERROR;
+ }
+
+ ngx_log_debug0(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
+ "PATH RESPONSE frame");
+
+ ngx_quic_hexdump0(pkt->log, "path response data",
+ f->u.path_response.data, 8);
break;
default:
diff --git a/src/event/ngx_event_quic_transport.h b/src/event/ngx_event_quic_transport.h
index a6d64aeb9..c8af85c33 100644
--- a/src/event/ngx_event_quic_transport.h
+++ b/src/event/ngx_event_quic_transport.h
@@ -172,6 +172,33 @@ typedef struct {
} ngx_quic_max_streams_frame_t;
+typedef struct {
+ uint64_t id;
+ uint64_t limit;
+} ngx_quic_max_stream_data_frame_t;
+
+
+typedef struct {
+ uint64_t limit;
+} ngx_quic_data_blocked_frame_t;
+
+
+typedef struct {
+ uint64_t id;
+ uint64_t limit;
+} ngx_quic_stream_data_blocked_frame_t;
+
+
+typedef struct {
+ uint64_t sequence_number;
+} ngx_quic_retire_cid_frame_t;
+
+
+typedef struct {
+ u_char data[8];
+} ngx_quic_path_challenge_frame_t;
+
+
typedef struct ngx_quic_frame_s ngx_quic_frame_t;
struct ngx_quic_frame_s {
@@ -189,6 +216,12 @@ struct ngx_quic_frame_s {
ngx_quic_stop_sending_frame_t stop_sending;
ngx_quic_streams_blocked_frame_t streams_blocked;
ngx_quic_max_streams_frame_t max_streams;
+ ngx_quic_max_stream_data_frame_t max_stream_data;
+ ngx_quic_data_blocked_frame_t data_blocked;
+ ngx_quic_stream_data_blocked_frame_t stream_data_blocked;
+ ngx_quic_retire_cid_frame_t retire_cid;
+ ngx_quic_path_challenge_frame_t path_challenge;
+ ngx_quic_path_challenge_frame_t path_response;
} u;
u_char info[128]; // for debug
};