From ca345ca5af50d919937673377ca4830dd23513fe Mon Sep 17 00:00:00 2001 From: Kevin Krakauer Date: Fri, 22 Nov 2024 14:08:24 -0800 Subject: [PATCH] netstack: revert SND.NXT when purging the write queue There are only 3 places we remove from the write queue. The other two are fairly self-contained and don't look suspicious. They are: - tcp.sender.maybeSendSegment - removes iff the segments are merged - tcp.sender.handleRcvdSegment - removes iff the whole segment is covered by an incoming ACK Given that the panic occurs when the write queue is empty and SND.NXT != SND.UNA, the bug likely occurs when either the writeList removes a segment or SND.NXT increments. PiperOrigin-RevId: 699283514 --- pkg/tcpip/transport/tcp/endpoint.go | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/pkg/tcpip/transport/tcp/endpoint.go b/pkg/tcpip/transport/tcp/endpoint.go index 4141f95d1..9752cd86a 100644 --- a/pkg/tcpip/transport/tcp/endpoint.go +++ b/pkg/tcpip/transport/tcp/endpoint.go @@ -1013,16 +1013,13 @@ func (e *Endpoint) purgeWriteQueue() { e.sndQueueInfo.sndQueueMu.Lock() defer e.sndQueueInfo.sndQueueMu.Unlock() e.snd.updateWriteNext(nil) - for { - s := e.snd.writeList.Front() - if s == nil { - break - } + for s := e.snd.writeList.Front(); s != nil; s = e.snd.writeList.Front() { e.snd.writeList.Remove(s) s.DecRef() } e.sndQueueInfo.SndBufUsed = 0 e.sndQueueInfo.SndClosed = true + e.snd.SndNxt = e.snd.SndUna } }