Stop and drain the timer before Reset in sendLoop.

Before go1.23, calling Stop, and draining the channel if the timer did
not already fire, is necessary before calling Reset:
https://pkg.go.dev/time@go1.22.12#Timer.Reset

This changed in go1.23: now Reset automatically effectively drains the
channel, and calling Stop is no longer necessary.
https://pkg.go.dev/time@go1.23.9#Timer.Reset

However, the changes in go1.23 only take effect if go.mod specifies
1.23 or later. We currently specify 1.21.
https://go.dev/doc/go1.23#timer-changes

For compatibility, do the Stop/drain procedure before calling Reset. We
were already doing this for pollTimer in DNSPacketConn) sendLoop in
dnstt-client.

This change may not have any observable effect. The duration we Reset
the timer to was 0, so if there had been a stale value in the channel
because of a failure to drain it, the effect would be the same as
waiting 0 seconds. We were already calling Stop when finished with the
timer, so it would have been garbage-collectable even before go1.23.
This commit is contained in:
David Fifield
2026-04-17 16:50:58 +00:00
parent e5e873bd64
commit 2d7ce00f5b
+9 -1
View File
@@ -592,6 +592,7 @@ func sendLoop(dnsConn net.PacketConn, ttConn *turbotunnel.QueuePacketConn, ch <-
// overflow the capacity of the DNS response, we stash
// to be bundled into a future response.
timer := time.NewTimer(maxResponseDelay)
timerExpired := false
for {
var p []byte
unstash := ttConn.Unstash(rec.ClientID)
@@ -612,6 +613,7 @@ func sendLoop(dnsConn net.PacketConn, ttConn *turbotunnel.QueuePacketConn, ch <-
case p = <-unstash:
case p = <-outgoing:
case <-timer.C:
timerExpired = true
case nextRec = <-ch:
}
}
@@ -620,7 +622,11 @@ func sendLoop(dnsConn net.PacketConn, ttConn *turbotunnel.QueuePacketConn, ch <-
// only. The second and later packets must be
// immediately available or they will be omitted
// from this bundle.
if !timerExpired && !timer.Stop() {
<-timer.C
}
timer.Reset(0)
timerExpired = false
if len(p) == 0 {
// timer expired or receive on ch, we
@@ -646,7 +652,9 @@ func sendLoop(dnsConn net.PacketConn, ttConn *turbotunnel.QueuePacketConn, ch <-
binary.Write(&payload, binary.BigEndian, uint16(len(p)))
payload.Write(p)
}
timer.Stop()
if !timerExpired && !timer.Stop() {
<-timer.C
}
rec.Resp.Answer[0].Data = dns.EncodeRDataTXT(payload.Bytes())
}