aboutsummaryrefslogtreecommitdiffstats
path: root/src/vnet/tcp
diff options
context:
space:
mode:
authorFlorin Coras <fcoras@cisco.com>2019-11-13 19:09:47 -0800
committerDave Barach <openvpp@barachs.net>2019-11-20 18:34:07 +0000
commit11e9e351046d8f4ab61b8aaf975046215fba7c5d (patch)
tree950838b8740b5b7e56a5157df8ac748b3868c920 /src/vnet/tcp
parentd28437cdf2133533c9092b881ce0e4c243d6c1f6 (diff)
session tcp: support pacer idle timeouts
Type: feature To avoid excessive bursts, pacer must be provided with an estimated rtt for the connection. That's used to compute an idle timeout, i.e., time after which the bucket is reset to 1 mtu due to inactivity. For now, idle timeout is computed as 5% of the rtt. Change-Id: Ia0b752fe7b4ad0ce97b477fb886b0133a2321541 Signed-off-by: Florin Coras <fcoras@cisco.com>
Diffstat (limited to 'src/vnet/tcp')
-rw-r--r--src/vnet/tcp/tcp.c8
-rw-r--r--src/vnet/tcp/tcp.h1
-rwxr-xr-xsrc/vnet/tcp/tcp_input.c59
-rw-r--r--src/vnet/tcp/tcp_output.c25
4 files changed, 30 insertions, 63 deletions
diff --git a/src/vnet/tcp/tcp.c b/src/vnet/tcp/tcp.c
index c0b50ce6962..86729011f8f 100644
--- a/src/vnet/tcp/tcp.c
+++ b/src/vnet/tcp/tcp.c
@@ -1396,8 +1396,11 @@ tcp_connection_tx_pacer_update (tcp_connection_t * tc)
if (!transport_connection_is_tx_paced (&tc->connection))
return;
+ f64 srtt = clib_min ((f64) tc->srtt * TCP_TICK, tc->mrtt_us);
+
transport_connection_tx_pacer_update (&tc->connection,
- tcp_cc_get_pacing_rate (tc));
+ tcp_cc_get_pacing_rate (tc),
+ srtt * CLIB_US_TIME_FREQ);
}
void
@@ -1406,7 +1409,8 @@ tcp_connection_tx_pacer_reset (tcp_connection_t * tc, u32 window,
{
f64 srtt = clib_min ((f64) tc->srtt * TCP_TICK, tc->mrtt_us);
u64 rate = (u64) window / srtt;
- transport_connection_tx_pacer_reset (&tc->connection, rate, start_bucket);
+ transport_connection_tx_pacer_reset (&tc->connection, rate, start_bucket,
+ srtt * CLIB_US_TIME_FREQ);
}
static void
diff --git a/src/vnet/tcp/tcp.h b/src/vnet/tcp/tcp.h
index 7dd88bf0a49..e9247eb86b2 100644
--- a/src/vnet/tcp/tcp.h
+++ b/src/vnet/tcp/tcp.h
@@ -394,7 +394,6 @@ typedef struct _tcp_connection
u32 prr_start; /**< snd_una when prr starts */
u32 rxt_delivered; /**< Rxt bytes delivered during current cc event */
u32 rxt_head; /**< snd_una last time we re rxted the head */
- u32 prev_dsegs_out; /**< Number of dsegs after last ack */
u32 tsecr_last_ack; /**< Timestamp echoed to us in last healthy ACK */
u32 snd_congestion; /**< snd_una_max when congestion is detected */
u32 tx_fifo_size; /**< Tx fifo size. Used to constrain cwnd */
diff --git a/src/vnet/tcp/tcp_input.c b/src/vnet/tcp/tcp_input.c
index 172dcd2ee6f..c94e5babc50 100755
--- a/src/vnet/tcp/tcp_input.c
+++ b/src/vnet/tcp/tcp_input.c
@@ -575,21 +575,6 @@ tcp_estimate_initial_rtt (tcp_connection_t * tc)
tcp_update_rto (tc);
}
-always_inline u8
-tcp_recovery_no_snd_space (tcp_connection_t * tc)
-{
- u32 space;
-
- ASSERT (tcp_in_cong_recovery (tc));
-
- if (tcp_in_recovery (tc))
- space = tcp_available_output_snd_space (tc);
- else
- space = tcp_fastrecovery_prr_snd_space (tc);
-
- return (space < tc->snd_mss + tc->burst_acked);
-}
-
/**
* Dequeue bytes for connections that have received acks in last burst
*/
@@ -610,33 +595,26 @@ tcp_handle_postponed_dequeues (tcp_worker_ctx_t * wrk)
tc = tcp_connection_get (pending_deq_acked[i], thread_index);
tc->flags &= ~TCP_CONN_DEQ_PENDING;
- if (tc->burst_acked)
- {
- /* Dequeue the newly ACKed bytes */
- session_tx_fifo_dequeue_drop (&tc->connection, tc->burst_acked);
- tcp_validate_txf_size (tc, tc->snd_una_max - tc->snd_una);
-
- if (PREDICT_FALSE (tc->flags & TCP_CONN_PSH_PENDING))
- {
- if (seq_leq (tc->psh_seq, tc->snd_una))
- tc->flags &= ~TCP_CONN_PSH_PENDING;
- }
+ if (PREDICT_FALSE (!tc->burst_acked))
+ continue;
- /* If everything has been acked, stop retransmit timer
- * otherwise update. */
- tcp_retransmit_timer_update (tc);
+ /* Dequeue the newly ACKed bytes */
+ session_tx_fifo_dequeue_drop (&tc->connection, tc->burst_acked);
+ tcp_validate_txf_size (tc, tc->snd_una_max - tc->snd_una);
- /* Update pacer based on our new cwnd estimate */
- tcp_connection_tx_pacer_update (tc);
+ if (PREDICT_FALSE (tc->flags & TCP_CONN_PSH_PENDING))
+ {
+ if (seq_leq (tc->psh_seq, tc->snd_una))
+ tc->flags &= ~TCP_CONN_PSH_PENDING;
}
- /* Reset the pacer if we've been idle, i.e., no data sent or if
- * we're in recovery and snd space constrained */
- if (tc->data_segs_out == tc->prev_dsegs_out
- || (tcp_in_cong_recovery (tc) && tcp_recovery_no_snd_space (tc)))
- transport_connection_tx_pacer_reset_bucket (&tc->connection);
+ /* If everything has been acked, stop retransmit timer
+ * otherwise update. */
+ tcp_retransmit_timer_update (tc);
+
+ /* Update pacer based on our new cwnd estimate */
+ tcp_connection_tx_pacer_update (tc);
- tc->prev_dsegs_out = tc->data_segs_out;
tc->burst_acked = 0;
}
_vec_len (wrk->pending_deq_acked) = 0;
@@ -1623,10 +1601,11 @@ process_ack:
if (tc->cfg_flags & TCP_CFG_F_RATE_SAMPLE)
tcp_bt_sample_delivery_rate (tc, &rs);
- tcp_program_dequeue (wrk, tc);
-
if (tc->bytes_acked)
- tcp_update_rtt (tc, &rs, vnet_buffer (b)->tcp.ack_number);
+ {
+ tcp_program_dequeue (wrk, tc);
+ tcp_update_rtt (tc, &rs, vnet_buffer (b)->tcp.ack_number);
+ }
TCP_EVT (TCP_EVT_ACK_RCVD, tc);
diff --git a/src/vnet/tcp/tcp_output.c b/src/vnet/tcp/tcp_output.c
index 64e3b1a584a..c06bbf19ef4 100644
--- a/src/vnet/tcp/tcp_output.c
+++ b/src/vnet/tcp/tcp_output.c
@@ -411,7 +411,7 @@ tcp_update_burst_snd_vars (tcp_connection_t * tc)
if (tc->snd_una == tc->snd_nxt)
{
tcp_cc_event (tc, TCP_CC_EVT_START_TX);
- tcp_connection_tx_pacer_reset (tc, tc->cwnd, TRANSPORT_PACER_MIN_MSS);
+ tcp_connection_tx_pacer_reset (tc, tc->cwnd, TRANSPORT_PACER_MIN_BURST);
}
}
@@ -1875,9 +1875,9 @@ static int
tcp_retransmit_sack (tcp_worker_ctx_t * wrk, tcp_connection_t * tc,
u32 burst_size)
{
- u8 snd_limited = 0, can_rescue = 0, reset_pacer = 0;
u32 n_written = 0, offset, max_bytes, n_segs = 0;
- u32 bi, max_deq, burst_bytes, sent_bytes;
+ u8 snd_limited = 0, can_rescue = 0;
+ u32 bi, max_deq, burst_bytes;
sack_scoreboard_hole_t *hole;
vlib_main_t *vm = wrk->vm;
vlib_buffer_t *b = 0;
@@ -1900,12 +1900,7 @@ tcp_retransmit_sack (tcp_worker_ctx_t * wrk, tcp_connection_t * tc,
snd_space = tcp_fastrecovery_prr_snd_space (tc);
if (snd_space < tc->snd_mss)
- {
- reset_pacer = burst_bytes > tc->snd_mss;
- goto done;
- }
-
- reset_pacer = snd_space < burst_bytes;
+ goto done;
sb = &tc->sack_sb;
@@ -2021,17 +2016,7 @@ tcp_retransmit_sack (tcp_worker_ctx_t * wrk, tcp_connection_t * tc,
done:
- if (reset_pacer)
- {
- transport_connection_tx_pacer_reset_bucket (&tc->connection);
- }
- else
- {
- sent_bytes = clib_min (n_segs * tc->snd_mss, burst_bytes);
- transport_connection_tx_pacer_update_bytes (&tc->connection,
- sent_bytes);
- }
-
+ transport_connection_tx_pacer_reset_bucket (&tc->connection, 0);
return n_segs;
}