Mercurial > hg > nginx
comparison src/event/quic/ngx_event_quic.c @ 8698:9ed95726b99b quic
QUIC: send PING frames on PTO expiration.
Two PING frames are sent per level that generate two UDP datagrams.
author | Roman Arutyunyan <arut@nginx.com> |
---|---|
date | Fri, 12 Feb 2021 14:51:53 +0300 |
parents | faa3201ff351 |
children | ba9e34c03968 |
comparison
equal
deleted
inserted
replaced
8697:faa3201ff351 | 8698:9ed95726b99b |
---|---|
5097 f->first = now; | 5097 f->first = now; |
5098 f->last = now; | 5098 f->last = now; |
5099 f->plen = 0; | 5099 f->plen = 0; |
5100 | 5100 |
5101 nframes++; | 5101 nframes++; |
5102 | |
5103 if (f->flush) { | |
5104 break; | |
5105 } | |
5102 } | 5106 } |
5103 | 5107 |
5104 if (nframes == 0) { | 5108 if (nframes == 0) { |
5105 return 0; | 5109 return 0; |
5106 } | 5110 } |
5344 | 5348 |
5345 static void | 5349 static void |
5346 ngx_quic_pto_handler(ngx_event_t *ev) | 5350 ngx_quic_pto_handler(ngx_event_t *ev) |
5347 { | 5351 { |
5348 ngx_uint_t i; | 5352 ngx_uint_t i; |
5349 ngx_queue_t *q; | 5353 ngx_msec_t now; |
5354 ngx_queue_t *q, *next; | |
5350 ngx_connection_t *c; | 5355 ngx_connection_t *c; |
5351 ngx_quic_frame_t *start; | 5356 ngx_quic_frame_t *f; |
5352 ngx_quic_send_ctx_t *ctx; | 5357 ngx_quic_send_ctx_t *ctx; |
5353 ngx_quic_connection_t *qc; | 5358 ngx_quic_connection_t *qc; |
5354 | 5359 |
5355 ngx_log_debug0(NGX_LOG_DEBUG_EVENT, ev->log, 0, "quic pto timer"); | 5360 ngx_log_debug0(NGX_LOG_DEBUG_EVENT, ev->log, 0, "quic pto timer"); |
5356 | 5361 |
5357 c = ev->data; | 5362 c = ev->data; |
5358 qc = ngx_quic_get_connection(c); | 5363 qc = ngx_quic_get_connection(c); |
5359 | 5364 now = ngx_current_msec; |
5360 qc->pto_count++; | |
5361 | 5365 |
5362 for (i = 0; i < NGX_QUIC_SEND_CTX_LAST; i++) { | 5366 for (i = 0; i < NGX_QUIC_SEND_CTX_LAST; i++) { |
5363 | 5367 |
5364 ctx = &qc->send_ctx[i]; | 5368 ctx = &qc->send_ctx[i]; |
5365 | 5369 |
5366 if (ngx_queue_empty(&ctx->sent)) { | 5370 if (ngx_queue_empty(&ctx->sent)) { |
5367 continue; | 5371 continue; |
5368 } | 5372 } |
5369 | 5373 |
5370 q = ngx_queue_head(&ctx->sent); | 5374 q = ngx_queue_head(&ctx->sent); |
5371 start = ngx_queue_data(q, ngx_quic_frame_t, queue); | 5375 f = ngx_queue_data(q, ngx_quic_frame_t, queue); |
5372 | 5376 |
5373 if (start->pnum <= ctx->largest_ack | 5377 if (f->pnum <= ctx->largest_ack |
5374 && ctx->largest_ack != NGX_QUIC_UNSET_PN) | 5378 && ctx->largest_ack != NGX_QUIC_UNSET_PN) |
5375 { | 5379 { |
5376 continue; | 5380 continue; |
5377 } | 5381 } |
5378 | 5382 |
5379 ngx_log_debug3(NGX_LOG_DEBUG_EVENT, c->log, 0, | 5383 if ((ngx_msec_int_t) (f->last + ngx_quic_pto(c, ctx) - now) > 0) { |
5380 "quic pto pnum:%uL pto_count:%ui level:%d", | 5384 continue; |
5381 start->pnum, qc->pto_count, start->level); | 5385 } |
5382 | 5386 |
5383 ngx_quic_resend_frames(c, ctx); | 5387 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0, |
5384 } | 5388 "quic pto %s pto_count:%ui", |
5389 ngx_quic_level_name(ctx->level), qc->pto_count); | |
5390 | |
5391 for (q = ngx_queue_head(&ctx->frames); | |
5392 q != ngx_queue_sentinel(&ctx->frames); | |
5393 /* void */) | |
5394 { | |
5395 next = ngx_queue_next(q); | |
5396 f = ngx_queue_data(q, ngx_quic_frame_t, queue); | |
5397 | |
5398 if (f->type == NGX_QUIC_FT_PING) { | |
5399 ngx_queue_remove(q); | |
5400 ngx_quic_free_frame(c, f); | |
5401 } | |
5402 | |
5403 q = next; | |
5404 } | |
5405 | |
5406 for (q = ngx_queue_head(&ctx->sent); | |
5407 q != ngx_queue_sentinel(&ctx->sent); | |
5408 /* void */) | |
5409 { | |
5410 next = ngx_queue_next(q); | |
5411 f = ngx_queue_data(q, ngx_quic_frame_t, queue); | |
5412 | |
5413 if (f->type == NGX_QUIC_FT_PING) { | |
5414 ngx_quic_congestion_lost(c, f); | |
5415 ngx_queue_remove(q); | |
5416 ngx_quic_free_frame(c, f); | |
5417 } | |
5418 | |
5419 q = next; | |
5420 } | |
5421 | |
5422 /* enforce 2 udp datagrams */ | |
5423 | |
5424 f = ngx_quic_alloc_frame(c); | |
5425 if (f == NULL) { | |
5426 break; | |
5427 } | |
5428 | |
5429 f->level = ctx->level; | |
5430 f->type = NGX_QUIC_FT_PING; | |
5431 f->flush = 1; | |
5432 | |
5433 ngx_quic_queue_frame(qc, f); | |
5434 | |
5435 f = ngx_quic_alloc_frame(c); | |
5436 if (f == NULL) { | |
5437 break; | |
5438 } | |
5439 | |
5440 f->level = ctx->level; | |
5441 f->type = NGX_QUIC_FT_PING; | |
5442 | |
5443 ngx_quic_queue_frame(qc, f); | |
5444 } | |
5445 | |
5446 qc->pto_count++; | |
5385 | 5447 |
5386 ngx_quic_connstate_dbg(c); | 5448 ngx_quic_connstate_dbg(c); |
5387 } | 5449 } |
5388 | 5450 |
5389 | 5451 |