]> git.ipfire.org Git - thirdparty/wireguard-apple.git/commitdiff
macOS: Delay .deactivated status to workaround system bug
authorRoopesh Chander <roop@roopc.net>
Fri, 25 Jan 2019 12:44:48 +0000 (18:14 +0530)
committerRoopesh Chander <roop@roopc.net>
Sat, 26 Jan 2019 08:55:38 +0000 (14:25 +0530)
For some time after it's connection status becomes .disconnected,
if a tunnel gets started, it gets automatically killed by the system
after ~25 seconds.

Signed-off-by: Roopesh Chander <roop@roopc.net>
WireGuard/WireGuard/Tunnel/TunnelsManager.swift

index 7b1a9af8ebda65fb8792b77ba9613b6b9d053b3b..29d486a78a6a01a1c6489c6eb9e400ff0299bac6 100644 (file)
@@ -388,6 +388,7 @@ class TunnelContainer: NSObject {
     }
     var activationAttemptId: String?
     var activationTimer: Timer?
+    var deactivationTimer: Timer?
 
     fileprivate var tunnelProvider: NETunnelProviderManager
 
@@ -426,8 +427,22 @@ class TunnelContainer: NSObject {
     }
 
     func refreshStatus() {
-        let status = TunnelStatus(from: tunnelProvider.connection.status)
-        self.status = status
+        #if os(macOS)
+        // In macOS, we wait for a few seconds after deactivation to work around a system bug.
+        // If a tunnel gets activated in this time interval, it's stopped by the system automatically in ~25 seconds.
+        if self.status == .deactivating && tunnelProvider.connection.status == .disconnected {
+            self.deactivationTimer?.invalidate()
+            let deactivationTimer = Timer(timeInterval: 5 /* seconds */, repeats: false) { [weak self] _ in
+                guard let self = self else { return }
+                self.status = TunnelStatus(from: self.tunnelProvider.connection.status)
+                self.isActivateOnDemandEnabled = self.tunnelProvider.isOnDemandEnabled
+            }
+            self.deactivationTimer = deactivationTimer
+            RunLoop.main.add(deactivationTimer, forMode: .default)
+            return
+        }
+        #endif
+        status = TunnelStatus(from: tunnelProvider.connection.status)
         isActivateOnDemandEnabled = tunnelProvider.isOnDemandEnabled
     }