diff options
author | Jason A. Donenfeld <Jason@zx2c4.com> | 2021-01-08 14:25:37 +0100 |
---|---|---|
committer | Jason A. Donenfeld <Jason@zx2c4.com> | 2021-01-08 14:30:04 +0100 |
commit | ea6c1cd7e6525f76041d341074a0e10b800d4e13 (patch) | |
tree | 20d488a58b5d9960a509edce216540707d286704 /device | |
parent | 3b3de758ec898e47aef609fbf16d78e97dac2000 (diff) |
device: receive: do not exit immediately on transient UDP receive errors
Some users report seeing lines like:
> Routine: receive incoming IPv4 - stopped
Popping up unexpectedly. Let's sleep and try again before failing, and
also log the error, and perhaps we'll eventually understand this
situation better in future versions.
Because we have to distinguish between the socket being closed
explicitly and whatever error this is, we bump the module to require Go
1.16.
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
Diffstat (limited to 'device')
-rw-r--r-- | device/receive.go | 22 |
1 files changed, 16 insertions, 6 deletions
diff --git a/device/receive.go b/device/receive.go index 0bd22bf..fa31a1a 100644 --- a/device/receive.go +++ b/device/receive.go @@ -8,6 +8,7 @@ package device import ( "bytes" "encoding/binary" + "errors" "net" "strconv" "sync" @@ -17,6 +18,7 @@ import ( "golang.org/x/crypto/chacha20poly1305" "golang.org/x/net/ipv4" "golang.org/x/net/ipv6" + "golang.zx2c4.com/wireguard/conn" ) @@ -117,15 +119,13 @@ func (device *Device) RoutineReceiveIncoming(IP int, bind conn.Bind) { buffer := device.GetMessageBuffer() var ( - err error - size int - endpoint conn.Endpoint + err error + size int + endpoint conn.Endpoint + deathSpiral int ) for { - - // read next datagram - switch IP { case ipv4.Version: size, endpoint, err = bind.ReceiveIPv4(buffer[:]) @@ -137,8 +137,18 @@ func (device *Device) RoutineReceiveIncoming(IP int, bind conn.Bind) { if err != nil { device.PutMessageBuffer(buffer) + if errors.Is(err, net.ErrClosed) { + return + } + device.log.Error.Printf("Failed to receive packet: %v", err) + if deathSpiral < 10 { + deathSpiral++ + time.Sleep(time.Second / 3) + continue + } return } + deathSpiral = 0 if size < MinMessageSize { continue |