From 0e0e93eeec8bd3f580a0250de9033648150925b2 Mon Sep 17 00:00:00 2001 From: Johan Bloemberg Date: Sun, 6 Jan 2019 19:35:12 +0100 Subject: [PATCH] Allow overriding brewPrefix and path to wg-quick. --- Misc/Uninstall.sh | 4 +++ Shared/Const.swift | 11 ++----- WireGuardStatusbar/AppDelegate.swift | 2 +- WireGuardStatusbar/Info.plist | 2 +- WireGuardStatusbar/Menu.swift | 6 ++-- WireGuardStatusbarHelper/Helper.swift | 39 +++++++++++++++++++++++- WireGuardStatusbarHelper/Info.plist | 4 +-- WireGuardStatusbarHelper/WireGuard.swift | 10 ++++-- 8 files changed, 59 insertions(+), 19 deletions(-) diff --git a/Misc/Uninstall.sh b/Misc/Uninstall.sh index 860c7cb..e93da6b 100755 --- a/Misc/Uninstall.sh +++ b/Misc/Uninstall.sh @@ -17,4 +17,8 @@ sudo rm /Library/PrivilegedHelperTools/WireGuardStatusbarHelper # Also remove application sudo rm -r /Applications/WireGuardStatusbar.app/ +# And all settings +defaults delete WireGuardStatusbar +sudo defaults delete WireGuardStatusbarHelper + exit 0 diff --git a/Shared/Const.swift b/Shared/Const.swift index 6cc613d..976a64f 100644 --- a/Shared/Const.swift +++ b/Shared/Const.swift @@ -2,17 +2,10 @@ import Foundation -let brewPrefix = "/usr/local" +let defaultBrewPrefix = "/usr/local" let runPath = "/var/run/wireguard" -// paths to search for tunnel configurations, ordered by wg-quick's preferences -let configPaths = [ - "/etc/wireguard", - "\(brewPrefix)/etc/wireguard", -] - -let wireguardBin = "\(brewPrefix)/bin/wg" -let wgquickBin = "\(brewPrefix)/bin/wg-quick" +let wireguardBinPath = "\(defaultBrewPrefix)/bin/wg" let installInstructions = """ Currently this Application does not come with WireGuard binaries. \ diff --git a/WireGuardStatusbar/AppDelegate.swift b/WireGuardStatusbar/AppDelegate.swift index 50576fd..bbc3c5c 100644 --- a/WireGuardStatusbar/AppDelegate.swift +++ b/WireGuardStatusbar/AppDelegate.swift @@ -30,7 +30,7 @@ class AppDelegate: NSObject, NSApplicationDelegate, AppProtocol { var tunnels = Tunnels() // To check wg binary is enough to also guarentee wg-quick and wireguard-go when installed with Homebrew - var wireguardInstalled = FileManager.default.fileExists(atPath: wireguardBin) + var wireguardInstalled = FileManager.default.fileExists(atPath: wireguardBinPath) let statusItem = NSStatusBar.system.statusItem(withLength: NSStatusItem.squareLength) diff --git a/WireGuardStatusbar/Info.plist b/WireGuardStatusbar/Info.plist index d40565d..cb1d0fb 100644 --- a/WireGuardStatusbar/Info.plist +++ b/WireGuardStatusbar/Info.plist @@ -17,7 +17,7 @@ CFBundlePackageType APPL CFBundleShortVersionString - 1.15 + 1.16 CFBundleVersion 1 LSApplicationCategoryType diff --git a/WireGuardStatusbar/Menu.swift b/WireGuardStatusbar/Menu.swift index 391419a..5ba029e 100644 --- a/WireGuardStatusbar/Menu.swift +++ b/WireGuardStatusbar/Menu.swift @@ -20,11 +20,11 @@ func buildMenu(tunnels: Tunnels, allTunnelDetails: Bool = false, connectedTunnel // WireGaurd missing is a big problem, user should fix this first. TODO, include WireGuard with the App if showInstallInstructions { - NSLog("WireGuard binary not found at '\(wireguardBin)'") - statusMenu.insertItem(NSMenuItem(title: "WireGuard not installed! Click here for instructions", + NSLog("WireGuard binary was not found at '\(wireguardBinPath)'") + statusMenu.insertItem(NSMenuItem(title: "WireGuard not installed! Click here for instructions...", action: #selector(AppDelegate.showInstallInstructions(_:)), keyEquivalent: ""), at: 0) - return statusMenu + statusMenu.insertItem(NSMenuItem.separator(), at: 0) } if tunnels.isEmpty { diff --git a/WireGuardStatusbarHelper/Helper.swift b/WireGuardStatusbarHelper/Helper.swift index 3546cd8..2049792 100644 --- a/WireGuardStatusbarHelper/Helper.swift +++ b/WireGuardStatusbarHelper/Helper.swift @@ -7,6 +7,43 @@ class Helper: NSObject, HelperProtocol, SKQueueDelegate { private var queue: SKQueue? + // prefix path for etc/wireguard, bin/wg, bin/wireguard-go and bin/bash (bash 4) + // can be overridden by the user via root defaults to allow custom location for Homebrew + private var brewPrefix: String + // path to wg-quick, can be overriden by the user via root defaults + private var wgquickBinPath: String + // NOTICE: the root defaults override feature is a half implemented feature + // the GUI App will not be aware of these settings and might falsely warn that WireGuard + // is not installed. This warning can be ignored. + // Example, to set defaults as root for wgquickBinPath run: + // sudo defaults write WireGuardStatusbarHelper wgquickBinPath /opt/local/bin/wg-quick + + // paths to search for tunnel configurations, ordered by wg-quick's preferences + private var configPaths: [String] + + // read preferences set via root defaults + override init() { + if let brewPrefix = CFPreferencesCopyAppValue("brewPrefix" as CFString, + HelperConstants.machServiceName as CFString) as? String { + NSLog("Overriding 'brewPrefix' with: \(brewPrefix)") + self.brewPrefix = brewPrefix + } else { + brewPrefix = defaultBrewPrefix + } + configPaths = [ + "/etc/wireguard", + "\(brewPrefix)/etc/wireguard", + ] + + if let wgquickBinPath = CFPreferencesCopyAppValue("wgquickBinPath" as CFString, + HelperConstants.machServiceName as CFString) as? String { + NSLog("Overriding 'wgquickBinPath' with: \(wgquickBinPath)") + self.wgquickBinPath = wgquickBinPath + } else { + wgquickBinPath = "\(brewPrefix)/bin/wg-quick" + } + } + // Starts the helper daemon func run() { // create XPC to App @@ -118,7 +155,7 @@ class Helper: NSObject, HelperProtocol, SKQueueDelegate { } NSLog("Set tunnel \(tunnelName) \(state)") - reply(wgQuick([state, tunnelName])) + reply(wgQuick([state, tunnelName], brewPrefix: brewPrefix, wgquickBinPath: wgquickBinPath)) // because /var/run/wireguard might not exist and can be created after upping the first tunnel // run the registration of watchdirectories again and force trigger a state update to the app diff --git a/WireGuardStatusbarHelper/Info.plist b/WireGuardStatusbarHelper/Info.plist index 6aebdf1..48e198d 100644 --- a/WireGuardStatusbarHelper/Info.plist +++ b/WireGuardStatusbarHelper/Info.plist @@ -9,9 +9,9 @@ CFBundleName WireGuardStatusbarHelper CFBundleShortVersionString - 1.15 + 1.16 CFBundleVersion - 1.0.13 + 1.0.14 SMAuthorizedClients anchor apple generic and identifier "WireGuardStatusbar" diff --git a/WireGuardStatusbarHelper/WireGuard.swift b/WireGuardStatusbarHelper/WireGuard.swift index d041899..e15eefd 100644 --- a/WireGuardStatusbarHelper/WireGuard.swift +++ b/WireGuardStatusbarHelper/WireGuard.swift @@ -10,9 +10,15 @@ func validateTunnelName(tunnelName: String) -> Bool { range: NSRange(location: 0, length: tunnelName.count)) != nil } -func wgQuick(_ arguments: [String]) -> NSNumber { +func wgQuick(_ arguments: [String], brewPrefix: String, wgquickBinPath: String) -> NSNumber { + // prevent passing an invalid path or else task.launch will result in a fatal NSInvalidArgumentException + guard FileManager.default.fileExists(atPath: wgquickBinPath) else { + NSLog("Path '\(wgquickBinPath)' for 'wg-quick' binary is invalid!") + return 1 + } + let task = Process() - task.launchPath = wgquickBin + task.launchPath = wgquickBinPath task.arguments = arguments // Add brew bin to path as wg-quick requires Bash 4 instead of macOS provided Bash 3 task.environment = ["PATH": "\(brewPrefix)/bin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin"]