diff options
Diffstat (limited to 'tunnel/src/main/java/com/wireguard/config/Interface.java')
-rw-r--r-- | tunnel/src/main/java/com/wireguard/config/Interface.java | 53 |
1 files changed, 41 insertions, 12 deletions
diff --git a/tunnel/src/main/java/com/wireguard/config/Interface.java b/tunnel/src/main/java/com/wireguard/config/Interface.java index c49357f7..53ca9111 100644 --- a/tunnel/src/main/java/com/wireguard/config/Interface.java +++ b/tunnel/src/main/java/com/wireguard/config/Interface.java @@ -1,5 +1,5 @@ /* - * Copyright © 2017-2019 WireGuard LLC. All Rights Reserved. + * Copyright © 2017-2025 WireGuard LLC. All Rights Reserved. * SPDX-License-Identifier: Apache-2.0 */ @@ -20,13 +20,11 @@ import java.util.LinkedHashSet; import java.util.List; import java.util.Locale; import java.util.Objects; +import java.util.Optional; import java.util.Set; +import java.util.stream.Collectors; import androidx.annotation.Nullable; -import java9.util.Lists; -import java9.util.Optional; -import java9.util.stream.Collectors; -import java9.util.stream.StreamSupport; /** * Represents the configuration for a WireGuard interface (an [Interface] block). Interfaces must @@ -42,6 +40,7 @@ public final class Interface { private final Set<InetNetwork> addresses; private final Set<InetAddress> dnsServers; + private final Set<String> dnsSearchDomains; private final Set<String> excludedApplications; private final Set<String> includedApplications; private final KeyPair keyPair; @@ -52,6 +51,7 @@ public final class Interface { // Defensively copy to ensure immutability even if the Builder is reused. addresses = Collections.unmodifiableSet(new LinkedHashSet<>(builder.addresses)); dnsServers = Collections.unmodifiableSet(new LinkedHashSet<>(builder.dnsServers)); + dnsSearchDomains = Collections.unmodifiableSet(new LinkedHashSet<>(builder.dnsSearchDomains)); excludedApplications = Collections.unmodifiableSet(new LinkedHashSet<>(builder.excludedApplications)); includedApplications = Collections.unmodifiableSet(new LinkedHashSet<>(builder.includedApplications)); keyPair = Objects.requireNonNull(builder.keyPair, "Interfaces must have a private key"); @@ -110,6 +110,7 @@ public final class Interface { final Interface other = (Interface) obj; return addresses.equals(other.addresses) && dnsServers.equals(other.dnsServers) + && dnsSearchDomains.equals(other.dnsSearchDomains) && excludedApplications.equals(other.excludedApplications) && includedApplications.equals(other.includedApplications) && keyPair.equals(other.keyPair) @@ -138,6 +139,16 @@ public final class Interface { } /** + * Returns the set of DNS search domains associated with the interface. + * + * @return a set of strings + */ + public Set<String> getDnsSearchDomains() { + // The collection is already immutable. + return dnsSearchDomains; + } + + /** * Returns the set of applications excluded from using the interface. * * @return a set of package names @@ -223,9 +234,8 @@ public final class Interface { if (!addresses.isEmpty()) sb.append("Address = ").append(Attribute.join(addresses)).append('\n'); if (!dnsServers.isEmpty()) { - final List<String> dnsServerStrings = StreamSupport.stream(dnsServers) - .map(InetAddress::getHostAddress) - .collect(Collectors.toUnmodifiableList()); + final List<String> dnsServerStrings = dnsServers.stream().map(InetAddress::getHostAddress).collect(Collectors.toList()); + dnsServerStrings.addAll(dnsSearchDomains); sb.append("DNS = ").append(Attribute.join(dnsServerStrings)).append('\n'); } if (!excludedApplications.isEmpty()) @@ -258,6 +268,8 @@ public final class Interface { // Defaults to an empty set. private final Set<InetAddress> dnsServers = new LinkedHashSet<>(); // Defaults to an empty set. + private final Set<String> dnsSearchDomains = new LinkedHashSet<>(); + // Defaults to an empty set. private final Set<String> excludedApplications = new LinkedHashSet<>(); // Defaults to an empty set. private final Set<String> includedApplications = new LinkedHashSet<>(); @@ -288,6 +300,16 @@ public final class Interface { return this; } + public Builder addDnsSearchDomain(final String dnsSearchDomain) { + dnsSearchDomains.add(dnsSearchDomain); + return this; + } + + public Builder addDnsSearchDomains(final Collection<String> dnsSearchDomains) { + this.dnsSearchDomains.addAll(dnsSearchDomains); + return this; + } + public Interface build() throws BadConfigException { if (keyPair == null) throw new BadConfigException(Section.INTERFACE, Location.PRIVATE_KEY, @@ -330,8 +352,15 @@ public final class Interface { public Builder parseDnsServers(final CharSequence dnsServers) throws BadConfigException { try { - for (final String dnsServer : Attribute.split(dnsServers)) - addDnsServer(InetAddresses.parse(dnsServer)); + for (final String dnsServer : Attribute.split(dnsServers)) { + try { + addDnsServer(InetAddresses.parse(dnsServer)); + } catch (final ParseException e) { + if (e.getParsingClass() != InetAddress.class || !InetAddresses.isHostname(dnsServer)) + throw e; + addDnsSearchDomain(dnsServer); + } + } return this; } catch (final ParseException e) { throw new BadConfigException(Section.INTERFACE, Location.DNS, e); @@ -339,11 +368,11 @@ public final class Interface { } public Builder parseExcludedApplications(final CharSequence apps) { - return excludeApplications(Lists.of(Attribute.split(apps))); + return excludeApplications(List.of(Attribute.split(apps))); } public Builder parseIncludedApplications(final CharSequence apps) { - return includeApplications(Lists.of(Attribute.split(apps))); + return includeApplications(List.of(Attribute.split(apps))); } public Builder parseListenPort(final String listenPort) throws BadConfigException { |