diff --git a/TunnelKit/Sources/Protocols/OpenVPN/Configuration.swift b/TunnelKit/Sources/Protocols/OpenVPN/Configuration.swift index 3b94188..26cd931 100644 --- a/TunnelKit/Sources/Protocols/OpenVPN/Configuration.swift +++ b/TunnelKit/Sources/Protocols/OpenVPN/Configuration.swift @@ -178,6 +178,9 @@ extension OpenVPN { /// The cipher algorithm for data encryption. public var cipher: Cipher? + /// The set of supported cipher algorithms for data encryption (2.5.). + public var dataCiphers: [Cipher]? + /// The digest algorithm for HMAC. public var digest: Digest? @@ -298,6 +301,7 @@ extension OpenVPN { public func build() -> Configuration { return Configuration( cipher: cipher, + dataCiphers: dataCiphers, digest: digest, compressionFraming: compressionFraming, compressionAlgorithm: compressionAlgorithm, @@ -355,6 +359,9 @@ extension OpenVPN { /// - Seealso: `ConfigurationBuilder.cipher` public let cipher: Cipher? + /// - Seealso: `ConfigurationBuilder.dataCiphers` + public let dataCiphers: [Cipher]? + /// - Seealso: `ConfigurationBuilder.digest` public let digest: Digest? @@ -476,6 +483,7 @@ extension OpenVPN.Configuration { public func builder() -> OpenVPN.ConfigurationBuilder { var builder = OpenVPN.ConfigurationBuilder() builder.cipher = cipher + builder.dataCiphers = dataCiphers builder.digest = digest builder.compressionFraming = compressionFraming builder.compressionAlgorithm = compressionAlgorithm diff --git a/TunnelKit/Sources/Protocols/OpenVPN/ConfigurationParser.swift b/TunnelKit/Sources/Protocols/OpenVPN/ConfigurationParser.swift index 6a15ae7..700db47 100644 --- a/TunnelKit/Sources/Protocols/OpenVPN/ConfigurationParser.swift +++ b/TunnelKit/Sources/Protocols/OpenVPN/ConfigurationParser.swift @@ -42,6 +42,8 @@ extension OpenVPN { static let cipher = NSRegularExpression("^cipher +[^,\\s]+") + static let dataCiphers = NSRegularExpression("^(data-ciphers|ncp-ciphers) +[^,\\s]+(:[^,\\s]+)*") + static let auth = NSRegularExpression("^auth +[\\w\\-]+") static let compLZO = NSRegularExpression("^comp-lzo.*") @@ -199,6 +201,7 @@ extension OpenVPN { var currentBlockName: String? var currentBlock: [String] = [] + var optDataCiphers: [Cipher]? var optCipher: Cipher? var optDigest: Digest? var optCompressionFraming: CompressionFraming? @@ -345,8 +348,19 @@ extension OpenVPN { return } optCipher = Cipher(rawValue: rawValue.uppercased()) - if optCipher == nil { - unsupportedError = ConfigurationError.unsupportedConfiguration(option: "cipher \(rawValue)") + } + Regex.dataCiphers.enumerateArguments(in: line) { + isHandled = true + guard let rawValue = $0.first else { + return + } + let rawCiphers = rawValue.components(separatedBy: ":") + optDataCiphers = [] + rawCiphers.forEach { + guard let cipher = Cipher(rawValue: $0.uppercased()) else { + return + } + optDataCiphers?.append(cipher) } } Regex.auth.enumerateArguments(in: line) { @@ -610,8 +624,8 @@ extension OpenVPN { guard let _ = optCA else { throw ConfigurationError.missingConfiguration(option: "ca") } - guard let _ = optCipher else { - throw ConfigurationError.missingConfiguration(option: "cipher") + guard optCipher != nil || !(optDataCiphers?.isEmpty ?? false) else { + throw ConfigurationError.missingConfiguration(option: "cipher or data-ciphers") } } @@ -622,6 +636,7 @@ extension OpenVPN { // MARK: General sessionBuilder.cipher = optCipher + sessionBuilder.dataCiphers = optDataCiphers sessionBuilder.digest = optDigest sessionBuilder.compressionFraming = optCompressionFraming sessionBuilder.compressionAlgorithm = optCompressionAlgorithm