summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorBug Magnet <marco.nikic@mullvad.net>2025-05-19 13:39:23 +0200
committerBug Magnet <marco.nikic@mullvad.net>2025-05-23 10:04:35 +0200
commite99b6504f0e943dc5967d1449b90dfaed3448c66 (patch)
tree82234ed311f06cd8e70186e22035ae4e7cf2aaff
parent0d8fe5e10a17a3d32f079fef1ab40bfb4692d7af (diff)
downloadmullvadvpn-e99b6504f0e943dc5967d1449b90dfaed3448c66.tar.xz
mullvadvpn-e99b6504f0e943dc5967d1449b90dfaed3448c66.zip
Add UITests for QUIC, add ability to block Wireguard traffic
-rw-r--r--ios/MullvadVPNTests/MullvadREST/Relay/ObfuscatorPortSelectorTests.swift18
-rw-r--r--ios/MullvadVPNUITests/Base/BaseUITestCase.swift4
-rw-r--r--ios/MullvadVPNUITests/Networking/FirewallRule.swift21
-rw-r--r--ios/MullvadVPNUITests/Networking/Networking.swift17
-rw-r--r--ios/MullvadVPNUITests/Pages/TunnelControlPage.swift4
-rw-r--r--ios/MullvadVPNUITests/RelayTests.swift43
6 files changed, 92 insertions, 15 deletions
diff --git a/ios/MullvadVPNTests/MullvadREST/Relay/ObfuscatorPortSelectorTests.swift b/ios/MullvadVPNTests/MullvadREST/Relay/ObfuscatorPortSelectorTests.swift
index bafc9cc1b6..9fa4edb54d 100644
--- a/ios/MullvadVPNTests/MullvadREST/Relay/ObfuscatorPortSelectorTests.swift
+++ b/ios/MullvadVPNTests/MullvadREST/Relay/ObfuscatorPortSelectorTests.swift
@@ -14,6 +14,7 @@ import XCTest
final class ObfuscatorPortSelectorTests: XCTestCase {
let defaultWireguardPort: RelayConstraint<UInt16> = .only(56)
+ let defaultQuicPort: RelayConstraint<UInt16> = .only(443)
let sampleRelays = ServerRelaysResponseStubs.sampleRelays
var tunnelSettings = LatestTunnelSettings()
@@ -175,4 +176,21 @@ final class ObfuscatorPortSelectorTests: XCTestCase {
XCTAssertEqual(obfuscationResult.wireguard.relays.count, sampleRelays.wireguard.relays.count)
}
+
+ // MARK: QUIC
+
+ func testObfuscateQuicOverPort443() throws {
+ tunnelSettings.wireGuardObfuscation = WireGuardObfuscationSettings(
+ state: .quic
+ )
+
+ let obfuscationResult = try ObfuscatorPortSelector(
+ relays: sampleRelays
+ ).obfuscate(
+ tunnelSettings: tunnelSettings,
+ connectionAttemptCount: 0
+ )
+
+ XCTAssertEqual(obfuscationResult.port, defaultQuicPort)
+ }
}
diff --git a/ios/MullvadVPNUITests/Base/BaseUITestCase.swift b/ios/MullvadVPNUITests/Base/BaseUITestCase.swift
index fd27c45900..d9265ff8ea 100644
--- a/ios/MullvadVPNUITests/Base/BaseUITestCase.swift
+++ b/ios/MullvadVPNUITests/Base/BaseUITestCase.swift
@@ -31,6 +31,10 @@ class BaseUITestCase: XCTestCase {
/// Default relay to use in tests
static let testsDefaultRelayName = "se-got-wg-001"
+ static let testsDefaultQuicCountryName = "Relay Software Country"
+ static let testsDefaultQuicCityName = "Relay Software city"
+ static let testsDefaultQuicRelayName = "se-got-wg-881"
+
/// True when the current test case is capturing packets
private var currentTestCaseShouldCapturePackets = false
diff --git a/ios/MullvadVPNUITests/Networking/FirewallRule.swift b/ios/MullvadVPNUITests/Networking/FirewallRule.swift
index 51d79c1931..eac79f9645 100644
--- a/ios/MullvadVPNUITests/Networking/FirewallRule.swift
+++ b/ios/MullvadVPNUITests/Networking/FirewallRule.swift
@@ -12,13 +12,13 @@ import XCTest
struct FirewallRule {
let fromIPAddress: String
let toIPAddress: String
- let protocols: [NetworkTransportProtocol]
+ let protocols: [TransportProtocol]
/// - Parameters:
/// - fromIPAddress: Block traffic originating from this source IP address.
/// - toIPAddress: Block traffic to this destination IP address.
/// - protocols: Protocols which should be blocked. If none is specified all will be blocked.
- private init(fromIPAddress: String, toIPAddress: String, protocols: [NetworkTransportProtocol]) {
+ private init(fromIPAddress: String, toIPAddress: String, protocols: [TransportProtocol]) {
self.fromIPAddress = fromIPAddress
self.toIPAddress = toIPAddress
self.protocols = protocols
@@ -35,7 +35,7 @@ struct FirewallRule {
return FirewallRule(
fromIPAddress: deviceIPAddress,
toIPAddress: apiIPAddress,
- protocols: [.TCP]
+ protocols: [.transport(.TCP)]
)
}
@@ -45,7 +45,18 @@ struct FirewallRule {
return FirewallRule(
fromIPAddress: deviceIPAddress,
toIPAddress: toIPAddress,
- protocols: [.ICMP, .TCP, .UDP]
+ protocols: [.transport(.ICMP), .transport(.TCP), .transport(.UDP)]
+ )
+ }
+
+ public static func makeBlockWireGuardTrafficRule(
+ fromIPAddress: String,
+ toIPAddress: String
+ ) throws -> FirewallRule {
+ FirewallRule(
+ fromIPAddress: fromIPAddress,
+ toIPAddress: toIPAddress,
+ protocols: [.application(.wireguard)]
)
}
@@ -55,7 +66,7 @@ struct FirewallRule {
return FirewallRule(
fromIPAddress: deviceIPAddress,
toIPAddress: toIPAddress,
- protocols: [.UDP]
+ protocols: [.transport(.UDP)]
)
}
}
diff --git a/ios/MullvadVPNUITests/Networking/Networking.swift b/ios/MullvadVPNUITests/Networking/Networking.swift
index 93d8eba7ff..df814f70c7 100644
--- a/ios/MullvadVPNUITests/Networking/Networking.swift
+++ b/ios/MullvadVPNUITests/Networking/Networking.swift
@@ -10,10 +10,27 @@ import Foundation
import Network
import XCTest
+enum TransportProtocol: Codable {
+ case transport(NetworkTransportProtocol)
+ case application(ApplicationProtocol)
+
+ var rawValue: String {
+ switch self {
+ case let .transport(transport): transport.rawValue
+ case let .application(application): application.rawValue
+ }
+ }
+}
+
+enum ApplicationProtocol: String, Codable {
+ case wireguard
+}
+
enum NetworkTransportProtocol: String, Codable {
case TCP = "tcp"
case UDP = "udp"
case ICMP = "icmp"
+ case ICMP6 = "icmp_v6"
}
enum NetworkingError: Error {
diff --git a/ios/MullvadVPNUITests/Pages/TunnelControlPage.swift b/ios/MullvadVPNUITests/Pages/TunnelControlPage.swift
index c2996c6741..f734ccd44e 100644
--- a/ios/MullvadVPNUITests/Pages/TunnelControlPage.swift
+++ b/ios/MullvadVPNUITests/Pages/TunnelControlPage.swift
@@ -71,10 +71,6 @@ class TunnelControlPage: Page {
return connectionAttempts
}
- func getInIPv4AddressLabel() -> String {
- app.staticTexts[AccessibilityIdentifier.connectionPanelInAddressRow].label.components(separatedBy: ":")[0]
- }
-
@discardableResult override init(_ app: XCUIApplication) {
super.init(app)
diff --git a/ios/MullvadVPNUITests/RelayTests.swift b/ios/MullvadVPNUITests/RelayTests.swift
index 17c0da2d2e..fe3d18c509 100644
--- a/ios/MullvadVPNUITests/RelayTests.swift
+++ b/ios/MullvadVPNUITests/RelayTests.swift
@@ -179,7 +179,7 @@ class RelayTests: LoggedInWithTimeUITestCase {
let connectedToIPAddress = TunnelControlPage(app)
.tapRelayStatusExpandCollapseButton()
- .getInIPv4AddressLabel()
+ .getInIPAddressFromConnectionStatus()
try Networking.verifyCanAccessInternet()
@@ -235,7 +235,7 @@ class RelayTests: LoggedInWithTimeUITestCase {
let connectedToIPAddress = TunnelControlPage(app)
.tapRelayStatusExpandCollapseButton()
- .getInIPv4AddressLabel()
+ .getInIPAddressFromConnectionStatus()
try Networking.verifyCanAccessInternet()
@@ -337,6 +337,8 @@ class RelayTests: LoggedInWithTimeUITestCase {
.tapWireGuardObfuscationOffCell()
}
+ let deviceIPAddress = try FirewallClient().getDeviceIPAddress()
+
HeaderBar(app)
.tapSettingsButton()
@@ -351,18 +353,47 @@ class RelayTests: LoggedInWithTimeUITestCase {
SettingsPage(app)
.tapDoneButton()
+ startPacketCapture()
+
TunnelControlPage(app)
- .tapConnectButton()
+ .tapSelectLocationButton()
+
+ SelectLocationPage(app)
+ .tapLocationCellExpandButton(withName: BaseUITestCase.testsDefaultQuicCountryName)
+ .tapLocationCellExpandButton(withName: BaseUITestCase.testsDefaultQuicCityName)
+ .tapLocationCell(withName: BaseUITestCase.testsDefaultQuicRelayName)
allowAddVPNConfigurationsIfAsked()
TunnelControlPage(app)
.waitForConnectedLabel()
- try Networking.verifyCanAccessInternet()
+ let connectedToIPAddress = TunnelControlPage(app)
+ .tapRelayStatusExpandCollapseButton()
+ .getInIPAddressFromConnectionStatus()
+ let relayIPAddress = TunnelControlPage(app)
+ .getInIPAddressFromConnectionStatus()
+
+ // Disconnect in order to create firewall rules, otherwise the test router cannot be reached
TunnelControlPage(app)
.tapDisconnectButton()
+
+ try FirewallClient().createRule(
+ FirewallRule.makeBlockWireGuardTrafficRule(
+ fromIPAddress: deviceIPAddress,
+ toIPAddress: relayIPAddress
+ )
+ )
+
+ // The VPN connects despite the wireguard protocol being blocked, QUIC obfuscation is in the works
+ TunnelControlPage(app)
+ .tapConnectButton()
+ .waitForConnectedLabel()
+
+ try Networking.verifyCanAccessInternet()
+
+ try generateTraffic(to: connectedToIPAddress, on: 443, assertProtocol: .UDP)
}
/// Test automatic switching to TCP is functioning when UDP traffic to relay is blocked. This test first connects to a realy to get the IP address of it, in order to block UDP traffic to this relay.
@@ -607,10 +638,10 @@ extension RelayTests {
// The capture will contain several streams where `other_addr` contains the IP the device connected to
// One stream will be for the source port, the other for the destination port
- let streamFromPeeerToRelay = try XCTUnwrap(
+ let streamFromPeerToRelay = try XCTUnwrap(
capturedStreams.filter { $0.destinationAddress == connectedToIPAddress && $0.destinationPort == port }.first
)
- XCTAssertTrue(streamFromPeeerToRelay.transportProtocol == transportProtocol)
+ XCTAssertTrue(streamFromPeerToRelay.transportProtocol == transportProtocol)
}
} // swiftlint:disable:this file_length