diff --git a/OpenVPN Adapter Tests/OpenVPNAdapterTests.swift b/OpenVPN Adapter Tests/OpenVPNAdapterTests.swift index e66be6f..8bcebb3 100644 --- a/OpenVPN Adapter Tests/OpenVPNAdapterTests.swift +++ b/OpenVPN Adapter Tests/OpenVPNAdapterTests.swift @@ -109,11 +109,11 @@ class OpenVPNAdapterTests: XCTestCase { extension OpenVPNAdapterTests: OpenVPNAdapterDelegate { - func configureTunnel(settings: NEPacketTunnelNetworkSettings, callback: @escaping (OpenVPNAdapterPacketFlow?) -> Void) { - callback(self) + func openVPNAdapter(_ openVPNAdapter: OpenVPNAdapter, configureTunnelWithNetworkSettings networkSettings: NEPacketTunnelNetworkSettings, completionHandler: @escaping (NEPacketTunnelFlow?) -> Void) { + completionHandler(NEPacketTunnelFlow()) } - func handle(event: OpenVPNAdapterEvent, message: String?) { + func openVPNAdapter(_ openVPNAdapter: OpenVPNAdapter, handleEvent event: OpenVPNAdapterEvent, message: String?) { switch event { case .connected: guard let connectionExpectation = expectations[.connection] else { return } @@ -127,23 +127,15 @@ extension OpenVPNAdapterTests: OpenVPNAdapterDelegate { } } - func handle(error: Error) { + func openVPNAdapter(_ openVPNAdapter: OpenVPNAdapter, handleError error: Error) { if let connectionExpectation = expectations[.connection] { XCTFail("Failed to establish conection. \(error.localizedDescription)") connectionExpectation.fulfill() } } - func handle(logMessage: String) { - print("\(logMessage)") + func openVPNAdapter(_ openVPNAdapter: OpenVPNAdapter, handleLogMessage logMessage: String) { + print(logMessage) } } - -extension OpenVPNAdapterTests: OpenVPNAdapterPacketFlow { - - func readPackets(completionHandler: @escaping ([Data], [NSNumber]) -> Void) { } - - func writePackets(_ packets: [Data], withProtocols protocols: [NSNumber]) -> Bool { return true } - -} diff --git a/OpenVPN Adapter.xcodeproj/project.pbxproj b/OpenVPN Adapter.xcodeproj/project.pbxproj index 86187e9..d37ec18 100644 --- a/OpenVPN Adapter.xcodeproj/project.pbxproj +++ b/OpenVPN Adapter.xcodeproj/project.pbxproj @@ -99,11 +99,7 @@ C9BB47601E71663A00F3F98C /* Umbrella-Header.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB475E1E71663A00F3F98C /* Umbrella-Header.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9BB47711E7171A100F3F98C /* OpenVPNError.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB476F1E7171A100F3F98C /* OpenVPNError.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9BB47721E7171A100F3F98C /* OpenVPNAdapterEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB47701E7171A100F3F98C /* OpenVPNAdapterEvent.h */; settings = {ATTRIBUTES = (Public, ); }; }; - C9BB47791E7171ED00F3F98C /* OpenVPNClient.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB47771E7171ED00F3F98C /* OpenVPNClient.h */; }; - C9BB477A1E7171ED00F3F98C /* OpenVPNClient.mm in Sources */ = {isa = PBXBuildFile; fileRef = C9BB47781E7171ED00F3F98C /* OpenVPNClient.mm */; }; C9BB477F1E7173C700F3F98C /* OpenVPNAdapter.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB477B1E7173C700F3F98C /* OpenVPNAdapter.h */; settings = {ATTRIBUTES = (Public, ); }; }; - C9BB47801E7173C700F3F98C /* OpenVPNAdapter+Internal.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB477C1E7173C700F3F98C /* OpenVPNAdapter+Internal.h */; }; - C9BB47811E7173C700F3F98C /* OpenVPNAdapter+Public.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB477D1E7173C700F3F98C /* OpenVPNAdapter+Public.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9BB47821E7173C700F3F98C /* OpenVPNAdapter.mm in Sources */ = {isa = PBXBuildFile; fileRef = C9BB477E1E7173C700F3F98C /* OpenVPNAdapter.mm */; }; C9BB47911E71821A00F3F98C /* OpenVPNAdapterTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9BB47901E71821A00F3F98C /* OpenVPNAdapterTests.swift */; }; C9BB47931E71821A00F3F98C /* OpenVPNAdapter.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C9BB475C1E71663A00F3F98C /* OpenVPNAdapter.framework */; }; @@ -114,10 +110,6 @@ C9BCE25B1EB3C0D9009D6AC1 /* OpenVPNSessionToken.mm in Sources */ = {isa = PBXBuildFile; fileRef = C9BCE2571EB3C0D9009D6AC1 /* OpenVPNSessionToken.mm */; }; C9BCE25E1EB3C201009D6AC1 /* OpenVPNSessionToken+Internal.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BCE25C1EB3C201009D6AC1 /* OpenVPNSessionToken+Internal.h */; }; C9BCE25F1EB3C201009D6AC1 /* OpenVPNSessionToken+Internal.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BCE25C1EB3C201009D6AC1 /* OpenVPNSessionToken+Internal.h */; }; - C9BDB1351EBCC3B900C204FF /* OpenVPNTunnelSettings.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BDB1331EBCC3B900C204FF /* OpenVPNTunnelSettings.h */; }; - C9BDB1361EBCC3B900C204FF /* OpenVPNTunnelSettings.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BDB1331EBCC3B900C204FF /* OpenVPNTunnelSettings.h */; }; - C9BDB1371EBCC3B900C204FF /* OpenVPNTunnelSettings.m in Sources */ = {isa = PBXBuildFile; fileRef = C9BDB1341EBCC3B900C204FF /* OpenVPNTunnelSettings.m */; }; - C9BDB1381EBCC3B900C204FF /* OpenVPNTunnelSettings.m in Sources */ = {isa = PBXBuildFile; fileRef = C9BDB1341EBCC3B900C204FF /* OpenVPNTunnelSettings.m */; }; C9CA4DD31F602F7B00C4F184 /* OpenVPNCertificate.h in Headers */ = {isa = PBXBuildFile; fileRef = C9CA4DD11F602F7B00C4F184 /* OpenVPNCertificate.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9CA4DD41F602F7B00C4F184 /* OpenVPNCertificate.h in Headers */ = {isa = PBXBuildFile; fileRef = C9CA4DD11F602F7B00C4F184 /* OpenVPNCertificate.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9CA4DD51F602F7B00C4F184 /* OpenVPNCertificate.m in Sources */ = {isa = PBXBuildFile; fileRef = C9CA4DD21F602F7B00C4F184 /* OpenVPNCertificate.m */; }; @@ -125,17 +117,13 @@ C9CA4DE11F603A5300C4F184 /* OpenVPNCertificateTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9CA4DE01F603A5300C4F184 /* OpenVPNCertificateTests.swift */; }; C9CA4DE21F603A5300C4F184 /* OpenVPNCertificateTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9CA4DE01F603A5300C4F184 /* OpenVPNCertificateTests.swift */; }; C9D2ABDB1EA20F99007EDF9D /* OpenVPNAdapter.mm in Sources */ = {isa = PBXBuildFile; fileRef = C9BB477E1E7173C700F3F98C /* OpenVPNAdapter.mm */; }; - C9D2ABDC1EA20F99007EDF9D /* OpenVPNClient.mm in Sources */ = {isa = PBXBuildFile; fileRef = C9BB47781E7171ED00F3F98C /* OpenVPNClient.mm */; }; C9D2ABDE1EA20F99007EDF9D /* ovpncli.cpp in Sources */ = {isa = PBXBuildFile; fileRef = C9FD92191E9A667600374FC4 /* ovpncli.cpp */; }; C9D2ABE01EA20F99007EDF9D /* NetworkExtension.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C912BB241E7C3339002B9414 /* NetworkExtension.framework */; }; C9D2ABE11EA20F99007EDF9D /* SystemConfiguration.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C90BAD301E73FF6C00DEFB32 /* SystemConfiguration.framework */; }; - C9D2ABE31EA20F99007EDF9D /* OpenVPNClient.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB47771E7171ED00F3F98C /* OpenVPNClient.h */; }; C9D2ABE41EA20F99007EDF9D /* OpenVPNAdapterEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB47701E7171A100F3F98C /* OpenVPNAdapterEvent.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9D2ABE51EA20F99007EDF9D /* OpenVPNAdapter.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB477B1E7173C700F3F98C /* OpenVPNAdapter.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9D2ABE61EA20F99007EDF9D /* Umbrella-Header.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB475E1E71663A00F3F98C /* Umbrella-Header.h */; settings = {ATTRIBUTES = (Public, ); }; }; - C9D2ABE71EA20F99007EDF9D /* OpenVPNAdapter+Public.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB477D1E7173C700F3F98C /* OpenVPNAdapter+Public.h */; settings = {ATTRIBUTES = (Public, ); }; }; C9D2ABE81EA20F99007EDF9D /* OpenVPNError.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB476F1E7171A100F3F98C /* OpenVPNError.h */; settings = {ATTRIBUTES = (Public, ); }; }; - C9D2ABE91EA20F99007EDF9D /* OpenVPNAdapter+Internal.h in Headers */ = {isa = PBXBuildFile; fileRef = C9BB477C1E7173C700F3F98C /* OpenVPNAdapter+Internal.h */; }; C9D2ABEA1EA20F99007EDF9D /* ovpncli.hpp in Headers */ = {isa = PBXBuildFile; fileRef = C9FD92181E9A667600374FC4 /* ovpncli.hpp */; }; C9D2ABF61EA212A3007EDF9D /* OpenVPNAdapterTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9BB47901E71821A00F3F98C /* OpenVPNAdapterTests.swift */; }; C9D2ABF71EA212A3007EDF9D /* Bundle.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9BB47A11E7183DB00F3F98C /* Bundle.swift */; }; @@ -223,11 +211,7 @@ C9BB475E1E71663A00F3F98C /* Umbrella-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Umbrella-Header.h"; sourceTree = ""; }; C9BB476F1E7171A100F3F98C /* OpenVPNError.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; lineEnding = 0; path = OpenVPNError.h; sourceTree = ""; xcLanguageSpecificationIdentifier = xcode.lang.objcpp; }; C9BB47701E7171A100F3F98C /* OpenVPNAdapterEvent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OpenVPNAdapterEvent.h; sourceTree = ""; }; - C9BB47771E7171ED00F3F98C /* OpenVPNClient.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OpenVPNClient.h; sourceTree = ""; }; - C9BB47781E7171ED00F3F98C /* OpenVPNClient.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = OpenVPNClient.mm; sourceTree = ""; }; C9BB477B1E7173C700F3F98C /* OpenVPNAdapter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OpenVPNAdapter.h; sourceTree = ""; }; - C9BB477C1E7173C700F3F98C /* OpenVPNAdapter+Internal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "OpenVPNAdapter+Internal.h"; sourceTree = ""; }; - C9BB477D1E7173C700F3F98C /* OpenVPNAdapter+Public.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "OpenVPNAdapter+Public.h"; sourceTree = ""; }; C9BB477E1E7173C700F3F98C /* OpenVPNAdapter.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; lineEnding = 0; path = OpenVPNAdapter.mm; sourceTree = ""; xcLanguageSpecificationIdentifier = xcode.lang.objcpp; }; C9BB478E1E71821A00F3F98C /* OpenVPNAdapterTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = OpenVPNAdapterTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; C9BB47901E71821A00F3F98C /* OpenVPNAdapterTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = OpenVPNAdapterTests.swift; sourceTree = ""; }; @@ -235,8 +219,6 @@ C9BCE2561EB3C0D9009D6AC1 /* OpenVPNSessionToken.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OpenVPNSessionToken.h; sourceTree = ""; }; C9BCE2571EB3C0D9009D6AC1 /* OpenVPNSessionToken.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = OpenVPNSessionToken.mm; sourceTree = ""; }; C9BCE25C1EB3C201009D6AC1 /* OpenVPNSessionToken+Internal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "OpenVPNSessionToken+Internal.h"; sourceTree = ""; }; - C9BDB1331EBCC3B900C204FF /* OpenVPNTunnelSettings.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OpenVPNTunnelSettings.h; sourceTree = ""; }; - C9BDB1341EBCC3B900C204FF /* OpenVPNTunnelSettings.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = OpenVPNTunnelSettings.m; sourceTree = ""; }; C9CA4DD11F602F7B00C4F184 /* OpenVPNCertificate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = OpenVPNCertificate.h; sourceTree = ""; }; C9CA4DD21F602F7B00C4F184 /* OpenVPNCertificate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = OpenVPNCertificate.m; sourceTree = ""; }; C9CA4DE01F603A5300C4F184 /* OpenVPNCertificateTests.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = OpenVPNCertificateTests.swift; sourceTree = ""; }; @@ -334,8 +316,6 @@ C9235AC41EB24F0100C7D303 /* Configuration */ = { isa = PBXGroup; children = ( - C9BDB1331EBCC3B900C204FF /* OpenVPNTunnelSettings.h */, - C9BDB1341EBCC3B900C204FF /* OpenVPNTunnelSettings.m */, C98467A41EAA5B7700272A9A /* OpenVPNConfiguration.h */, C98467AA1EAA5BB500272A9A /* OpenVPNConfiguration+Internal.h */, C98467A51EAA5B7700272A9A /* OpenVPNConfiguration.mm */, @@ -434,11 +414,7 @@ C9BB47671E7169F000F3F98C /* Adapter */ = { isa = PBXGroup; children = ( - C9BB47771E7171ED00F3F98C /* OpenVPNClient.h */, - C9BB47781E7171ED00F3F98C /* OpenVPNClient.mm */, C9BB477B1E7173C700F3F98C /* OpenVPNAdapter.h */, - C9BB477C1E7173C700F3F98C /* OpenVPNAdapter+Internal.h */, - C9BB477D1E7173C700F3F98C /* OpenVPNAdapter+Public.h */, C9BB477E1E7173C700F3F98C /* OpenVPNAdapter.mm */, ); name = Adapter; @@ -556,7 +532,6 @@ buildActionMask = 2147483647; files = ( C9CA4DD31F602F7B00C4F184 /* OpenVPNCertificate.h in Headers */, - C9BB47791E7171ED00F3F98C /* OpenVPNClient.h in Headers */, C9657A3A1EB0BAAB00EFF210 /* OpenVPNInterfaceStats+Internal.h in Headers */, C9354F451F1E4A4500F4C935 /* OpenVPNReachabilityStatus.h in Headers */, C9BCE25E1EB3C201009D6AC1 /* OpenVPNSessionToken+Internal.h in Headers */, @@ -567,7 +542,6 @@ C9657A571EB0CDFB00EFF210 /* OpenVPNProperties+Internal.h in Headers */, C9BCE2581EB3C0D9009D6AC1 /* OpenVPNSessionToken.h in Headers */, C9657A341EB0BA3900EFF210 /* OpenVPNInterfaceStats.h in Headers */, - C9BDB1351EBCC3B900C204FF /* OpenVPNTunnelSettings.h in Headers */, C9657A401EB0CAC200EFF210 /* OpenVPNServerEntry.h in Headers */, C98467AB1EAA5BE100272A9A /* OpenVPNConfiguration+Internal.h in Headers */, C98467A61EAA5B7700272A9A /* OpenVPNConfiguration.h in Headers */, @@ -579,10 +553,8 @@ C9B7955E1F1D16AA00CF35FE /* OpenVPNReachability.h in Headers */, C915F1F41F612F3300B3DF23 /* OpenVPNPrivateKey.h in Headers */, C9657A171EB0A7F800EFF210 /* OpenVPNConnectionInfo.h in Headers */, - C9BB47811E7173C700F3F98C /* OpenVPNAdapter+Public.h in Headers */, C9BB47711E7171A100F3F98C /* OpenVPNError.h in Headers */, C9B795641F1D182500CF35FE /* OpenVPNReachabilityTracker.h in Headers */, - C9BB47801E7173C700F3F98C /* OpenVPNAdapter+Internal.h in Headers */, C9E4401D1F6086A1001D7C41 /* NSError+Message.h in Headers */, C9657A611EB0D64E00EFF210 /* OpenVPNIPv6Preference.h in Headers */, C9657A671EB0D73200EFF210 /* OpenVPNMinTLSVersion.h in Headers */, @@ -601,7 +573,6 @@ buildActionMask = 2147483647; files = ( C9CA4DD41F602F7B00C4F184 /* OpenVPNCertificate.h in Headers */, - C9D2ABE31EA20F99007EDF9D /* OpenVPNClient.h in Headers */, C9657A3B1EB0BAAB00EFF210 /* OpenVPNInterfaceStats+Internal.h in Headers */, C9354F461F1E4A4600F4C935 /* OpenVPNReachabilityStatus.h in Headers */, C9BCE25F1EB3C201009D6AC1 /* OpenVPNSessionToken+Internal.h in Headers */, @@ -612,7 +583,6 @@ C9657A561EB0CDFA00EFF210 /* OpenVPNProperties+Internal.h in Headers */, C9BCE2591EB3C0D9009D6AC1 /* OpenVPNSessionToken.h in Headers */, C9657A351EB0BA3900EFF210 /* OpenVPNInterfaceStats.h in Headers */, - C9BDB1361EBCC3B900C204FF /* OpenVPNTunnelSettings.h in Headers */, C9657A411EB0CAC200EFF210 /* OpenVPNServerEntry.h in Headers */, C98467AC1EAA5BE200272A9A /* OpenVPNConfiguration+Internal.h in Headers */, C98467A71EAA5B7700272A9A /* OpenVPNConfiguration.h in Headers */, @@ -624,10 +594,8 @@ C9B7955F1F1D16AA00CF35FE /* OpenVPNReachability.h in Headers */, C915F1F51F612F3300B3DF23 /* OpenVPNPrivateKey.h in Headers */, C9657A181EB0A7F800EFF210 /* OpenVPNConnectionInfo.h in Headers */, - C9D2ABE71EA20F99007EDF9D /* OpenVPNAdapter+Public.h in Headers */, C9D2ABE81EA20F99007EDF9D /* OpenVPNError.h in Headers */, C9B795651F1D182500CF35FE /* OpenVPNReachabilityTracker.h in Headers */, - C9D2ABE91EA20F99007EDF9D /* OpenVPNAdapter+Internal.h in Headers */, C9E4401E1F6086A1001D7C41 /* NSError+Message.h in Headers */, C9657A621EB0D64E00EFF210 /* OpenVPNIPv6Preference.h in Headers */, C9657A681EB0D73200EFF210 /* OpenVPNMinTLSVersion.h in Headers */, @@ -848,13 +816,11 @@ C9BB47821E7173C700F3F98C /* OpenVPNAdapter.mm in Sources */, C98467A81EAA5B7700272A9A /* OpenVPNConfiguration.mm in Sources */, C9E4401F1F6086A1001D7C41 /* NSError+Message.m in Sources */, - C9BDB1371EBCC3B900C204FF /* OpenVPNTunnelSettings.m in Sources */, C9657A311EB0B7A900EFF210 /* OpenVPNTransportStats.mm in Sources */, C9B795661F1D182500CF35FE /* OpenVPNReachabilityTracker.mm in Sources */, C9657A581EB0CE1300EFF210 /* OpenVPNProperties.mm in Sources */, C9CA4DD51F602F7B00C4F184 /* OpenVPNCertificate.m in Sources */, C915F1F61F612F3300B3DF23 /* OpenVPNPrivateKey.m in Sources */, - C9BB477A1E7171ED00F3F98C /* OpenVPNClient.mm in Sources */, C9FD921B1E9A667600374FC4 /* ovpncli.cpp in Sources */, C9657A361EB0BA3900EFF210 /* OpenVPNInterfaceStats.mm in Sources */, C9657A211EB0ACAE00EFF210 /* OpenVPNConnectionInfo.mm in Sources */, @@ -886,13 +852,11 @@ C9D2ABDB1EA20F99007EDF9D /* OpenVPNAdapter.mm in Sources */, C98467A91EAA5B7700272A9A /* OpenVPNConfiguration.mm in Sources */, C9E440201F6086A1001D7C41 /* NSError+Message.m in Sources */, - C9BDB1381EBCC3B900C204FF /* OpenVPNTunnelSettings.m in Sources */, C9657A301EB0B7A600EFF210 /* OpenVPNTransportStats.mm in Sources */, C9B795671F1D182500CF35FE /* OpenVPNReachabilityTracker.mm in Sources */, C9657A591EB0CE1400EFF210 /* OpenVPNProperties.mm in Sources */, C9CA4DD61F602F7B00C4F184 /* OpenVPNCertificate.m in Sources */, C915F1F71F612F3300B3DF23 /* OpenVPNPrivateKey.m in Sources */, - C9D2ABDC1EA20F99007EDF9D /* OpenVPNClient.mm in Sources */, C9D2ABDE1EA20F99007EDF9D /* ovpncli.cpp in Sources */, C9657A371EB0BA3900EFF210 /* OpenVPNInterfaceStats.mm in Sources */, C9657A221EB0ACAE00EFF210 /* OpenVPNConnectionInfo.mm in Sources */, diff --git a/OpenVPN Adapter/OpenVPNAdapter+Internal.h b/OpenVPN Adapter/OpenVPNAdapter+Internal.h deleted file mode 100644 index 6f82c9d..0000000 --- a/OpenVPN Adapter/OpenVPNAdapter+Internal.h +++ /dev/null @@ -1,40 +0,0 @@ -// -// OpenVPNAdapter+Internal.h -// OpenVPN Adapter -// -// Created by Sergey Abramchuk on 11.02.17. -// -// - -#import - -#import "OpenVPNAdapter.h" - -using namespace openvpn; - -@interface OpenVPNAdapter (Internal) - -- (BOOL)configureSockets; - -- (BOOL)setRemoteAddress:(NSString *)address isIPv6:(BOOL)isIPv6; - -- (BOOL)addLocalAddress:(NSString *)address prefixLength:(NSNumber *)prefixLength gateway:(NSString *)gateway isIPv6:(BOOL)isIPv6; - -- (BOOL)defaultGatewayRerouteIPv4:(BOOL)rerouteIPv4 rerouteIPv6:(BOOL)rerouteIPv6; -- (BOOL)addRoute:(NSString *)route prefixLength:(NSNumber *)prefixLength isIPv6:(BOOL)isIPv6; -- (BOOL)excludeRoute:(NSString *)route prefixLength:(NSNumber *)prefixLength isIPv6:(BOOL)isIPv6; - -- (BOOL)addDNSAddress:(NSString *)address isIPv6:(BOOL)isIPv6; -- (BOOL)addSearchDomain:(NSString *)domain; - -- (BOOL)setMTU:(NSNumber *)mtu; - -- (CFSocketNativeHandle)establishTunnel; -- (void)teardownTunnel:(BOOL)disconnect; - -- (void)handleEvent:(const ClientAPI::Event *)event; -- (void)handleLog:(const ClientAPI::LogInfo *)log; - -- (void)tick; - -@end diff --git a/OpenVPN Adapter/OpenVPNAdapter+Public.h b/OpenVPN Adapter/OpenVPNAdapter+Public.h deleted file mode 100644 index 13797b0..0000000 --- a/OpenVPN Adapter/OpenVPNAdapter+Public.h +++ /dev/null @@ -1,191 +0,0 @@ -// -// OpenVPNAdapter+Public.h -// OpenVPN Adapter -// -// Created by Sergey Abramchuk on 11.02.17. -// -// - -#import "OpenVPNAdapterEvent.h" -#import "OpenVPNAdapter.h" - -@class OpenVPNConfiguration; -@class OpenVPNProperties; -@class OpenVPNCredentials; -@class OpenVPNConnectionInfo; -@class OpenVPNSessionToken; -@class OpenVPNTransportStats; -@class OpenVPNInterfaceStats; -@class NEPacketTunnelNetworkSettings; - -// TODO: Add documentation to properties and methods - -/** - <#Description#> - */ -@protocol OpenVPNAdapterPacketFlow - -/** - <#Description#> - - @param completionHandler <#completionHandler description#> - */ -- (void)readPacketsWithCompletionHandler:(nonnull void (^)(NSArray * _Nonnull packets, NSArray * _Nonnull protocols))completionHandler; - -/** - <#Description#> - - @param packets <#packets description#> - @param protocols <#protocols description#> - @return <#return value description#> - */ -- (BOOL)writePackets:(nonnull NSArray *)packets withProtocols:(nonnull NSArray *)protocols; - -@end - -/** - <#Description#> - */ -@protocol OpenVPNAdapterDelegate - -/** - <#Description#> - - @param settings <#settings description#> - @param callback <#callback description#> - */ -- (void)configureTunnelWithSettings:(nonnull NEPacketTunnelNetworkSettings *)settings - callback:(nonnull void (^)(id _Nullable flow))callback -NS_SWIFT_NAME(configureTunnel(settings:callback:)); - -/** - <#Description#> - - @param event <#event description#> - @param message <#message description#> - */ -- (void)handleEvent:(OpenVPNAdapterEvent)event - message:(nullable NSString *)message -NS_SWIFT_NAME(handle(event:message:)); - -/** - <#Description#> - - @param error <#error description#> - */ -- (void)handleError:(nonnull NSError *)error -NS_SWIFT_NAME(handle(error:)); - -@optional - -/** - <#Description#> - - @param logMessage <#logMessage description#> - */ -- (void)handleLog:(nonnull NSString *)logMessage -NS_SWIFT_NAME(handle(logMessage:)); - -/** - <#Description#> - */ -- (void)tick; - -@end - -/** - <#Description#> - */ -@interface OpenVPNAdapter (Public) - -/** - Return core copyright - */ -@property (class, nonnull, readonly, nonatomic) NSString *copyright; - -/** - Return platform description - */ -@property (class, nonnull, readonly, nonatomic) NSString *platform; - -/** - <#Description#> - */ -@property (weak, nonatomic, null_unspecified) id delegate; - -/** - Return information about the most recent connection. Will be available - after an event of type "OpenVPNAdapterEventConnected, otherwise return nil. - */ -@property (nullable, readonly, nonatomic) OpenVPNConnectionInfo *connectionInfo; - -/** - Return current session token or nil if session token is unavailable - */ -@property (nullable, readonly, nonatomic) OpenVPNSessionToken *sessionToken; - -/** - Return transport stats - */ -@property (nonnull, readonly, nonatomic) OpenVPNTransportStats *transportStats; - -/** - Return tun stats - */ -@property (nonnull, readonly, nonatomic) OpenVPNInterfaceStats *interfaceStats; - -/** - <#Description#> - - @param configuration <#configuration description#> - @param error <#error description#> - @return <#return value description#> - */ -- (nullable OpenVPNProperties *)applyConfiguration:(nonnull OpenVPNConfiguration *)configuration - error:(out NSError * __nullable * __nullable)error -NS_SWIFT_NAME(apply(configuration:)); - -/** - <#Description#> - - @param credentials <#credentials description#> - @param error <#error description#> - @return <#return value description#> - */ -- (BOOL)provideCredentials:(nonnull OpenVPNCredentials *)credentials - error:(out NSError * __nullable * __nullable)error -NS_SWIFT_NAME(provide(credentials:)); - -/** - Establish connection with the VPN server - */ -- (void)connect; - -/** - Pause the client –- useful to avoid continuous reconnection attempts - when network is down - - @param pauseReason <#reason description#> - */ -- (void)pauseWithReason:(nullable NSString *)pauseReason -NS_SWIFT_NAME(pause(reason:)); - -/** - Resume the client after it has been paused - */ -- (void)resume; - -/** - Do a disconnect/reconnect cycle after given amount of seconds from now - - @param interval <#interval description#> - */ -- (void)reconnectAfterTimeInterval:(NSInteger)interval -NS_SWIFT_NAME(reconnect(interval:)); - -/** - Close connection with the VPN server - */ -- (void)disconnect; - -@end diff --git a/OpenVPN Adapter/OpenVPNAdapter.h b/OpenVPN Adapter/OpenVPNAdapter.h index 5ee94d7..0d4faaa 100644 --- a/OpenVPN Adapter/OpenVPNAdapter.h +++ b/OpenVPN Adapter/OpenVPNAdapter.h @@ -7,7 +7,163 @@ // #import +#import "OpenVPNAdapterEvent.h" + +NS_ASSUME_NONNULL_BEGIN + +@class NEPacketTunnelFlow; +@class NEPacketTunnelNetworkSettings; +@class OpenVPNAdapter; +@class OpenVPNConfiguration; +@class OpenVPNConnectionInfo; +@class OpenVPNCredentials; +@class OpenVPNInterfaceStats; +@class OpenVPNProperties; +@class OpenVPNTransportStats; +@class OpenVPNSessionToken; + +@protocol OpenVPNAdapterDelegate + +/** + This method is called once the network settings to be used have been established. + The receiver should call the completion handler once these settings have been set, returning a NEPacketTunnelFlow object for the TUN interface, or nil if an error occurred. + + @param openVPNAdapter The OpenVPNAdapter instance requesting this information. + @param networkSettings The NEPacketTunnelNetworkSettings to be used for the tunnel. + @param completionHandler The completion handler to be called with a NEPacketTunnelFlow object, or nil if an error occurred. + */ +- (void)openVPNAdapter:(OpenVPNAdapter *)openVPNAdapter configureTunnelWithNetworkSettings:(NEPacketTunnelNetworkSettings *)networkSettings completionHandler:(void (^)(NEPacketTunnelFlow * _Nullable packetFlow))completionHandler NS_SWIFT_NAME(openVPNAdapter(_:configureTunnelWithNetworkSettings:completionHandler:)); + + +/** + Informs the receiver that an OpenVPN error has occurred. + Some errors are fatal and should trigger the diconnection of the tunnel, check for fatal errors with the OpenVPNAdapterErrorFatalKey. + + @param openVPNAdapter The OpenVPNAdapter instance which encountered the error. + @param error The error which has occurred. + */ +- (void)openVPNAdapter:(OpenVPNAdapter *)openVPNAdapter handleError:(NSError *)error; + + +/** + Informs the receiver that an OpenVPN event has occurred. + + @param openVPNAdapter The OpenVPNAdapter instance which encountered the event. + @param event The event which has occurred. + @param message An accompanying message, may be nil. + */ +- (void)openVPNAdapter:(OpenVPNAdapter *)openVPNAdapter handleEvent:(OpenVPNAdapterEvent)event message:(nullable NSString *)message NS_SWIFT_NAME(openVPNAdapter(_:handleEvent:message:)); + +@optional + +/** + Informs the receiver that an OpenVPN message has been logged. + + @param openVPNAdapter The OpenVPNAdapter instance which encountered the log message. + @param logMessage The log message. + */ +- (void)openVPNAdapter:(OpenVPNAdapter *)openVPNAdapter handleLogMessage:(NSString *)logMessage; + +/** + Informs the receiver that a clock tick has occurred. + Clock ticks can be configured with an OpenVPNConfiguration object. + + @param openVPNAdapter The OpenVPNAdapter instance which encountered the clock tick. + */ +- (void)openVPNAdapterDidReceiveClockTick:(OpenVPNAdapter *)openVPNAdapter; + +@end @interface OpenVPNAdapter : NSObject +/** + The OpenVPN core copyright message. + */ +@property (nonatomic, class, readonly) NSString *copyright; + +/** + The OpenVPN platform. + */ +@property (nonatomic, class, readonly) NSString *platform; + +/** + The object that acts as the delegate of the adapter. + */ +@property (nonatomic, weak) id delegate; + +/** + The session name, nil unless the tunnel is connected. + */ +@property (nonatomic, nullable, readonly) NSString *sessionName; + +/** + The connection information, nil unless the tunnel is connected. + */ +@property (nonatomic, nullable, readonly) OpenVPNConnectionInfo *connectionInformation; + +/** + The interface statistics. + */ +@property (nonatomic, readonly) OpenVPNInterfaceStats *interfaceStatistics; + +/** + The session token, nil unless the tunnel is connected. + */ +@property (nonatomic, nullable, readonly) OpenVPNSessionToken *sessionToken; + +/** + The transport statistics. + */ +@property (nonatomic, readonly) OpenVPNTransportStats *transportStatistics; + +/** + Applies the given configuration object. + Call this method prior to connecting, this method has no effect after calling connect. + + @param configuration The configuration object. + @param error If there is an error applying the configuration, upon return contains an error object that describes the problem. + @return A properties object describing the configuration which has been applied. + */ +- (nullable OpenVPNProperties *)applyConfiguration:(OpenVPNConfiguration *)configuration error:(NSError **)error NS_SWIFT_NAME(apply(configuration:)); + +/** + Provides credentials to the receiver. + + @param credentials The credentials object. + @param error If there is an error providing the credentials, upon return contains an error object that describes the problem. + @return Returns YES if this method was successful, otherwise NO. + */ +- (BOOL)provideCredentials:(OpenVPNCredentials *)credentials error:(NSError **)error NS_SWIFT_NAME(provide(credentials:)); + +/** + Starts the tunnel. + */ +- (void)connect; + +/** + Pauses the tunnel. + + @param reason The reason for pausing the tunnel. + */ +- (void)pauseWithReason:(NSString *)reason NS_SWIFT_NAME(pause(withReason:)); + +/** + Resumes the connection. + */ +- (void)resume; + +/** + Reconnects after a given time period, perhaps due to an interface change. + + @param timeInterval The time interval to wait before reconnecting. + */ +- (void)reconnectAfterTimeInterval:(NSTimeInterval)timeInterval NS_SWIFT_NAME(reconnect(afterTimeInterval:)); + +/** + Disconnect from the tunnel. + */ +- (void)disconnect; + @end + +NS_ASSUME_NONNULL_END diff --git a/OpenVPN Adapter/OpenVPNAdapter.mm b/OpenVPN Adapter/OpenVPNAdapter.mm index 7e73f12..e7cd043 100644 --- a/OpenVPN Adapter/OpenVPNAdapter.mm +++ b/OpenVPN Adapter/OpenVPNAdapter.mm @@ -6,74 +6,309 @@ // // -#import -#import -#import -#import -#import +#import "OpenVPNAdapter.h" -#import +#define OPENVPN_EXTERN extern +#import +#import #import #import - -#import "OpenVPNTunnelSettings.h" -#import "OpenVPNClient.h" -#import "OpenVPNError.h" +#import #import "OpenVPNAdapterEvent.h" -#import "OpenVPNConfiguration+Internal.h" #import "OpenVPNCredentials+Internal.h" -#import "OpenVPNProperties+Internal.h" +#import "OpenVPNConfiguration+Internal.h" #import "OpenVPNConnectionInfo+Internal.h" +#import "OpenVPNError.h" +#import "OpenVPNInterfaceStats+Internal.h" +#import "OpenVPNProperties+Internal.h" #import "OpenVPNSessionToken+Internal.h" #import "OpenVPNTransportStats+Internal.h" -#import "OpenVPNInterfaceStats+Internal.h" -#import "OpenVPNAdapter.h" -#import "OpenVPNAdapter+Internal.h" -#import "OpenVPNAdapter+Public.h" + +class Client; @interface OpenVPNAdapter () { CFSocketRef _tunSocket; CFSocketRef _vpnSocket; - __weak id _delegate; } - -@property (assign, nonatomic) OpenVPNClient *vpnClient; - -@property (strong, nonatomic) NSString *remoteAddress; - -@property (strong, nonatomic) NSString *defaultGatewayIPv6; -@property (strong, nonatomic) NSString *defaultGatewayIPv4; - -@property (strong, nonatomic) OpenVPNTunnelSettings *tunnelSettingsIPv6; -@property (strong, nonatomic) OpenVPNTunnelSettings *tunnelSettingsIPv4; - -@property (strong, nonatomic) NSMutableArray *searchDomains; - -@property (strong, nonatomic) NSNumber *mtu; - -@property (weak, nonatomic) id packetFlow; - +@property (nonatomic) Client *client; +@property (nonatomic) NEPacketTunnelFlow *packetFlow; +@property (nonatomic) NSString *remoteAddress; +@property (nonatomic) NSString *ipv4DefaultGateway; +@property (nonatomic) NSString *ipv6DefaultGateway; +@property (nonatomic) NSNumber *mtu; +@property (nonatomic) NSMutableArray *ipv4LocalAddresses; +@property (nonatomic) NSMutableArray *ipv4SubnetMasks; +@property (nonatomic) NSMutableArray *ipv4IncludedRoutes; +@property (nonatomic) NSMutableArray *ipv4ExcludedRoutes; +@property (nonatomic) NSMutableArray *ipv6LocalAddresses; +@property (nonatomic) NSMutableArray *ipv6NetworkPrefixLengths; +@property (nonatomic) NSMutableArray *ipv6IncludedRoutes; +@property (nonatomic) NSMutableArray *ipv6ExcludedRoutes; +@property (nonatomic) NSMutableArray *dnsServers; +@property (nonatomic) NSMutableArray *searchDomains; +@property (nonatomic) NSMutableArray *proxyExceptionList; +@property (nonatomic) NSString *sessionName; +@property (nonatomic) BOOL autoProxyConfigurationEnabled; +@property (nonatomic) NSURL *proxyAutoConfigurationURL; +@property (nonatomic) BOOL httpProxyServerEnabled; +@property (nonatomic) NEProxyServer *httpProxyServer; +@property (nonatomic) BOOL httpsProxyServerEnabled; +@property (nonatomic) NEProxyServer *httpsProxyServer; +@property (nonatomic, readonly) NEPacketTunnelNetworkSettings *networkSettings; +- (CFSocketNativeHandle)configureSockets; +- (void)readTUNPackets; +- (void)teardownTunnel:(BOOL)disconnect; +- (OpenVPNAdapterError)errorByName:(NSString *)errorName; +- (OpenVPNAdapterEvent)eventByName:(NSString *)errorName; +- (NSString *)reasonForError:(OpenVPNAdapterError)error; @end +using namespace openvpn; + +class Client : public ClientAPI::OpenVPNClient { +public: + Client(OpenVPNAdapter *client) { + this->client = client; + } + + bool tun_builder_set_remote_address(const std::string& address, bool ipv6) override { + NSString *remoteAddress = [[NSString alloc] initWithUTF8String:address.c_str()]; + client.remoteAddress = remoteAddress; + return true; + } + + bool tun_builder_add_address(const std::string& address, int prefix_length, const std::string& gateway, bool ipv6, bool net30) override { + NSString *localAddress = [[NSString alloc] initWithUTF8String:address.c_str()]; + NSString *gatewayAddress = [[NSString alloc] initWithUTF8String:gateway.c_str()]; + NSString *defaultGateway = gatewayAddress.length == 0 || [gatewayAddress isEqualToString:@"UNSPEC"] ? nil : gatewayAddress; + if (ipv6) { + client.ipv6DefaultGateway = defaultGateway; + [client.ipv6LocalAddresses addObject:localAddress]; + [client.ipv6NetworkPrefixLengths addObject:@(prefix_length)]; + } else { + NSString *subnetMask = [[NSString alloc] initWithUTF8String:IPv4::Addr::netmask_from_prefix_len(prefix_length).to_string().c_str()]; + client.ipv4DefaultGateway = defaultGateway; + [client.ipv4LocalAddresses addObject:localAddress]; + [client.ipv4SubnetMasks addObject:subnetMask]; + } + return true; + } + + bool tun_builder_reroute_gw(bool ipv4, bool ipv6, unsigned int flags) override { + if (ipv4) { + NEIPv4Route *includedRoute = [NEIPv4Route defaultRoute]; + includedRoute.gatewayAddress = client.ipv4DefaultGateway; + [client.ipv4IncludedRoutes addObject:includedRoute]; + } + if (ipv6) { + NEIPv6Route *includedRoute = [NEIPv6Route defaultRoute]; + includedRoute.gatewayAddress = client.ipv6DefaultGateway; + [client.ipv6IncludedRoutes addObject:includedRoute]; + } + return true; + } + + bool tun_builder_add_route(const std::string& address, int prefix_length, int metric, bool ipv6) override { + NSString *route = [[NSString alloc] initWithUTF8String:address.c_str()]; + if (ipv6) { + NEIPv6Route *includedRoute = [[NEIPv6Route alloc] initWithDestinationAddress:route networkPrefixLength:@(prefix_length)]; + includedRoute.gatewayAddress = client.ipv6DefaultGateway; + [client.ipv6IncludedRoutes addObject:includedRoute]; + } else { + NSString *subnetMask = [[NSString alloc] initWithUTF8String:IPv4::Addr::netmask_from_prefix_len(prefix_length).to_string().c_str()]; + NEIPv4Route *includedRoute = [[NEIPv4Route alloc] initWithDestinationAddress:route subnetMask:subnetMask]; + includedRoute.gatewayAddress = client.ipv4DefaultGateway; + [client.ipv4IncludedRoutes addObject:includedRoute]; + } + return true; + } + + bool tun_builder_exclude_route(const std::string& address, int prefix_length, int metric, bool ipv6) override { + NSString *route = [[NSString alloc] initWithUTF8String:address.c_str()]; + if (ipv6) { + NEIPv6Route *excludedRoute = [[NEIPv6Route alloc] initWithDestinationAddress:route networkPrefixLength:@(prefix_length)]; + [client.ipv6ExcludedRoutes addObject:excludedRoute]; + } else { + NSString *subnetMask = [[NSString alloc] initWithUTF8String:IPv4::Addr::netmask_from_prefix_len(prefix_length).to_string().c_str()]; + NEIPv4Route *excludedRoute = [[NEIPv4Route alloc] initWithDestinationAddress:route subnetMask:subnetMask]; + [client.ipv4ExcludedRoutes addObject:excludedRoute]; + } + return true; + } + + bool tun_builder_add_dns_server(const std::string& address, bool ipv6) override { + NSString *dnsAddress = [[NSString alloc] initWithUTF8String:address.c_str()]; + [client.dnsServers addObject:dnsAddress]; + return true; + } + + bool tun_builder_add_search_domain(const std::string& domain) override { + NSString *searchDomain = [[NSString alloc] initWithUTF8String:domain.c_str()]; + [client.searchDomains addObject:searchDomain]; + return true; + } + + bool tun_builder_set_mtu(int mtu) override { + client.mtu = @(mtu); + return true; + } + + bool tun_builder_set_session_name(const std::string& name) override { + client.sessionName = [[NSString alloc] initWithUTF8String:name.c_str()]; + return true; + } + + bool tun_builder_add_proxy_bypass(const std::string& bypass_host) override { + NSString *bypassHost = [[NSString alloc] initWithUTF8String:bypass_host.c_str()]; + [client.proxyExceptionList addObject:bypassHost]; + return true; + } + + bool tun_builder_set_proxy_auto_config_url(const std::string& urlString) override { + NSURL *url = [[NSURL alloc] initWithString:[[NSString alloc] initWithUTF8String:urlString.c_str()]]; + client.autoProxyConfigurationEnabled = url != nil; + client.proxyAutoConfigurationURL = url; + return true; + } + + bool tun_builder_set_proxy_http(const std::string& host, int port) override { + NSString *address = [[NSString alloc] initWithUTF8String:host.c_str()]; + client.httpProxyServerEnabled = YES; + client.httpProxyServer = [[NEProxyServer alloc] initWithAddress:address port:port]; + return true; + } + + bool tun_builder_set_proxy_https(const std::string& host, int port) override { + NSString *address = [[NSString alloc] initWithUTF8String:host.c_str()]; + client.httpsProxyServerEnabled = YES; + client.httpsProxyServer = [[NEProxyServer alloc] initWithAddress:address port:port]; + return true; + } + + bool tun_builder_set_block_ipv6(bool block_ipv6) override { + return false; + } + + bool tun_builder_new() override { + reset_network_parameters(); + return true; + } + + int tun_builder_establish() override { + dispatch_semaphore_t semaphore = dispatch_semaphore_create(0); + [client.delegate openVPNAdapter:client configureTunnelWithNetworkSettings:client.networkSettings completionHandler:^(NEPacketTunnelFlow * _Nullable packetFlow) { + client.packetFlow = packetFlow; + dispatch_semaphore_signal(semaphore); + }]; + dispatch_semaphore_wait(semaphore, dispatch_time(DISPATCH_TIME_NOW, 30 * NSEC_PER_SEC)); + + if (client.packetFlow) { + [client readTUNPackets]; + return [client configureSockets]; + } else { + return -1; + } + } + + void tun_builder_teardown(bool disconnect) override { + reset_network_parameters(); + [client teardownTunnel:disconnect]; + } + + bool tun_builder_persist() override { + return true; + } + + bool socket_protect(int socket) override { + return true; + } + + bool pause_on_connection_timeout() override { + return false; + } + + void external_pki_cert_request(ClientAPI::ExternalPKICertRequest& certreq) override { + + } + + void external_pki_sign_request(ClientAPI::ExternalPKISignRequest& signreq) override { + + } + + void event(const ClientAPI::Event& event) override { + NSString *name = [[NSString alloc] initWithUTF8String:event.name.c_str()]; + NSString *message = [[NSString alloc] initWithUTF8String:event.info.c_str()]; + + if (event.error) { + OpenVPNAdapterError errorCode = [client errorByName:name]; + NSString *errorReason = [client reasonForError:errorCode]; + NSError *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain code:errorCode userInfo:@{NSLocalizedDescriptionKey: @"OpenVPN error occured.", NSLocalizedFailureReasonErrorKey: errorReason, OpenVPNAdapterErrorMessageKey: message != nil ? message : @"", OpenVPNAdapterErrorFatalKey: @(event.fatal)}]; + [client.delegate openVPNAdapter:client handleError:error]; + } else { + OpenVPNAdapterEvent eventIdentifier = [client eventByName:name]; + [client.delegate openVPNAdapter:client handleEvent:eventIdentifier message:message.length ? message : nil]; + } + } + + void log(const ClientAPI::LogInfo& log) override { + if ([client.delegate respondsToSelector:@selector(openVPNAdapter:handleLogMessage:)]) { + [client.delegate openVPNAdapter:client handleLogMessage:[[NSString alloc] initWithUTF8String:log.text.c_str()]]; + } + } + + void clock_tick() override { + if ([client.delegate respondsToSelector:@selector(openVPNAdapterDidReceiveClockTick:)]) { + [client.delegate openVPNAdapterDidReceiveClockTick:client]; + } + } + + void reset_network_parameters() { + client.remoteAddress = nil; + client.ipv4DefaultGateway = nil; + client.ipv6DefaultGateway = nil; + client.mtu = nil; + client.ipv4LocalAddresses = nil; + client.ipv4SubnetMasks = nil; + client.ipv4IncludedRoutes = nil; + client.ipv4ExcludedRoutes = nil; + client.ipv6LocalAddresses = nil; + client.ipv6NetworkPrefixLengths = nil; + client.ipv6IncludedRoutes = nil; + client.ipv6ExcludedRoutes = nil; + client.dnsServers = nil; + client.searchDomains = nil; + client.sessionName = nil; + client.proxyExceptionList = nil; + client.autoProxyConfigurationEnabled = NO; + client.proxyAutoConfigurationURL = nil; + client.httpProxyServerEnabled = NO; + client.httpProxyServer = nil; + client.httpsProxyServerEnabled = NO; + client.httpsProxyServer = nil; + } +private: + OpenVPNAdapter *client; +}; + @implementation OpenVPNAdapter -#pragma mark Sockets Configuration +- (instancetype)init { + if ((self = [super init])) { + self.client = new Client(self); + } + return self; +} -static void socketCallback(CFSocketRef socket, CFSocketCallBackType type, CFDataRef address, const void *data, void *info) { - OpenVPNAdapter *adapter = (__bridge OpenVPNAdapter *)info; - - switch (type) { - case kCFSocketDataCallBack: - [adapter readVPNPacket:(__bridge NSData *)data]; - break; - - default: - break; +static inline void SocketCallback(CFSocketRef socket, CFSocketCallBackType type, CFDataRef address, const void *data, void *info) { + if (type == kCFSocketDataCallBack) { + [(__bridge OpenVPNAdapter *)info readVPNPacket:(__bridge NSData *)data]; } } -- (BOOL)configureSockets { +- (CFSocketNativeHandle)configureSockets { + [self invalidateSockets]; + int sockets[2]; if (socketpair(PF_LOCAL, SOCK_DGRAM, IPPROTO_IP, sockets) == -1) { NSLog(@"Failed to create a pair of connected sockets: %@", [NSString stringWithUTF8String:strerror(errno)]); @@ -87,20 +322,38 @@ static void socketCallback(CFSocketRef socket, CFSocketCallBackType type, CFData CFSocketContext socketCtxt = {0, (__bridge void *)self, NULL, NULL, NULL}; - _vpnSocket = CFSocketCreateWithNative(kCFAllocatorDefault, sockets[0], kCFSocketDataCallBack, &socketCallback, &socketCtxt); + _vpnSocket = CFSocketCreateWithNative(kCFAllocatorDefault, sockets[0], kCFSocketDataCallBack, SocketCallback, &socketCtxt); _tunSocket = CFSocketCreateWithNative(kCFAllocatorDefault, sockets[1], kCFSocketNoCallBack, NULL, NULL); if (!_vpnSocket || !_tunSocket) { + [self invalidateSockets]; NSLog(@"Failed to create core foundation sockets from native sockets"); return NO; } CFRunLoopSourceRef tunSocketSource = CFSocketCreateRunLoopSource(kCFAllocatorDefault, _vpnSocket, 0); CFRunLoopAddSource(CFRunLoopGetMain(), tunSocketSource, kCFRunLoopDefaultMode); - CFRelease(tunSocketSource); - return YES; + return CFSocketGetNative(_tunSocket); +} + +- (void)teardownTunnel:(BOOL)disconnect { + [self invalidateSockets]; +} + +- (void)invalidateSockets { + if (_vpnSocket) { + CFSocketInvalidate(_vpnSocket); + CFRelease(_vpnSocket); + _vpnSocket = nil; + } + + if (_tunSocket) { + CFSocketInvalidate(_tunSocket); + CFRelease(_tunSocket); + _tunSocket = nil; + } } - (BOOL)configureBufferSizeForSocket:(int)socket { @@ -120,433 +373,6 @@ static void socketCallback(CFSocketRef socket, CFSocketCallBackType type, CFData return YES; } -#pragma mark TUN Configuration - -- (BOOL)setRemoteAddress:(NSString *)address isIPv6:(BOOL)isIPv6 { - if (address == nil) { - return NO; - } - - self.remoteAddress = address; - - return YES; -} - -- (BOOL)addLocalAddress:(NSString *)address prefixLength:(NSNumber *)prefixLength gateway:(NSString *)gateway isIPv6:(BOOL)isIPv6 { - if (address == nil || prefixLength == nil) { - return NO; - } - - NSString *defaultGateway = [gateway length] == 0 || [gateway isEqualToString:@"UNSPEC"] ? nil : gateway; - - if (isIPv6) { - if (!self.tunnelSettingsIPv6.initialized) { - self.tunnelSettingsIPv6.initialized = YES; - } - - self.defaultGatewayIPv6 = defaultGateway; - - [self.tunnelSettingsIPv6.localAddresses addObject:address]; - [self.tunnelSettingsIPv6.prefixLengths addObject:prefixLength]; - } else { - if (!self.tunnelSettingsIPv4.initialized) { - self.tunnelSettingsIPv4.initialized = YES; - } - - self.defaultGatewayIPv4 = defaultGateway; - - [self.tunnelSettingsIPv4.localAddresses addObject:address]; - [self.tunnelSettingsIPv4.prefixLengths addObject:prefixLength]; - } - - return YES; -} - -- (BOOL)defaultGatewayRerouteIPv4:(BOOL)rerouteIPv4 rerouteIPv6:(BOOL)rerouteIPv6 { - if (rerouteIPv6) { - NEIPv6Route *includedRoute = [NEIPv6Route defaultRoute]; - includedRoute.gatewayAddress = self.defaultGatewayIPv6; - - [self.tunnelSettingsIPv6.includedRoutes addObject:includedRoute]; - } - - if (rerouteIPv4) { - NEIPv4Route *includedRoute = [NEIPv4Route defaultRoute]; - includedRoute.gatewayAddress = self.defaultGatewayIPv4; - - [self.tunnelSettingsIPv4.includedRoutes addObject:includedRoute]; - } - - return YES; -} - -- (BOOL)addRoute:(NSString *)route prefixLength:(NSNumber *)prefixLength isIPv6:(BOOL)isIPv6 { - if (route == nil || prefixLength == nil) { - return NO; - } - - if (isIPv6) { - NEIPv6Route *includedRoute = [[NEIPv6Route alloc] initWithDestinationAddress:route networkPrefixLength:prefixLength]; - includedRoute.gatewayAddress = self.defaultGatewayIPv6; - - [self.tunnelSettingsIPv6.includedRoutes addObject:includedRoute]; - } else { - NSString *subnet = [self subnetFromPrefixLength:prefixLength]; - - NEIPv4Route *includedRoute = [[NEIPv4Route alloc] initWithDestinationAddress:route subnetMask:subnet]; - includedRoute.gatewayAddress = self.defaultGatewayIPv4; - - [self.tunnelSettingsIPv4.includedRoutes addObject:includedRoute]; - } - - return YES; -} - -- (BOOL)excludeRoute:(NSString *)route prefixLength:(NSNumber *)prefixLength isIPv6:(BOOL)isIPv6 { - if (route == nil || prefixLength == nil) { - return NO; - } - - if (isIPv6) { - NEIPv6Route *excludedRoute = [[NEIPv6Route alloc] initWithDestinationAddress:route networkPrefixLength:prefixLength]; - [self.tunnelSettingsIPv6.excludedRoutes addObject:excludedRoute]; - } else { - NSString *subnet = [self subnetFromPrefixLength:prefixLength]; - NEIPv4Route *excludedRoute = [[NEIPv4Route alloc] initWithDestinationAddress:route subnetMask:subnet]; - [self.tunnelSettingsIPv4.excludedRoutes addObject:excludedRoute]; - } - - return YES; -} - -- (BOOL)addDNSAddress:(NSString *)address isIPv6:(BOOL)isIPv6 { - if (address == nil) { - return NO; - } - - if (isIPv6) { - [self.tunnelSettingsIPv6.dnsAddresses addObject:address]; - } else { - [self.tunnelSettingsIPv4.dnsAddresses addObject:address]; - } - - return YES; -} - -- (BOOL)addSearchDomain:(NSString *)domain { - if (domain == nil) { - return NO; - } - - [self.searchDomains addObject:domain]; - - return YES; -} - -- (BOOL)setMTU:(NSNumber *)mtu { - self.mtu = mtu; - return YES; -} - -- (CFSocketNativeHandle)establishTunnel { - NSAssert(self.delegate != nil, @"delegate property should not be nil"); - - NEPacketTunnelNetworkSettings *networkSettings = [[NEPacketTunnelNetworkSettings alloc] initWithTunnelRemoteAddress:self.remoteAddress]; - - // Configure IPv6 addresses and routes - if (self.tunnelSettingsIPv6.initialized) { - NEIPv6Settings *settingsIPv6 = [[NEIPv6Settings alloc] initWithAddresses:self.tunnelSettingsIPv6.localAddresses networkPrefixLengths:self.tunnelSettingsIPv6.prefixLengths]; - settingsIPv6.includedRoutes = self.tunnelSettingsIPv6.includedRoutes; - settingsIPv6.excludedRoutes = self.tunnelSettingsIPv6.excludedRoutes; - - networkSettings.IPv6Settings = settingsIPv6; - } - - // Configure IPv4 addresses and routes - if (self.tunnelSettingsIPv4.initialized) { - NSMutableArray *subnets = [NSMutableArray new]; - [self.tunnelSettingsIPv4.prefixLengths enumerateObjectsUsingBlock:^(id _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { - NSString *subnet = [self subnetFromPrefixLength:obj]; - [subnets addObject:subnet]; - }]; - - NEIPv4Settings *ipSettings = [[NEIPv4Settings alloc] initWithAddresses:self.tunnelSettingsIPv4.localAddresses subnetMasks:subnets]; - ipSettings.includedRoutes = self.tunnelSettingsIPv4.includedRoutes; - ipSettings.excludedRoutes = self.tunnelSettingsIPv4.excludedRoutes; - - networkSettings.IPv4Settings = ipSettings; - } - - // Configure DNS addresses and search domains - NSMutableArray *dnsAddresses = [NSMutableArray new]; - - if (self.tunnelSettingsIPv6.dnsAddresses.count > 0) { - [dnsAddresses addObjectsFromArray:self.tunnelSettingsIPv6.dnsAddresses]; - } - - if (self.tunnelSettingsIPv4.dnsAddresses.count > 0) { - [dnsAddresses addObjectsFromArray:self.tunnelSettingsIPv4.dnsAddresses]; - } - - if (dnsAddresses.count > 0) { - networkSettings.DNSSettings = [[NEDNSSettings alloc] initWithServers:dnsAddresses]; - } - - if (networkSettings.DNSSettings && self.searchDomains.count > 0) { - networkSettings.DNSSettings.searchDomains = self.searchDomains; - } - - // Set MTU - networkSettings.MTU = self.mtu; - - // Establish TUN interface - dispatch_semaphore_t sema = dispatch_semaphore_create(0); - - [self performAsyncBlock:^{ - [self.delegate configureTunnelWithSettings:networkSettings callback:^(id _Nullable flow) { - self.packetFlow = flow; - dispatch_semaphore_signal(sema); - }]; - }]; - - // Wait 10 seconds - dispatch_time_t timeout = dispatch_time(DISPATCH_TIME_NOW, 10 * NSEC_PER_SEC); - if (dispatch_semaphore_wait(sema, timeout) != 0) { - NSLog(@"Failed to establish tunnel in a reasonable time"); - return -1; - } - - if (self.packetFlow) { - [self readTUNPackets]; - return CFSocketGetNative(_tunSocket); - } else { - return -1; - } -} - -- (void)teardownTunnel:(BOOL)disconnect { - [self resetTunnelSettings]; - - if (_vpnSocket) { - CFSocketInvalidate(_vpnSocket); - CFRelease(_vpnSocket); - _vpnSocket = nil; - } - - if (_tunSocket) { - CFSocketInvalidate(_tunSocket); - CFRelease(_tunSocket); - _tunSocket = nil; - } -} - -- (void)resetTunnelSettings { - self.remoteAddress = nil; - self.defaultGatewayIPv6 = nil; - self.defaultGatewayIPv4 = nil; - self.tunnelSettingsIPv6 = [[OpenVPNTunnelSettings alloc] init]; - self.tunnelSettingsIPv4 = [[OpenVPNTunnelSettings alloc] init]; - self.searchDomains = [[NSMutableArray alloc] init]; - self.mtu = nil; -} - -#pragma mark Event and Log Handlers - -- (void)handleEvent:(const ClientAPI::Event *)event { - NSAssert(self.delegate != nil, @"delegate property should not be nil"); - - NSString *name = [NSString stringWithUTF8String:event->name.c_str()]; - NSString *message = [NSString stringWithUTF8String:event->info.c_str()]; - - if (event->error) { - OpenVPNAdapterError errorCode = [self errorByName:name]; - NSString *errorReason = [self reasonForError:errorCode]; - - NSError *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain - code:errorCode - userInfo:@{ NSLocalizedDescriptionKey: @"OpenVPN error occurred.", - NSLocalizedFailureReasonErrorKey: errorReason, - OpenVPNAdapterErrorMessageKey: message != nil ? message : @"", - OpenVPNAdapterErrorFatalKey: @(event->fatal) }]; - - [self performAsyncBlock:^{ - [self.delegate handleError:error]; - }]; - } else { - OpenVPNAdapterEvent eventIdentifier = [self eventByName:name]; - [self performAsyncBlock:^{ - [self.delegate handleEvent:eventIdentifier message:message == nil || [message isEqualToString:@""] ? nil : message]; - }]; - } -} - -- (void)handleLog:(const ClientAPI::LogInfo *)log { - NSAssert(self.delegate != nil, @"delegate property should not be nil"); - - if ([self.delegate respondsToSelector:@selector(handleLog:)]) { - NSString *message = [NSString stringWithCString:log->text.c_str() encoding:NSUTF8StringEncoding]; - [self performAsyncBlock:^{ - [self.delegate handleLog:message]; - }]; - } -} - -#pragma mark Clock Tick - -- (void)tick { - NSAssert(self.delegate != nil, @"delegate property should not be nil"); - - if ([self.delegate respondsToSelector:@selector(tick)]) { - [self performAsyncBlock:^{ - [self.delegate tick]; - }]; - } -} - -#pragma mark Properties - -+ (NSString *)copyright { - std::string copyright = OpenVPNClient::copyright(); - return [NSString stringWithUTF8String:copyright.c_str()]; -} - -+ (NSString *)platform { - std::string platform = OpenVPNClient::platform(); - return [NSString stringWithUTF8String:platform.c_str()]; -} - -- (void)setDelegate:(id)delegate { - _delegate = delegate; -} - -- (id)delegate { - return _delegate; -} - -- (OpenVPNConnectionInfo *)connectionInfo { - ClientAPI::ConnectionInfo info = self.vpnClient->connection_info(); - return info.defined ? [[OpenVPNConnectionInfo alloc] initWithConnectionInfo:info] : nil; -} - -- (OpenVPNSessionToken *)sessionToken { - ClientAPI::SessionToken token; - bool gotToken = self.vpnClient->session_token(token); - - return gotToken ? [[OpenVPNSessionToken alloc] initWithSessionToken:token] : nil; -} - -- (OpenVPNTransportStats *)transportStats { - ClientAPI::TransportStats stats = self.vpnClient->transport_stats(); - return [[OpenVPNTransportStats alloc] initWithTransportStats:stats]; -} - -- (OpenVPNInterfaceStats *)interfaceStats { - ClientAPI::InterfaceStats stats = self.vpnClient->tun_stats(); - return [[OpenVPNInterfaceStats alloc] initWithInterfaceStats:stats]; -} - -#pragma mark Client Configuration - -- (OpenVPNProperties *)applyConfiguration:(nonnull OpenVPNConfiguration *)configuration error:(out NSError **)error { - ClientAPI::EvalConfig eval = self.vpnClient->eval_config(configuration.config); - if (eval.error) { - NSString *errorReason = [self reasonForError:OpenVPNAdapterErrorConfigurationFailure]; - - if (error) *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain code:OpenVPNAdapterErrorConfigurationFailure userInfo:@{ - NSLocalizedDescriptionKey: @"Failed to apply OpenVPN configuration.", - NSLocalizedFailureReasonErrorKey: errorReason, - OpenVPNAdapterErrorMessageKey: [NSString stringWithUTF8String:eval.message.c_str()], - OpenVPNAdapterErrorFatalKey: @(YES) - }]; - return nil; - } - - return [[OpenVPNProperties alloc] initWithEvalConfig:eval]; -} - -- (BOOL)provideCredentials:(nonnull OpenVPNCredentials *)credentials error:(out NSError **)error { - ClientAPI::Status status = self.vpnClient->provide_creds(credentials.credentials); - if (status.error) { - if (error) { - OpenVPNAdapterError errorCode = !status.status.empty() ? [self errorByName:[NSString stringWithUTF8String:status.status.c_str()]] : OpenVPNAdapterErrorCredentialsFailure; - NSString *errorReason = [self reasonForError:errorCode]; - - *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain code:errorCode userInfo:@{ - NSLocalizedDescriptionKey: @"Failed to provide OpenVPN credentials.", - NSLocalizedFailureReasonErrorKey: errorReason, - OpenVPNAdapterErrorMessageKey: [NSString stringWithUTF8String:status.message.c_str()], - OpenVPNAdapterErrorFatalKey: @(YES) - }]; - } - return NO; - } - - return YES; -} - -#pragma mark Connection Control - -- (void)connect { - dispatch_queue_t connectQueue = dispatch_queue_create("me.ss-abramchuk.openvpn-adapter.connection-queue", NULL); - dispatch_async(connectQueue, ^{ - OpenVPNClient::init_process(); - - self.tunnelSettingsIPv6 = [OpenVPNTunnelSettings new]; - self.tunnelSettingsIPv4 = [OpenVPNTunnelSettings new]; - - self.searchDomains = [NSMutableArray new]; - - ClientAPI::Status status = self.vpnClient->connect(); - if (status.error) { - OpenVPNAdapterError errorCode = !status.status.empty() ? [self errorByName:[NSString stringWithUTF8String:status.status.c_str()]] : OpenVPNAdapterErrorUnknown; - NSString *errorReason = [self reasonForError:errorCode]; - - NSError *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain - code:errorCode - userInfo:@{ NSLocalizedDescriptionKey: @"Failed to establish connection with OpenVPN server.", - NSLocalizedFailureReasonErrorKey: errorReason, - OpenVPNAdapterErrorMessageKey: [NSString stringWithUTF8String:status.message.c_str()], - OpenVPNAdapterErrorFatalKey: @(YES) }]; - [self performAsyncBlock:^{ - [self.delegate handleError:error]; - }]; - } - - OpenVPNClient::uninit_process(); - }); -} - -- (void)pauseWithReason:(NSString *)pauseReason { - std::string reason = pauseReason ? std::string([pauseReason UTF8String]) : ""; - self.vpnClient->pause(reason); -} - -- (void)resume { - self.vpnClient->resume(); -} - -- (void)reconnectAfterTimeInterval:(NSInteger)interval { - self.vpnClient->reconnect(interval); -} - -- (void)disconnect { - self.vpnClient->stop(); -} - -#pragma mark Initialization - -- (instancetype)init -{ - self = [super init]; - if (self) { - _delegate = nil; - self.vpnClient = new OpenVPNClient((__bridge void *)self); - } - return self; -} - -#pragma mark TUN -> OpenVPN - - (void)readTUNPackets { [self.packetFlow readPacketsWithCompletionHandler:^(NSArray * _Nonnull packets, NSArray * _Nonnull protocols) { [self writeVPNPackets:packets protocols:protocols]; @@ -583,8 +409,6 @@ static void socketCallback(CFSocketRef socket, CFSocketCallBackType type, CFData return [data copy]; } -#pragma mark OpenVPN -> TUN - - (void)readVPNPacket:(NSData *)packet { #if TARGET_OS_IPHONE // Get network protocol from prefix @@ -618,104 +442,228 @@ static void socketCallback(CFSocketRef socket, CFSocketCallBackType type, CFData } } -#pragma mark Utils +- (uint8_t)protocolFamilyForVersion:(uint32_t)version { + switch (version) { + case 4: return PF_INET; + case 6: return PF_INET6; + default: return PF_UNSPEC; + } +} + +- (NEPacketTunnelNetworkSettings *)networkSettings { + NEPacketTunnelNetworkSettings *networkSettings = [[NEPacketTunnelNetworkSettings alloc] initWithTunnelRemoteAddress:self.remoteAddress]; + + NEIPv4Settings *ipv4Settings = [[NEIPv4Settings alloc] initWithAddresses:self.ipv4LocalAddresses subnetMasks:self.ipv4SubnetMasks]; + ipv4Settings.includedRoutes = self.ipv4IncludedRoutes; + ipv4Settings.excludedRoutes = self.ipv4ExcludedRoutes; + networkSettings.IPv4Settings = ipv4Settings; + + NEIPv6Settings *ipv6Settings = [[NEIPv6Settings alloc] initWithAddresses:self.ipv6LocalAddresses networkPrefixLengths:self.ipv6NetworkPrefixLengths]; + ipv6Settings.includedRoutes = self.ipv6IncludedRoutes; + ipv6Settings.excludedRoutes = self.ipv6ExcludedRoutes; + networkSettings.IPv6Settings = ipv6Settings; + + NEDNSSettings *dnsSettings = [[NEDNSSettings alloc] initWithServers:self.dnsServers]; + dnsSettings.searchDomains = self.searchDomains; + networkSettings.DNSSettings = dnsSettings; + + NEProxySettings *proxySettings = [[NEProxySettings alloc] init]; + proxySettings.autoProxyConfigurationEnabled = self.autoProxyConfigurationEnabled; + proxySettings.proxyAutoConfigurationURL = self.proxyAutoConfigurationURL; + proxySettings.exceptionList = self.proxyExceptionList; + proxySettings.HTTPServer = self.httpProxyServer; + proxySettings.HTTPEnabled = self.httpProxyServerEnabled; + proxySettings.HTTPSServer = self.httpsProxyServer; + proxySettings.HTTPSEnabled = self.httpsProxyServerEnabled; + + networkSettings.MTU = self.mtu; + + return networkSettings; +} + ++ (NSString *)copyright { + return [[NSString alloc] initWithUTF8String:Client::copyright().c_str()]; +} + ++ (NSString *)platform { + return [[NSString alloc] initWithUTF8String:Client::platform().c_str()]; +} + +- (OpenVPNConnectionInfo *)connectionInformation { + ClientAPI::ConnectionInfo information = self.client->connection_info(); + return information.defined ? [[OpenVPNConnectionInfo alloc] initWithConnectionInfo:information] : nil; +} + +- (OpenVPNInterfaceStats *)interfaceStatistics { + return [[OpenVPNInterfaceStats alloc] initWithInterfaceStats:self.client->tun_stats()]; +} + +- (OpenVPNSessionToken *)sessionToken { + ClientAPI::SessionToken token; + return self.client->session_token(token) ? [[OpenVPNSessionToken alloc] initWithSessionToken:token] : nil; +} + +- (OpenVPNTransportStats *)transportStatistics { + return [[OpenVPNTransportStats alloc] initWithTransportStats:self.client->transport_stats()]; +} + +- (OpenVPNProperties *)applyConfiguration:(OpenVPNConfiguration *)configuration error:(NSError * _Nullable __autoreleasing *)error { + ClientAPI::EvalConfig eval = self.client->eval_config(configuration.config); + if (eval.error) { + if (error) { + NSString *errorReason = [self reasonForError:OpenVPNAdapterErrorConfigurationFailure]; + *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain code:OpenVPNAdapterErrorConfigurationFailure userInfo:@{NSLocalizedDescriptionKey: @"Failed to apply OpenVPN configuration.", NSLocalizedFailureReasonErrorKey: errorReason, OpenVPNAdapterErrorMessageKey: [[NSString alloc] initWithUTF8String:eval.message.c_str()], OpenVPNAdapterErrorFatalKey: @YES}]; + } + return nil; + } + + return [[OpenVPNProperties alloc] initWithEvalConfig:eval]; +} + +- (BOOL)provideCredentials:(OpenVPNCredentials *)credentials error:(NSError * _Nullable __autoreleasing *)error { + ClientAPI::Status status = self.client->provide_creds(credentials.credentials); + + if (status.error) { + if (error) { + OpenVPNAdapterError errorCode = !status.status.empty() ? [self errorByName:[[NSString alloc] initWithUTF8String:status.status.c_str()]] : OpenVPNAdapterErrorCredentialsFailure; + NSString *errorReason = [self reasonForError:errorCode]; + *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain code:errorCode userInfo:@{NSLocalizedDescriptionKey: @"Failed to provide OpenVPN credentials.", NSLocalizedFailureReasonErrorKey: errorReason, OpenVPNAdapterErrorMessageKey: [[NSString alloc] initWithUTF8String:status.message.c_str()], OpenVPNAdapterErrorFatalKey: @YES}]; + } + return NO; + } + + return YES; +} + +- (void)connect { + dispatch_queue_attr_t attributes = dispatch_queue_attr_make_with_qos_class(DISPATCH_QUEUE_SERIAL, QOS_CLASS_UTILITY, 0); + dispatch_queue_t connectQueue = dispatch_queue_create("com.openvpnadapter.connection", attributes); + dispatch_async(connectQueue, ^{ + Client::init_process(); + ClientAPI::Status status = self.client->connect(); + [self handleStatus:status]; + Client::uninit_process(); + }); +} + +- (void)pauseWithReason:(NSString *)reason { + self.client->pause(std::string(reason.UTF8String)); +} + +- (void)resume { + self.client->resume(); +} + +- (void)reconnectAfterTimeInterval:(NSTimeInterval)timeInterval { + self.client->reconnect(timeInterval); +} + +- (void)disconnect { + self.client->stop(); +} + +- (void)handleStatus:(ClientAPI::Status)status { + if (!status.error) { + return; + } + + OpenVPNAdapterError errorCode = !status.status.empty() ? [self errorByName:[[NSString alloc] initWithUTF8String:status.status.c_str()]] : OpenVPNAdapterErrorUnknown; + NSString *errorReason = [self reasonForError:errorCode]; + NSError *error = [NSError errorWithDomain:OpenVPNAdapterErrorDomain code:errorCode userInfo:@{NSLocalizedDescriptionKey: @"Failed to establish connection with OpenVPN server.", NSLocalizedFailureReasonErrorKey: errorReason, OpenVPNAdapterErrorMessageKey: [[NSString alloc] initWithUTF8String:status.message.c_str()], OpenVPNAdapterErrorFatalKey: @YES}]; + [self.delegate openVPNAdapter:self handleError:error]; +} - (OpenVPNAdapterEvent)eventByName:(NSString *)eventName { - NSDictionary *events = @{ - @"DISCONNECTED": @(OpenVPNAdapterEventDisconnected), - @"CONNECTED": @(OpenVPNAdapterEventConnected), - @"RECONNECTING": @(OpenVPNAdapterEventReconnecting), - @"RESOLVE": @(OpenVPNAdapterEventResolve), - @"WAIT": @(OpenVPNAdapterEventWait), - @"WAIT_PROXY": @(OpenVPNAdapterEventWaitProxy), - @"CONNECTING": @(OpenVPNAdapterEventConnecting), - @"GET_CONFIG": @(OpenVPNAdapterEventGetConfig), - @"ASSIGN_IP": @(OpenVPNAdapterEventAssignIP), - @"ADD_ROUTES": @(OpenVPNAdapterEventAddRoutes), - @"ECHO": @(OpenVPNAdapterEventEcho), - @"INFO": @(OpenVPNAdapterEventInfo), - @"PAUSE": @(OpenVPNAdapterEventPause), - @"RESUME": @(OpenVPNAdapterEventResume), - @"RELAY": @(OpenVPNAdapterEventRelay) - }; + NSDictionary *events = @{@"DISCONNECTED": @(OpenVPNAdapterEventDisconnected), + @"CONNECTED": @(OpenVPNAdapterEventConnected), + @"RECONNECTING": @(OpenVPNAdapterEventReconnecting), + @"RESOLVE": @(OpenVPNAdapterEventResolve), + @"WAIT": @(OpenVPNAdapterEventWait), + @"WAIT_PROXY": @(OpenVPNAdapterEventWaitProxy), + @"CONNECTING": @(OpenVPNAdapterEventConnecting), + @"GET_CONFIG": @(OpenVPNAdapterEventGetConfig), + @"ASSIGN_IP": @(OpenVPNAdapterEventAssignIP), + @"ADD_ROUTES": @(OpenVPNAdapterEventAddRoutes), + @"ECHO": @(OpenVPNAdapterEventEcho), + @"INFO": @(OpenVPNAdapterEventInfo), + @"PAUSE": @(OpenVPNAdapterEventPause), + @"RESUME": @(OpenVPNAdapterEventResume), + @"RELAY": @(OpenVPNAdapterEventRelay)}; OpenVPNAdapterEvent event = events[eventName] != nil ? (OpenVPNAdapterEvent)[events[eventName] integerValue] : OpenVPNAdapterEventUnknown; return event; } - (OpenVPNAdapterError)errorByName:(NSString *)errorName { - NSDictionary *errors = @{ - @"NETWORK_RECV_ERROR": @(OpenVPNAdapterErrorNetworkRecvError), - @"NETWORK_EOF_ERROR": @(OpenVPNAdapterErrorNetworkEOFError), - @"NETWORK_SEND_ERROR": @(OpenVPNAdapterErrorNetworkSendError), - @"NETWORK_UNAVAILABLE": @(OpenVPNAdapterErrorNetworkUnavailable), - @"DECRYPT_ERROR": @(OpenVPNAdapterErrorDecryptError), - @"HMAC_ERROR": @(OpenVPNAdapterErrorDecryptError), - @"REPLAY_ERROR": @(OpenVPNAdapterErrorReplayError), - @"BUFFER_ERROR": @(OpenVPNAdapterErrorBufferError), - @"CC_ERROR": @(OpenVPNAdapterErrorCCError), - @"BAD_SRC_ADDR": @(OpenVPNAdapterErrorBadSrcAddr), - @"COMPRESS_ERROR": @(OpenVPNAdapterErrorCompressError), - @"RESOLVE_ERROR": @(OpenVPNAdapterErrorResolveError), - @"SOCKET_PROTECT_ERROR": @(OpenVPNAdapterErrorSocketProtectError), - @"TUN_READ_ERROR": @(OpenVPNAdapterErrorTUNReadError), - @"TUN_WRITE_ERROR": @(OpenVPNAdapterErrorTUNWriteError), - @"TUN_FRAMING_ERROR": @(OpenVPNAdapterErrorTUNFramingError), - @"TUN_SETUP_FAILED": @(OpenVPNAdapterErrorTUNSetupFailed), - @"TUN_IFACE_CREATE": @(OpenVPNAdapterErrorTUNIfaceCreate), - @"TUN_IFACE_DISABLED": @(OpenVPNAdapterErrorTUNIfaceDisabled), - @"TUN_ERROR": @(OpenVPNAdapterErrorTUNError), - @"TAP_NOT_SUPPORTED": @(OpenVPNAdapterErrorTAPNotSupported), - @"REROUTE_GW_NO_DNS": @(OpenVPNAdapterErrorRerouteGatewayNoDns), - @"TRANSPORT_ERROR": @(OpenVPNAdapterErrorTransportError), - @"TCP_OVERFLOW": @(OpenVPNAdapterErrorTCPOverflow), - @"TCP_SIZE_ERROR": @(OpenVPNAdapterErrorTCPSizeError), - @"TCP_CONNECT_ERROR": @(OpenVPNAdapterErrorTCPConnectError), - @"UDP_CONNECT_ERROR": @(OpenVPNAdapterErrorUDPConnectError), - @"SSL_ERROR": @(OpenVPNAdapterErrorSSLError), - @"SSL_PARTIAL_WRITE": @(OpenVPNAdapterErrorSSLPartialWrite), - @"ENCAPSULATION_ERROR": @(OpenVPNAdapterErrorEncapsulationError), - @"EPKI_CERT_ERROR": @(OpenVPNAdapterErrorEPKICertError), - @"EPKI_SIGN_ERROR": @(OpenVPNAdapterErrorEPKISignError), - @"HANDSHAKE_TIMEOUT": @(OpenVPNAdapterErrorHandshakeTimeout), - @"KEEPALIVE_TIMEOUT": @(OpenVPNAdapterErrorKeepaliveTimeout), - @"INACTIVE_TIMEOUT": @(OpenVPNAdapterErrorInactiveTimeout), - @"CONNECTION_TIMEOUT": @(OpenVPNAdapterErrorConnectionTimeout), - @"PRIMARY_EXPIRE": @(OpenVPNAdapterErrorPrimaryExpire), - @"TLS_VERSION_MIN": @(OpenVPNAdapterErrorTLSVersionMin), - @"TLS_AUTH_FAIL": @(OpenVPNAdapterErrorTLSAuthFail), - @"CERT_VERIFY_FAIL": @(OpenVPNAdapterErrorCertVerifyFail), - @"PEM_PASSWORD_FAIL": @(OpenVPNAdapterErrorPEMPasswordFail), - @"AUTH_FAILED": @(OpenVPNAdapterErrorAuthFailed), - @"CLIENT_HALT": @(OpenVPNAdapterErrorClientHalt), - @"CLIENT_RESTART": @(OpenVPNAdapterErrorClientRestart), - @"RELAY": @(OpenVPNAdapterErrorRelay), - @"RELAY_ERROR": @(OpenVPNAdapterErrorRelayError), - @"N_PAUSE": @(OpenVPNAdapterErrorPauseNumber), - @"N_RECONNECT": @(OpenVPNAdapterErrorReconnectNumber), - @"N_KEY_LIMIT_RENEG": @(OpenVPNAdapterErrorKeyLimitRenegNumber), - @"KEY_STATE_ERROR": @(OpenVPNAdapterErrorKeyStateError), - @"PROXY_ERROR": @(OpenVPNAdapterErrorProxyError), - @"PROXY_NEED_CREDS": @(OpenVPNAdapterErrorProxyNeedCreds), - @"KEV_NEGOTIATE_ERROR": @(OpenVPNAdapterErrorKevNegotiateError), - @"KEV_PENDING_ERROR": @(OpenVPNAdapterErrorKevPendingError), - @"N_KEV_EXPIRE": @(OpenVPNAdapterErrorKevExpireNumber), - @"PKTID_INVALID": @(OpenVPNAdapterErrorPKTIDInvalid), - @"PKTID_BACKTRACK": @(OpenVPNAdapterErrorPKTIDBacktrack), - @"PKTID_EXPIRE": @(OpenVPNAdapterErrorPKTIDExpire), - @"PKTID_REPLAY": @(OpenVPNAdapterErrorPKTIDReplay), - @"PKTID_TIME_BACKTRACK": @(OpenVPNAdapterErrorPKTIDTimeBacktrack), - @"DYNAMIC_CHALLENGE": @(OpenVPNAdapterErrorDynamicChallenge), - @"EPKI_ERROR": @(OpenVPNAdapterErrorEPKIError), - @"EPKI_INVALID_ALIAS": @(OpenVPNAdapterErrorEPKIInvalidAlias), - }; + NSDictionary *errors = @{@"NETWORK_RECV_ERROR": @(OpenVPNAdapterErrorNetworkRecvError), + @"NETWORK_EOF_ERROR": @(OpenVPNAdapterErrorNetworkEOFError), + @"NETWORK_SEND_ERROR": @(OpenVPNAdapterErrorNetworkSendError), + @"NETWORK_UNAVAILABLE": @(OpenVPNAdapterErrorNetworkUnavailable), + @"DECRYPT_ERROR": @(OpenVPNAdapterErrorDecryptError), + @"HMAC_ERROR": @(OpenVPNAdapterErrorDecryptError), + @"REPLAY_ERROR": @(OpenVPNAdapterErrorReplayError), + @"BUFFER_ERROR": @(OpenVPNAdapterErrorBufferError), + @"CC_ERROR": @(OpenVPNAdapterErrorCCError), + @"BAD_SRC_ADDR": @(OpenVPNAdapterErrorBadSrcAddr), + @"COMPRESS_ERROR": @(OpenVPNAdapterErrorCompressError), + @"RESOLVE_ERROR": @(OpenVPNAdapterErrorResolveError), + @"SOCKET_PROTECT_ERROR": @(OpenVPNAdapterErrorSocketProtectError), + @"TUN_READ_ERROR": @(OpenVPNAdapterErrorTUNReadError), + @"TUN_WRITE_ERROR": @(OpenVPNAdapterErrorTUNWriteError), + @"TUN_FRAMING_ERROR": @(OpenVPNAdapterErrorTUNFramingError), + @"TUN_SETUP_FAILED": @(OpenVPNAdapterErrorTUNSetupFailed), + @"TUN_IFACE_CREATE": @(OpenVPNAdapterErrorTUNIfaceCreate), + @"TUN_IFACE_DISABLED": @(OpenVPNAdapterErrorTUNIfaceDisabled), + @"TUN_ERROR": @(OpenVPNAdapterErrorTUNError), + @"TAP_NOT_SUPPORTED": @(OpenVPNAdapterErrorTAPNotSupported), + @"REROUTE_GW_NO_DNS": @(OpenVPNAdapterErrorRerouteGatewayNoDns), + @"TRANSPORT_ERROR": @(OpenVPNAdapterErrorTransportError), + @"TCP_OVERFLOW": @(OpenVPNAdapterErrorTCPOverflow), + @"TCP_SIZE_ERROR": @(OpenVPNAdapterErrorTCPSizeError), + @"TCP_CONNECT_ERROR": @(OpenVPNAdapterErrorTCPConnectError), + @"UDP_CONNECT_ERROR": @(OpenVPNAdapterErrorUDPConnectError), + @"SSL_ERROR": @(OpenVPNAdapterErrorSSLError), + @"SSL_PARTIAL_WRITE": @(OpenVPNAdapterErrorSSLPartialWrite), + @"ENCAPSULATION_ERROR": @(OpenVPNAdapterErrorEncapsulationError), + @"EPKI_CERT_ERROR": @(OpenVPNAdapterErrorEPKICertError), + @"EPKI_SIGN_ERROR": @(OpenVPNAdapterErrorEPKISignError), + @"HANDSHAKE_TIMEOUT": @(OpenVPNAdapterErrorHandshakeTimeout), + @"KEEPALIVE_TIMEOUT": @(OpenVPNAdapterErrorKeepaliveTimeout), + @"INACTIVE_TIMEOUT": @(OpenVPNAdapterErrorInactiveTimeout), + @"CONNECTION_TIMEOUT": @(OpenVPNAdapterErrorConnectionTimeout), + @"PRIMARY_EXPIRE": @(OpenVPNAdapterErrorPrimaryExpire), + @"TLS_VERSION_MIN": @(OpenVPNAdapterErrorTLSVersionMin), + @"TLS_AUTH_FAIL": @(OpenVPNAdapterErrorTLSAuthFail), + @"CERT_VERIFY_FAIL": @(OpenVPNAdapterErrorCertVerifyFail), + @"PEM_PASSWORD_FAIL": @(OpenVPNAdapterErrorPEMPasswordFail), + @"AUTH_FAILED": @(OpenVPNAdapterErrorAuthFailed), + @"CLIENT_HALT": @(OpenVPNAdapterErrorClientHalt), + @"CLIENT_RESTART": @(OpenVPNAdapterErrorClientRestart), + @"RELAY": @(OpenVPNAdapterErrorRelay), + @"RELAY_ERROR": @(OpenVPNAdapterErrorRelayError), + @"N_PAUSE": @(OpenVPNAdapterErrorPauseNumber), + @"N_RECONNECT": @(OpenVPNAdapterErrorReconnectNumber), + @"N_KEY_LIMIT_RENEG": @(OpenVPNAdapterErrorKeyLimitRenegNumber), + @"KEY_STATE_ERROR": @(OpenVPNAdapterErrorKeyStateError), + @"PROXY_ERROR": @(OpenVPNAdapterErrorProxyError), + @"PROXY_NEED_CREDS": @(OpenVPNAdapterErrorProxyNeedCreds), + @"KEV_NEGOTIATE_ERROR": @(OpenVPNAdapterErrorKevNegotiateError), + @"KEV_PENDING_ERROR": @(OpenVPNAdapterErrorKevPendingError), + @"N_KEV_EXPIRE": @(OpenVPNAdapterErrorKevExpireNumber), + @"PKTID_INVALID": @(OpenVPNAdapterErrorPKTIDInvalid), + @"PKTID_BACKTRACK": @(OpenVPNAdapterErrorPKTIDBacktrack), + @"PKTID_EXPIRE": @(OpenVPNAdapterErrorPKTIDExpire), + @"PKTID_REPLAY": @(OpenVPNAdapterErrorPKTIDReplay), + @"PKTID_TIME_BACKTRACK": @(OpenVPNAdapterErrorPKTIDTimeBacktrack), + @"DYNAMIC_CHALLENGE": @(OpenVPNAdapterErrorDynamicChallenge), + @"EPKI_ERROR": @(OpenVPNAdapterErrorEPKIError), + @"EPKI_INVALID_ALIAS": @(OpenVPNAdapterErrorEPKIInvalidAlias)}; OpenVPNAdapterError error = errors[errorName] != nil ? (OpenVPNAdapterError)[errors[errorName] integerValue] : OpenVPNAdapterErrorUnknown; return error; } - (NSString *)reasonForError:(OpenVPNAdapterError)error { - // TODO: Add missing error reasons switch (error) { case OpenVPNAdapterErrorConfigurationFailure: return @"See OpenVPN error message for more details."; case OpenVPNAdapterErrorCredentialsFailure: return @"See OpenVPN error message for more details."; @@ -786,28 +734,85 @@ static void socketCallback(CFSocketRef socket, CFSocketCallBackType type, CFData } } -- (NSString *)subnetFromPrefixLength:(NSNumber *)prefixLength { - std::string subnet = openvpn::IPv4::Addr::netmask_from_prefix_len([prefixLength intValue]).to_string(); - return [NSString stringWithUTF8String:subnet.c_str()]; -} - -- (uint8_t)protocolFamilyForVersion:(uint32_t)version { - switch (version) { - case 4: return PF_INET; - case 6: return PF_INET6; - default: return PF_UNSPEC; +- (NSMutableArray *)ipv4LocalAddresses { + if (!_ipv4LocalAddresses) { + _ipv4LocalAddresses = [[NSMutableArray alloc] init]; } -} - -- (void)performAsyncBlock:(void (^)())block { - dispatch_queue_t mainQueue = dispatch_get_main_queue(); - dispatch_async(mainQueue, block); + return _ipv4LocalAddresses; } -#pragma mark Deallocation +- (NSMutableArray *)ipv4SubnetMasks { + if (!_ipv4SubnetMasks) { + _ipv4SubnetMasks = [[NSMutableArray alloc] init]; + } + return _ipv4SubnetMasks; +} + +- (NSMutableArray *)ipv4IncludedRoutes { + if (!_ipv4IncludedRoutes) { + _ipv4IncludedRoutes = [[NSMutableArray alloc] init]; + } + return _ipv4IncludedRoutes; +} + +- (NSMutableArray *)ipv4ExcludedRoutes { + if (!_ipv4ExcludedRoutes) { + _ipv4ExcludedRoutes = [[NSMutableArray alloc] init]; + } + return _ipv4ExcludedRoutes; +} + +- (NSMutableArray *)ipv6LocalAddresses { + if (!_ipv6LocalAddresses) { + _ipv6LocalAddresses = [[NSMutableArray alloc] init]; + } + return _ipv6LocalAddresses; +} + +- (NSMutableArray *)ipv6NetworkPrefixLengths { + if (!_ipv6NetworkPrefixLengths) { + _ipv6NetworkPrefixLengths = [[NSMutableArray alloc] init]; + } + return _ipv6NetworkPrefixLengths; +} + +- (NSMutableArray *)ipv6IncludedRoutes { + if (!_ipv6IncludedRoutes) { + _ipv6IncludedRoutes = [[NSMutableArray alloc] init]; + } + return _ipv6IncludedRoutes; +} + +- (NSMutableArray *)ipv6ExcludedRoutes { + if (!_ipv6ExcludedRoutes) { + _ipv6ExcludedRoutes = [[NSMutableArray alloc] init]; + } + return _ipv6ExcludedRoutes; +} + +- (NSMutableArray *)dnsServers { + if (!_dnsServers) { + _dnsServers = [[NSMutableArray alloc] init]; + } + return _dnsServers; +} + +- (NSMutableArray *)searchDomains { + if (!_searchDomains) { + _searchDomains = [[NSMutableArray alloc] init]; + } + return _searchDomains; +} + +- (NSMutableArray *)proxyExceptionList { + if (!_proxyExceptionList) { + _proxyExceptionList = [[NSMutableArray alloc] init]; + } + return _proxyExceptionList; +} - (void)dealloc { - delete self.vpnClient; + delete _client; } @end diff --git a/OpenVPN Adapter/OpenVPNClient.h b/OpenVPN Adapter/OpenVPNClient.h deleted file mode 100644 index c9741e9..0000000 --- a/OpenVPN Adapter/OpenVPNClient.h +++ /dev/null @@ -1,69 +0,0 @@ -// -// OpenVPNClient.h -// OpenVPN Adapter -// -// Created by Sergey Abramchuk on 11.02.17. -// -// - -#import -#import - -using namespace openvpn; - -class OpenVPNClient : public ClientAPI::OpenVPNClient -{ -public: - OpenVPNClient(void * adapter); - - virtual bool tun_builder_new() override; - - virtual bool tun_builder_set_remote_address(const std::string& address, bool ipv6) override; - virtual bool tun_builder_add_address(const std::string& address, - int prefix_length, - const std::string& gateway, - bool ipv6, - bool net30) override; - virtual bool tun_builder_reroute_gw(bool ipv4, - bool ipv6, - unsigned int flags) override; - virtual bool tun_builder_add_route(const std::string& address, - int prefix_length, - int metric, - bool ipv6) override; - virtual bool tun_builder_exclude_route(const std::string& address, - int prefix_length, - int metric, - bool ipv6) override; - virtual bool tun_builder_add_dns_server(const std::string& address, bool ipv6) override; - virtual bool tun_builder_add_search_domain(const std::string& domain) override; - virtual bool tun_builder_set_mtu(int mtu) override; - virtual bool tun_builder_set_session_name(const std::string& name) override; - virtual bool tun_builder_add_proxy_bypass(const std::string& bypass_host) override; - virtual bool tun_builder_set_proxy_auto_config_url(const std::string& url) override; - virtual bool tun_builder_set_proxy_http(const std::string& host, int port) override; - virtual bool tun_builder_set_proxy_https(const std::string& host, int port) override; - virtual bool tun_builder_add_wins_server(const std::string& address) override; - - virtual int tun_builder_establish() override; - - virtual bool tun_builder_persist() override; - virtual void tun_builder_establish_lite() override; - - virtual void tun_builder_teardown(bool disconnect) override; - - virtual bool socket_protect(int socket) override; - - virtual bool pause_on_connection_timeout() override; - - virtual void external_pki_cert_request(ClientAPI::ExternalPKICertRequest& certreq) override; - virtual void external_pki_sign_request(ClientAPI::ExternalPKISignRequest& signreq) override; - - virtual void event(const ClientAPI::Event& ev) override; - virtual void log(const ClientAPI::LogInfo& log) override; - - virtual void clock_tick() override; - -private: - void* adapter; -}; diff --git a/OpenVPN Adapter/OpenVPNClient.mm b/OpenVPN Adapter/OpenVPNClient.mm deleted file mode 100644 index 6f01719..0000000 --- a/OpenVPN Adapter/OpenVPNClient.mm +++ /dev/null @@ -1,121 +0,0 @@ -// -// OpenVPNClient.m -// OpenVPN Adapter -// -// Created by Sergey Abramchuk on 11.02.17. -// -// - -#import - -#import "OpenVPNAdapter+Internal.h" -#import "OpenVPNClient.h" - -OpenVPNClient::OpenVPNClient(void *adapter) : ClientAPI::OpenVPNClient() { - this->adapter = adapter; -} - -bool OpenVPNClient::tun_builder_new() { - return [(__bridge OpenVPNAdapter *)adapter configureSockets]; -} - -bool OpenVPNClient::tun_builder_set_remote_address(const std::string &address, bool ipv6) { - NSString *remoteAddress = [NSString stringWithUTF8String:address.c_str()]; - return [(__bridge OpenVPNAdapter *)adapter setRemoteAddress:remoteAddress isIPv6:ipv6]; -} - -bool OpenVPNClient::tun_builder_add_address(const std::string &address, int prefix_length, const std::string &gateway, bool ipv6, bool net30) { - NSString *localAddress = [NSString stringWithUTF8String:address.c_str()]; - NSString *gatewayAddress = [NSString stringWithUTF8String:gateway.c_str()]; - - return [(__bridge OpenVPNAdapter *)adapter addLocalAddress:localAddress prefixLength:@(prefix_length) gateway:gatewayAddress isIPv6:ipv6]; -} - -bool OpenVPNClient::tun_builder_reroute_gw(bool ipv4, bool ipv6, unsigned int flags) { - return [(__bridge OpenVPNAdapter *)adapter defaultGatewayRerouteIPv4:ipv4 rerouteIPv6:ipv6]; -} - -bool OpenVPNClient::tun_builder_add_route(const std::string& address, int prefix_length, int metric, bool ipv6) { - NSString *route = [NSString stringWithUTF8String:address.c_str()]; - return [(__bridge OpenVPNAdapter *)adapter addRoute:route prefixLength:@(prefix_length) isIPv6:ipv6]; -} - -bool OpenVPNClient::tun_builder_exclude_route(const std::string& address, int prefix_length, int metric, bool ipv6) { - NSString *route = [NSString stringWithUTF8String:address.c_str()]; - return [(__bridge OpenVPNAdapter *)adapter excludeRoute:route prefixLength:@(prefix_length) isIPv6:ipv6]; -} - -bool OpenVPNClient::tun_builder_add_dns_server(const std::string& address, bool ipv6) { - NSString *dnsAddress = [NSString stringWithUTF8String:address.c_str()]; - return [(__bridge OpenVPNAdapter *)adapter addDNSAddress:dnsAddress isIPv6:ipv6]; -} - -bool OpenVPNClient::tun_builder_add_search_domain(const std::string& domain) { - NSString *searchDomain = [NSString stringWithUTF8String:domain.c_str()]; - return [(__bridge OpenVPNAdapter *)adapter addSearchDomain:searchDomain]; -} - -bool OpenVPNClient::tun_builder_set_mtu(int mtu) { - return [(__bridge OpenVPNAdapter *)adapter setMTU:@(mtu)]; -} - -bool OpenVPNClient::tun_builder_set_session_name(const std::string& name) { - return true; -} - -bool OpenVPNClient::tun_builder_add_proxy_bypass(const std::string& bypass_host) { - return true; -} - -bool OpenVPNClient::tun_builder_set_proxy_auto_config_url(const std::string& url) { - return true; -} - -bool OpenVPNClient::tun_builder_set_proxy_http(const std::string& host, int port) { - return true; -} - -bool OpenVPNClient::tun_builder_set_proxy_https(const std::string& host, int port) { - return true; -} - -bool OpenVPNClient::tun_builder_add_wins_server(const std::string& address) { - return true; -} - -int OpenVPNClient::tun_builder_establish() { - return (int)[(__bridge OpenVPNAdapter *)adapter establishTunnel]; -} - -bool OpenVPNClient::tun_builder_persist() { - return true; -} - -void OpenVPNClient::tun_builder_establish_lite() { } - -void OpenVPNClient::tun_builder_teardown(bool disconnect) { - [(__bridge OpenVPNAdapter *)adapter teardownTunnel:disconnect]; -} - -bool OpenVPNClient::socket_protect(int socket) { - return true; -} - -bool OpenVPNClient::pause_on_connection_timeout() { - return false; -} - -void OpenVPNClient::external_pki_cert_request(ClientAPI::ExternalPKICertRequest& certreq) { } -void OpenVPNClient::external_pki_sign_request(ClientAPI::ExternalPKISignRequest& signreq) { } - -void OpenVPNClient::event(const ClientAPI::Event& ev) { - [(__bridge OpenVPNAdapter* )adapter handleEvent:&ev]; -} - -void OpenVPNClient::log(const ClientAPI::LogInfo& log) { - [(__bridge OpenVPNAdapter* )adapter handleLog:&log]; -} - -void OpenVPNClient::clock_tick() { - [(__bridge OpenVPNAdapter* )adapter tick]; -} diff --git a/OpenVPN Adapter/OpenVPNTunnelSettings.h b/OpenVPN Adapter/OpenVPNTunnelSettings.h deleted file mode 100644 index e8fbd40..0000000 --- a/OpenVPN Adapter/OpenVPNTunnelSettings.h +++ /dev/null @@ -1,23 +0,0 @@ -// -// OpenVPNTunnelSettings.h -// OpenVPN Adapter -// -// Created by Sergey Abramchuk on 26.02.17. -// -// - -#import - -@interface OpenVPNTunnelSettings : NSObject - -@property (nonatomic) BOOL initialized; - -@property (readonly, strong, nonatomic) NSMutableArray *localAddresses; -@property (readonly, strong, nonatomic) NSMutableArray *prefixLengths; - -@property (readonly, strong, nonatomic) NSMutableArray *includedRoutes; -@property (readonly, strong, nonatomic) NSMutableArray *excludedRoutes; - -@property (readonly, strong, nonatomic) NSMutableArray *dnsAddresses; - -@end diff --git a/OpenVPN Adapter/OpenVPNTunnelSettings.m b/OpenVPN Adapter/OpenVPNTunnelSettings.m deleted file mode 100644 index f8d105d..0000000 --- a/OpenVPN Adapter/OpenVPNTunnelSettings.m +++ /dev/null @@ -1,30 +0,0 @@ -// -// OpenVPNTunnelSettings.m -// OpenVPN Adapter -// -// Created by Sergey Abramchuk on 26.02.17. -// -// - -#import "OpenVPNTunnelSettings.h" - -@implementation OpenVPNTunnelSettings - -- (instancetype)init -{ - self = [super init]; - if (self) { - _initialized = NO; - - _localAddresses = [NSMutableArray new]; - _prefixLengths = [NSMutableArray new]; - - _includedRoutes = [NSMutableArray new]; - _excludedRoutes = [NSMutableArray new]; - - _dnsAddresses = [NSMutableArray new]; - } - return self; -} - -@end diff --git a/OpenVPN Adapter/Umbrella-Header.h b/OpenVPN Adapter/Umbrella-Header.h index 640441d..95b98cf 100644 --- a/OpenVPN Adapter/Umbrella-Header.h +++ b/OpenVPN Adapter/Umbrella-Header.h @@ -32,7 +32,6 @@ FOUNDATION_EXPORT const unsigned char OpenVPNAdapterVersionString[]; #import #import #import -#import #import #import #import