Browse Source

lib: Fix panic due to closed event subscriptions on shutdown (#8079)

Gahl Saraf 3 years ago
parent
commit
cc39341eb9

+ 5 - 1
lib/model/folder_summary.go

@@ -178,7 +178,11 @@ func (c *folderSummaryService) listenForUpdates(ctx context.Context) error {
 		// This loop needs to be fast so we don't miss too many events.
 		// This loop needs to be fast so we don't miss too many events.
 
 
 		select {
 		select {
-		case ev := <-sub.C():
+		case ev, ok := <-sub.C():
+			if !ok {
+				<-ctx.Done()
+				return ctx.Err()
+			}
 			c.processUpdate(ev)
 			c.processUpdate(ev)
 		case <-ctx.Done():
 		case <-ctx.Done():
 			return ctx.Err()
 			return ctx.Err()

+ 5 - 1
lib/syncthing/auditservice.go

@@ -38,7 +38,11 @@ func (s *auditService) Serve(ctx context.Context) error {
 
 
 	for {
 	for {
 		select {
 		select {
-		case ev := <-sub.C():
+		case ev, ok := <-sub.C():
+			if !ok {
+				<-ctx.Done()
+				return ctx.Err()
+			}
 			enc.Encode(ev)
 			enc.Encode(ev)
 		case <-ctx.Done():
 		case <-ctx.Done():
 			return ctx.Err()
 			return ctx.Err()

+ 5 - 1
lib/syncthing/verboseservice.go

@@ -31,7 +31,11 @@ func (s *verboseService) Serve(ctx context.Context) error {
 	defer sub.Unsubscribe()
 	defer sub.Unsubscribe()
 	for {
 	for {
 		select {
 		select {
-		case ev := <-sub.C():
+		case ev, ok := <-sub.C():
+			if !ok {
+				<-ctx.Done()
+				return ctx.Err()
+			}
 			formatted := s.formatEvent(ev)
 			formatted := s.formatEvent(ev)
 			if formatted != "" {
 			if formatted != "" {
 				l.Verboseln(formatted)
 				l.Verboseln(formatted)

+ 4 - 2
lib/watchaggregator/aggregator.go

@@ -162,8 +162,10 @@ func (a *aggregator) mainLoop(in <-chan fs.Event, out chan<- []string, cfg confi
 		select {
 		select {
 		case event := <-in:
 		case event := <-in:
 			a.newEvent(event, inProgress)
 			a.newEvent(event, inProgress)
-		case event := <-inProgressItemSubscription.C():
-			updateInProgressSet(event, inProgress)
+		case event, ok := <-inProgressItemSubscription.C():
+			if ok {
+				updateInProgressSet(event, inProgress)
+			}
 		case <-a.notifyTimer.C:
 		case <-a.notifyTimer.C:
 			a.actOnTimer(out)
 			a.actOnTimer(out)
 		case interval := <-a.notifyTimerResetChan:
 		case interval := <-a.notifyTimerResetChan: