wgengine/magicsock: fix watchdog timeout on Close when IPv6 not available

The blockForeverConn was only using its sync.Cond one side. Looks like it
was just forgotten.

Fixes #3671

Change-Id: I4ed0191982cdd0bfd451f133139428a4fa48238c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
This commit is contained in:
Brad Fitzpatrick 2022-01-06 13:19:09 -08:00 committed by Brad Fitzpatrick
parent 64c2657448
commit addda5b96f
2 changed files with 25 additions and 0 deletions

View File

@ -3121,6 +3121,7 @@ func (c *blockForeverConn) Close() error {
return net.ErrClosed
}
c.closed = true
c.cond.Broadcast()
return nil
}

View File

@ -1763,3 +1763,27 @@ func (m *peerMap) validate() error {
return nil
}
func TestBlockForeverConnUnblocks(t *testing.T) {
c := newBlockForeverConn()
done := make(chan error, 1)
go func() {
defer close(done)
_, _, err := c.ReadFrom(make([]byte, 1))
done <- err
}()
time.Sleep(50 * time.Millisecond) // give ReadFrom time to get blocked
if err := c.Close(); err != nil {
t.Fatal(err)
}
timer := time.NewTimer(5 * time.Second)
defer timer.Stop()
select {
case err := <-done:
if err != net.ErrClosed {
t.Errorf("got %v; want net.ErrClosed", err)
}
case <-timer.C:
t.Fatal("timeout")
}
}