Don't panic on clean shutdown
This commit is contained in:
parent
b2da0120d6
commit
aa42aafe33
@ -11,6 +11,7 @@ import (
|
|||||||
"net"
|
"net"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
|
"github.com/syncthing/syncthing/lib/sync"
|
||||||
"github.com/thejerf/suture"
|
"github.com/thejerf/suture"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -44,11 +45,13 @@ func NewBroadcast(port int) *Broadcast {
|
|||||||
b.br = &broadcastReader{
|
b.br = &broadcastReader{
|
||||||
port: port,
|
port: port,
|
||||||
outbox: b.outbox,
|
outbox: b.outbox,
|
||||||
|
connMut: sync.NewMutex(),
|
||||||
}
|
}
|
||||||
b.Add(b.br)
|
b.Add(b.br)
|
||||||
b.bw = &broadcastWriter{
|
b.bw = &broadcastWriter{
|
||||||
port: port,
|
port: port,
|
||||||
inbox: b.inbox,
|
inbox: b.inbox,
|
||||||
|
connMut: sync.NewMutex(),
|
||||||
}
|
}
|
||||||
b.Add(b.bw)
|
b.Add(b.bw)
|
||||||
|
|
||||||
@ -75,6 +78,7 @@ type broadcastWriter struct {
|
|||||||
port int
|
port int
|
||||||
inbox chan []byte
|
inbox chan []byte
|
||||||
conn *net.UDPConn
|
conn *net.UDPConn
|
||||||
|
connMut sync.Mutex
|
||||||
errorHolder
|
errorHolder
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -82,14 +86,17 @@ func (w *broadcastWriter) Serve() {
|
|||||||
l.Debugln(w, "starting")
|
l.Debugln(w, "starting")
|
||||||
defer l.Debugln(w, "stopping")
|
defer l.Debugln(w, "stopping")
|
||||||
|
|
||||||
var err error
|
conn, err := net.ListenUDP("udp4", nil)
|
||||||
w.conn, err = net.ListenUDP("udp4", nil)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
l.Debugln(err)
|
l.Debugln(err)
|
||||||
w.setError(err)
|
w.setError(err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
defer w.conn.Close()
|
defer conn.Close()
|
||||||
|
|
||||||
|
w.connMut.Lock()
|
||||||
|
w.conn = conn
|
||||||
|
w.connMut.Unlock()
|
||||||
|
|
||||||
for bs := range w.inbox {
|
for bs := range w.inbox {
|
||||||
addrs, err := net.InterfaceAddrs()
|
addrs, err := net.InterfaceAddrs()
|
||||||
@ -118,9 +125,9 @@ func (w *broadcastWriter) Serve() {
|
|||||||
for _, ip := range dsts {
|
for _, ip := range dsts {
|
||||||
dst := &net.UDPAddr{IP: ip, Port: w.port}
|
dst := &net.UDPAddr{IP: ip, Port: w.port}
|
||||||
|
|
||||||
w.conn.SetWriteDeadline(time.Now().Add(time.Second))
|
conn.SetWriteDeadline(time.Now().Add(time.Second))
|
||||||
_, err := w.conn.WriteTo(bs, dst)
|
_, err := conn.WriteTo(bs, dst)
|
||||||
w.conn.SetWriteDeadline(time.Time{})
|
conn.SetWriteDeadline(time.Time{})
|
||||||
|
|
||||||
if err, ok := err.(net.Error); ok && err.Timeout() {
|
if err, ok := err.(net.Error); ok && err.Timeout() {
|
||||||
// Write timeouts should not happen. We treat it as a fatal
|
// Write timeouts should not happen. We treat it as a fatal
|
||||||
@ -154,8 +161,12 @@ func (w *broadcastWriter) Serve() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (w *broadcastWriter) Stop() {
|
func (w *broadcastWriter) Stop() {
|
||||||
|
w.connMut.Lock()
|
||||||
|
if w.conn != nil {
|
||||||
w.conn.Close()
|
w.conn.Close()
|
||||||
}
|
}
|
||||||
|
w.connMut.Unlock()
|
||||||
|
}
|
||||||
|
|
||||||
func (w *broadcastWriter) String() string {
|
func (w *broadcastWriter) String() string {
|
||||||
return fmt.Sprintf("broadcastWriter@%p", w)
|
return fmt.Sprintf("broadcastWriter@%p", w)
|
||||||
@ -165,6 +176,7 @@ type broadcastReader struct {
|
|||||||
port int
|
port int
|
||||||
outbox chan recv
|
outbox chan recv
|
||||||
conn *net.UDPConn
|
conn *net.UDPConn
|
||||||
|
connMut sync.Mutex
|
||||||
errorHolder
|
errorHolder
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -172,18 +184,21 @@ func (r *broadcastReader) Serve() {
|
|||||||
l.Debugln(r, "starting")
|
l.Debugln(r, "starting")
|
||||||
defer l.Debugln(r, "stopping")
|
defer l.Debugln(r, "stopping")
|
||||||
|
|
||||||
var err error
|
conn, err := net.ListenUDP("udp4", &net.UDPAddr{Port: r.port})
|
||||||
r.conn, err = net.ListenUDP("udp4", &net.UDPAddr{Port: r.port})
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
l.Debugln(err)
|
l.Debugln(err)
|
||||||
r.setError(err)
|
r.setError(err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
defer r.conn.Close()
|
defer conn.Close()
|
||||||
|
|
||||||
|
r.connMut.Lock()
|
||||||
|
r.conn = conn
|
||||||
|
r.connMut.Unlock()
|
||||||
|
|
||||||
bs := make([]byte, 65536)
|
bs := make([]byte, 65536)
|
||||||
for {
|
for {
|
||||||
n, addr, err := r.conn.ReadFrom(bs)
|
n, addr, err := conn.ReadFrom(bs)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
l.Debugln(err)
|
l.Debugln(err)
|
||||||
r.setError(err)
|
r.setError(err)
|
||||||
@ -206,8 +221,12 @@ func (r *broadcastReader) Serve() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (r *broadcastReader) Stop() {
|
func (r *broadcastReader) Stop() {
|
||||||
|
r.connMut.Lock()
|
||||||
|
if r.conn != nil {
|
||||||
r.conn.Close()
|
r.conn.Close()
|
||||||
}
|
}
|
||||||
|
r.connMut.Unlock()
|
||||||
|
}
|
||||||
|
|
||||||
func (r *broadcastReader) String() string {
|
func (r *broadcastReader) String() string {
|
||||||
return fmt.Sprintf("broadcastReader@%p", r)
|
return fmt.Sprintf("broadcastReader@%p", r)
|
||||||
|
|||||||
@ -75,6 +75,7 @@ func NewSvc(cfg *config.Wrapper, tlsCfg *tls.Config) *Svc {
|
|||||||
|
|
||||||
eventBc := &eventBroadcaster{
|
eventBc := &eventBroadcaster{
|
||||||
svc: svc,
|
svc: svc,
|
||||||
|
stop: make(chan struct{}),
|
||||||
}
|
}
|
||||||
|
|
||||||
svc.Add(receiver)
|
svc.Add(receiver)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user