Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

tcp: use correct counters in CA_CWR state too

As CWR is stronger than CA_Disorder state, we can miscount
SACK/Reno failure into other timeouts. Not a bad problem as
it can happen only due to ECN, FRTO detecting spurious RTO
or xmit error which are the only callers of tcp_enter_cwr.
And even then losses and RTO must still follow thereafter
to actually end up into the relevant code paths.

Compile tested.

Signed-off-by: Ilpo Järvinen <ilpo.jarvinen@helsinki.fi>
Signed-off-by: David S. Miller <davem@davemloft.net>

authored by

Ilpo Järvinen and committed by
David S. Miller
c60ce4e2 1fdb9361

+7 -6
+7 -6
net/ipv4/tcp_timer.c
··· 367 367 if (icsk->icsk_retransmits == 0) { 368 368 int mib_idx; 369 369 370 - if (icsk->icsk_ca_state == TCP_CA_Disorder) { 371 - if (tcp_is_sack(tp)) 372 - mib_idx = LINUX_MIB_TCPSACKFAILURES; 373 - else 374 - mib_idx = LINUX_MIB_TCPRENOFAILURES; 375 - } else if (icsk->icsk_ca_state == TCP_CA_Recovery) { 370 + if (icsk->icsk_ca_state == TCP_CA_Recovery) { 376 371 if (tcp_is_sack(tp)) 377 372 mib_idx = LINUX_MIB_TCPSACKRECOVERYFAIL; 378 373 else 379 374 mib_idx = LINUX_MIB_TCPRENORECOVERYFAIL; 380 375 } else if (icsk->icsk_ca_state == TCP_CA_Loss) { 381 376 mib_idx = LINUX_MIB_TCPLOSSFAILURES; 377 + } else if ((icsk->icsk_ca_state == TCP_CA_Disorder) || 378 + tp->sacked_out) { 379 + if (tcp_is_sack(tp)) 380 + mib_idx = LINUX_MIB_TCPSACKFAILURES; 381 + else 382 + mib_idx = LINUX_MIB_TCPRENOFAILURES; 382 383 } else { 383 384 mib_idx = LINUX_MIB_TCPTIMEOUTS; 384 385 }