From 8e96fdc9de8ff9aaf5e4a7f376810d1232ec2d8d Mon Sep 17 00:00:00 2001 From: Mike Yu Date: Thu, 23 Feb 2023 09:05:09 +0000 Subject: [PATCH] Pass DoH information to DnsResolver Bug: 240259333 Test: atest ConnectivityCoverageTests Change-Id: I535275923ad4d689d90a2ce6a3216b90b810535c --- .../server/connectivity/DnsManager.java | 40 +++++++++++++++---- .../server/connectivity/DnsManagerTest.java | 19 +++++++-- 2 files changed, 48 insertions(+), 11 deletions(-) diff --git a/service/src/com/android/server/connectivity/DnsManager.java b/service/src/com/android/server/connectivity/DnsManager.java index ac022298e7..b95e3b1e6c 100644 --- a/service/src/com/android/server/connectivity/DnsManager.java +++ b/service/src/com/android/server/connectivity/DnsManager.java @@ -41,6 +41,7 @@ import android.net.Network; import android.net.NetworkCapabilities; import android.net.ResolverParamsParcel; import android.net.Uri; +import android.net.resolv.aidl.DohParamsParcel; import android.net.shared.PrivateDnsConfig; import android.os.Binder; import android.os.RemoteException; @@ -52,16 +53,17 @@ import android.util.Log; import android.util.Pair; import java.net.InetAddress; +import java.util.ArrayList; import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; +import java.util.List; import java.util.Map; import java.util.Set; import java.util.concurrent.ConcurrentHashMap; -import java.util.stream.Collectors; /** * Encapsulate the management of DNS settings for networks. @@ -382,15 +384,14 @@ public class DnsManager { paramsParcel.domains = getDomainStrings(lp.getDomains()); paramsParcel.tlsName = strictMode ? privateDnsCfg.hostname : ""; paramsParcel.tlsServers = - strictMode ? makeStrings( - Arrays.stream(privateDnsCfg.ips) - .filter((ip) -> lp.isReachable(ip)) - .collect(Collectors.toList())) + strictMode ? makeStrings(getReachableAddressList(privateDnsCfg.ips, lp)) : useTls ? paramsParcel.servers // Opportunistic : new String[0]; // Off paramsParcel.transportTypes = nc.getTransportTypes(); paramsParcel.meteredNetwork = nc.isMetered(); paramsParcel.interfaceNames = lp.getAllInterfaceNames().toArray(new String[0]); + paramsParcel.dohParams = makeDohParamsParcel(privateDnsCfg, lp); + // Prepare to track the validation status of the DNS servers in the // resolver config when private DNS is in opportunistic or strict mode. if (useTls) { @@ -404,15 +405,16 @@ public class DnsManager { } Log.d(TAG, String.format("sendDnsConfigurationForNetwork(%d, %s, %s, %d, %d, %d, %d, " - + "%d, %d, %s, %s, %s, %b, %s)", paramsParcel.netId, + + "%d, %d, %s, %s, %s, %b, %s, %s, %s, %s, %d)", paramsParcel.netId, Arrays.toString(paramsParcel.servers), Arrays.toString(paramsParcel.domains), paramsParcel.sampleValiditySeconds, paramsParcel.successThreshold, paramsParcel.minSamples, paramsParcel.maxSamples, paramsParcel.baseTimeoutMsec, paramsParcel.retryCount, paramsParcel.tlsName, Arrays.toString(paramsParcel.tlsServers), Arrays.toString(paramsParcel.transportTypes), paramsParcel.meteredNetwork, - Arrays.toString(paramsParcel.interfaceNames))); - + Arrays.toString(paramsParcel.interfaceNames), + paramsParcel.dohParams.name, Arrays.toString(paramsParcel.dohParams.ips), + paramsParcel.dohParams.dohpath, paramsParcel.dohParams.port)); try { mDnsResolver.setResolverConfiguration(paramsParcel); } catch (RemoteException | ServiceSpecificException e) { @@ -498,4 +500,26 @@ public class DnsManager { private static String[] getDomainStrings(String domains) { return (TextUtils.isEmpty(domains)) ? new String[0] : domains.split(" "); } + + @NonNull + private List getReachableAddressList(@NonNull InetAddress[] ips, + @NonNull LinkProperties lp) { + final ArrayList out = new ArrayList(Arrays.asList(ips)); + out.removeIf(ip -> !lp.isReachable(ip)); + return out; + } + + @NonNull + private DohParamsParcel makeDohParamsParcel(@NonNull PrivateDnsConfig cfg, + @NonNull LinkProperties lp) { + if (cfg.mode == PRIVATE_DNS_MODE_OFF) { + return new DohParamsParcel.Builder().build(); + } + return new DohParamsParcel.Builder() + .setName(cfg.dohName) + .setIps(makeStrings(getReachableAddressList(cfg.dohIps, lp))) + .setDohpath(cfg.dohPath) + .setPort(cfg.dohPort) + .build(); + } } diff --git a/tests/unit/java/com/android/server/connectivity/DnsManagerTest.java b/tests/unit/java/com/android/server/connectivity/DnsManagerTest.java index ea3d2dd06a..b47b97d605 100644 --- a/tests/unit/java/com/android/server/connectivity/DnsManagerTest.java +++ b/tests/unit/java/com/android/server/connectivity/DnsManagerTest.java @@ -54,6 +54,7 @@ import android.net.NetworkCapabilities; import android.net.ResolverOptionsParcel; import android.net.ResolverParamsParcel; import android.net.RouteInfo; +import android.net.resolv.aidl.DohParamsParcel; import android.net.shared.PrivateDnsConfig; import android.os.Build; import android.provider.Settings; @@ -327,8 +328,16 @@ public class DnsManagerTest { @Test public void testSendDnsConfiguration() throws Exception { reset(mMockDnsResolver); - mDnsManager.updatePrivateDns(new Network(TEST_NETID), - mDnsManager.getPrivateDnsConfig()); + final PrivateDnsConfig cfg = new PrivateDnsConfig( + PRIVATE_DNS_MODE_OPPORTUNISTIC /* mode */, + null /* hostname */, + null /* ips */, + "doh.com" /* dohName */, + null /* dohIps */, + "/some-path{?dns}" /* dohPath */, + 5353 /* dohPort */); + + mDnsManager.updatePrivateDns(new Network(TEST_NETID), cfg); final LinkProperties lp = new LinkProperties(); lp.setInterfaceName(TEST_IFACENAME); lp.addDnsServer(InetAddress.getByName("3.3.3.3")); @@ -352,7 +361,11 @@ public class DnsManagerTest { expectedParams.transportTypes = TEST_TRANSPORT_TYPES; expectedParams.resolverOptions = null; expectedParams.meteredNetwork = true; - expectedParams.dohParams = null; + expectedParams.dohParams = new DohParamsParcel.Builder() + .setName("doh.com") + .setDohpath("/some-path{?dns}") + .setPort(5353) + .build(); expectedParams.interfaceNames = new String[]{TEST_IFACENAME}; verify(mMockDnsResolver, times(1)).setResolverConfiguration(eq(expectedParams)); }