From 74733b24c971a006c03e6d413a1ee71102c499d7 Mon Sep 17 00:00:00 2001
From: "Kali Kaneko (leap communications)" <kali@leap.se>
Date: Thu, 5 Sep 2019 01:16:17 +0200
Subject: [PATCH] [bug] exit cleanly in osx

two things happen differently in osx:

- call to systray.Quit() halts the program (so if called directly, none
        of the deferred functions that we use for cleanup get to
        execute)
- systray.Run() blocks (so after loop returns, the main run.Run() function
        did not get to receive the boolean through the finishedCh channel.

proper shutdown is therefore fixed here by moving the call to
systray.Quit() to a goroutine that executes when the initialize()
function calls all the deferred functions.

we need to revisit this in case we want to break the main select loop
for a reson other than successfully terminating the program.
---
 pkg/standalone/main.go | 1 +
 pkg/systray/run.go     | 7 ++++++-
 pkg/systray/systray.go | 8 ++++++--
 3 files changed, 13 insertions(+), 3 deletions(-)

diff --git a/pkg/standalone/main.go b/pkg/standalone/main.go
index 6c267d6b..4ac57769 100644
--- a/pkg/standalone/main.go
+++ b/pkg/standalone/main.go
@@ -68,6 +68,7 @@ func (b *Bitmask) GetStatusCh() <-chan string {
 
 // Close the connection to bitmask
 func (b *Bitmask) Close() {
+	log.Printf("Close: cleanup and vpn shutdown...")
 	b.StopVPN()
 	err := b.launch.close()
 	if err != nil {
diff --git a/pkg/systray/run.go b/pkg/systray/run.go
index 6521da61..5764b367 100644
--- a/pkg/systray/run.go
+++ b/pkg/systray/run.go
@@ -27,8 +27,13 @@ func Run(conf *Config) {
 	bt := bmTray{conf: conf, waitCh: make(chan bool)}
 	finishedCh := make(chan bool)
 	go initialize(conf, &bt, finishedCh)
+	go func() {
+		<-finishedCh
+		/* in osx, systray.Quit() halts the program */
+		bt.quit()
+		os.Exit(0)
+	}()
 	bt.start()
-	<-finishedCh
 }
 
 func initialize(conf *Config, bt *bmTray, finishedCh chan bool) {
diff --git a/pkg/systray/systray.go b/pkg/systray/systray.go
index 708ee3ba..714852da 100644
--- a/pkg/systray/systray.go
+++ b/pkg/systray/systray.go
@@ -57,6 +57,10 @@ func (bt *bmTray) start() {
 	systray.Run(bt.onReady, bt.onExit)
 }
 
+func (bt *bmTray) quit() {
+	systray.Quit()
+}
+
 func (bt *bmTray) onExit() {
 	log.Println("Closing systray")
 }
@@ -146,10 +150,10 @@ func (bt *bmTray) loop(bm bitmask.Bitmask, notify *notificator, as bitmask.Autos
 			if err != nil {
 				log.Printf("Error disabling autostart: %v", err)
 			}
-			systray.Quit()
+			/* we return and leave bt.quit() to the caller */
 			return
 		case <-signalCh:
-			systray.Quit()
+			/* we return and leave bt.quit() to the caller */
 			return
 
 		case <-time.After(5 * time.Second):
-- 
GitLab