|
|
@ -63,6 +63,8 @@ type TUN struct {
|
|
|
|
// tdev is the underlying TUN device.
|
|
|
|
// tdev is the underlying TUN device.
|
|
|
|
tdev tun.Device
|
|
|
|
tdev tun.Device
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
closeOnce sync.Once
|
|
|
|
|
|
|
|
|
|
|
|
_ [4]byte // force 64-bit alignment of following field on 32-bit
|
|
|
|
_ [4]byte // force 64-bit alignment of following field on 32-bit
|
|
|
|
lastActivityAtomic int64 // unix seconds of last send or receive
|
|
|
|
lastActivityAtomic int64 // unix seconds of last send or receive
|
|
|
|
|
|
|
|
|
|
|
@ -140,15 +142,14 @@ func (t *TUN) SetDestIPActivityFuncs(m map[packet.IP]func()) {
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
func (t *TUN) Close() error {
|
|
|
|
func (t *TUN) Close() error {
|
|
|
|
select {
|
|
|
|
var err error
|
|
|
|
case <-t.closed:
|
|
|
|
t.closeOnce.Do(func() {
|
|
|
|
// continue
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
|
|
|
// Other channels need not be closed: poll will exit gracefully after this.
|
|
|
|
// Other channels need not be closed: poll will exit gracefully after this.
|
|
|
|
close(t.closed)
|
|
|
|
close(t.closed)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return t.tdev.Close()
|
|
|
|
err = t.tdev.Close()
|
|
|
|
|
|
|
|
})
|
|
|
|
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
func (t *TUN) Events() chan tun.Event {
|
|
|
|
func (t *TUN) Events() chan tun.Event {
|
|
|
|