[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <20250613102012.724405-2-ptesarik@suse.com>
Date: Fri, 13 Jun 2025 12:20:11 +0200
From: Petr Tesarik <ptesarik@...e.com>
To: "David S. Miller" <davem@...emloft.net>,
Eric Dumazet <edumazet@...gle.com>,
Neal Cardwell <ncardwell@...gle.com>,
Kuniyuki Iwashima <kuniyu@...gle.com>,
netdev@...r.kernel.org (open list:NETWORKING [TCP])
Cc: David Ahern <dsahern@...nel.org>,
Jakub Kicinski <kuba@...nel.org>,
Paolo Abeni <pabeni@...hat.com>,
linux-kernel@...r.kernel.org (open list),
Petr Tesarik <ptesarik@...e.com>
Subject: [PATCH net 1/2] tcp_metrics: set maximum cwnd from the dst entry
Always initialize tp->snd_cwnd_clamp from the corresponding dst entry.
There are two issues with setting it from the TCP metrics:
1. If the cwnd option is changed in the routing table, the new value is not
used as long as there is a cached TCP metric for the destination.
2. After evicting the cached TCP metric entry, the next connection will use
the default value (i.e. no limit). Only after this connection is
finished, a new entry is created, and this entry gets the locked value
from the routing table.
As a result, the following shenanigan is required to set a new locked cwnd
value:
- update the route (``ip route replace ... cwnd lock $value``)
- flush any existing TCP metric entry (``ip tcp_metrics flush $dest``)
- create and finish a dummy connection to the destination to create a TCP
metric entry with the new value
- *next* connection to this destination will use the new value
It does not seem to be intentional.
Fixes: 51c5d0c4b169 ("tcp: Maintain dynamic metrics in local cache.")
Signed-off-by: Petr Tesarik <ptesarik@...e.com>
---
net/ipv4/tcp_metrics.c | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/net/ipv4/tcp_metrics.c b/net/ipv4/tcp_metrics.c
index 4251670e328c8..dd8f3457bd72e 100644
--- a/net/ipv4/tcp_metrics.c
+++ b/net/ipv4/tcp_metrics.c
@@ -477,6 +477,9 @@ void tcp_init_metrics(struct sock *sk)
if (!dst)
goto reset;
+ if (dst_metric_locked(dst, RTAX_CWND))
+ tp->snd_cwnd_clamp = dst_metric(dst, RTAX_CWND);
+
rcu_read_lock();
tm = tcp_get_metrics(sk, dst, false);
if (!tm) {
@@ -484,9 +487,6 @@ void tcp_init_metrics(struct sock *sk)
goto reset;
}
- if (tcp_metric_locked(tm, TCP_METRIC_CWND))
- tp->snd_cwnd_clamp = tcp_metric_get(tm, TCP_METRIC_CWND);
-
val = READ_ONCE(net->ipv4.sysctl_tcp_no_ssthresh_metrics_save) ?
0 : tcp_metric_get(tm, TCP_METRIC_SSTHRESH);
if (val) {
--
2.49.0
Powered by blists - more mailing lists