blob: 1aeb4c22139a646a6c3ef2caf1ab1d8c69f324b3 [file] [log] [blame]
Ken Chenb9fa2062018-11-13 21:51:13 +08001/*
2 * Copyright (C) 2016 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
Lorenzo Colitti0a8b4aa2019-06-26 22:31:03 +090010 * Unless required by applicable law or agreed to in writing, software
Ken Chenb9fa2062018-11-13 21:51:13 +080011 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 *
16 */
17
Bernie Innocenti3952ccc2019-03-03 19:39:53 +090018#define LOG_TAG "resolv_integration_test"
Ken Chenb9fa2062018-11-13 21:51:13 +080019
Hungming Chen5bf09772019-04-25 11:16:13 +080020#include <android-base/logging.h>
Bernie Innocenti41b82c42019-06-05 22:38:25 +090021#include <android-base/parseint.h>
Mike Yu40e67072019-10-09 21:14:09 +080022#include <android-base/properties.h>
Bernie Innocenti41b82c42019-06-05 22:38:25 +090023#include <android-base/stringprintf.h>
24#include <android-base/unique_fd.h>
25#include <android/multinetwork.h> // ResNsendFlags
Ken Chenb9fa2062018-11-13 21:51:13 +080026#include <arpa/inet.h>
Luke Huang94b10b92018-11-21 20:13:38 +080027#include <arpa/nameser.h>
Hungming Chene8f970c2019-04-10 17:34:06 +080028#include <binder/ProcessState.h>
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +090029#include <bpf/BpfUtils.h>
Bernie Innocenti41b82c42019-06-05 22:38:25 +090030#include <cutils/sockets.h>
31#include <gmock/gmock-matchers.h>
32#include <gtest/gtest.h>
Ken Chenb9fa2062018-11-13 21:51:13 +080033#include <netdb.h>
Luke Huang9d2d25b2019-06-14 00:34:05 +080034#include <netdutils/InternetAddresses.h>
Luke Huang579ddc72019-06-14 00:59:39 +080035#include <netdutils/NetworkConstants.h> // SHA256_SIZE
Luke Huang9d2d25b2019-06-14 00:34:05 +080036#include <netdutils/ResponseCode.h>
Hungming Chen63779052019-10-30 15:06:13 +080037#include <netdutils/Slice.h>
Luke Huang9d2d25b2019-06-14 00:34:05 +080038#include <netdutils/SocketOption.h>
Mike Yu40e67072019-10-09 21:14:09 +080039#include <netdutils/Stopwatch.h>
Luke Huang94b10b92018-11-21 20:13:38 +080040#include <netinet/in.h>
41#include <poll.h> /* poll */
Bernie Innocenti41b82c42019-06-05 22:38:25 +090042#include <private/android_filesystem_config.h>
Luke Huang94b10b92018-11-21 20:13:38 +080043#include <resolv.h>
Ken Chenb9fa2062018-11-13 21:51:13 +080044#include <stdarg.h>
Ken Chenb9fa2062018-11-13 21:51:13 +080045#include <stdlib.h>
Luke Huang94b10b92018-11-21 20:13:38 +080046#include <sys/socket.h>
47#include <sys/un.h>
Ken Chenb9fa2062018-11-13 21:51:13 +080048#include <unistd.h>
49
50#include <algorithm>
51#include <chrono>
52#include <iterator>
53#include <numeric>
54#include <thread>
55
Luke Huangf8215372019-11-22 11:53:41 +080056#include <aidl/android/net/IDnsResolver.h>
57#include <android/binder_manager.h>
58#include <android/binder_process.h>
Bernie Innocenti41b82c42019-06-05 22:38:25 +090059#include "NetdClient.h"
Bernie Innocenti41b82c42019-06-05 22:38:25 +090060#include "ResolverStats.h"
Luke Huangf8215372019-11-22 11:53:41 +080061#include "netid_client.h" // NETID_UNSET
62#include "params.h" // MAXNS
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +090063#include "test_utils.h"
Hungming Chene8f970c2019-04-10 17:34:06 +080064#include "tests/dns_metrics_listener/dns_metrics_listener.h"
chenbruceb43ec752019-07-24 20:19:41 +080065#include "tests/dns_responder/dns_responder.h"
Luke Huangf8215372019-11-22 11:53:41 +080066#include "tests/dns_responder/dns_responder_client_ndk.h"
Hungming Chenc6556622019-10-02 16:01:07 +080067#include "tests/dns_responder/dns_tls_certificate.h"
chenbruceb43ec752019-07-24 20:19:41 +080068#include "tests/dns_responder/dns_tls_frontend.h"
Luke Huangfde82482019-06-04 01:04:53 +080069#include "tests/resolv_test_utils.h"
Ken Chenb9fa2062018-11-13 21:51:13 +080070
Luke Huang0d592bc2019-05-25 18:24:03 +080071// Valid VPN netId range is 100 ~ 65535
72constexpr int TEST_VPN_NETID = 65502;
Luke Huang94b10b92018-11-21 20:13:38 +080073constexpr int MAXPACKET = (8 * 1024);
Ken Chenb9fa2062018-11-13 21:51:13 +080074
Sehee Park2c118782019-05-07 13:02:45 +090075// Use maximum reserved appId for applications to avoid conflict with existing uids.
76static const int TEST_UID = 99999;
77
Ken Chenb9fa2062018-11-13 21:51:13 +080078// Semi-public Bionic hook used by the NDK (frameworks/base/native/android/net.c)
79// Tested here for convenience.
80extern "C" int android_getaddrinfofornet(const char* hostname, const char* servname,
81 const addrinfo* hints, unsigned netid, unsigned mark,
82 struct addrinfo** result);
83
Luke Huang70070852019-11-25 18:25:50 +080084using aidl::android::net::IDnsResolver;
Luke Huangf8215372019-11-22 11:53:41 +080085using aidl::android::net::INetd;
Mike Yu8ac63402019-12-02 15:28:38 +080086using aidl::android::net::ResolverParamsParcel;
Luke Huang9807e6b2019-05-20 16:17:12 +080087using android::base::ParseInt;
Ken Chenb9fa2062018-11-13 21:51:13 +080088using android::base::StringPrintf;
Luke Huang9807e6b2019-05-20 16:17:12 +080089using android::base::unique_fd;
Ken Chenb9fa2062018-11-13 21:51:13 +080090using android::net::ResolverStats;
Hungming Chene8f970c2019-04-10 17:34:06 +080091using android::net::metrics::DnsMetricsListener;
Ken Chenb9fa2062018-11-13 21:51:13 +080092using android::netdutils::enableSockopt;
Hungming Chen63779052019-10-30 15:06:13 +080093using android::netdutils::makeSlice;
Luke Huang9807e6b2019-05-20 16:17:12 +080094using android::netdutils::ResponseCode;
Luke Huang9d2d25b2019-06-14 00:34:05 +080095using android::netdutils::ScopedAddrinfo;
Mike Yu40e67072019-10-09 21:14:09 +080096using android::netdutils::Stopwatch;
Hungming Chen63779052019-10-30 15:06:13 +080097using android::netdutils::toHex;
Ken Chenb9fa2062018-11-13 21:51:13 +080098
99// TODO: move into libnetdutils?
100namespace {
Luke Huangfde82482019-06-04 01:04:53 +0800101
Ken Chenb9fa2062018-11-13 21:51:13 +0800102ScopedAddrinfo safe_getaddrinfo(const char* node, const char* service,
103 const struct addrinfo* hints) {
104 addrinfo* result = nullptr;
105 if (getaddrinfo(node, service, hints, &result) != 0) {
106 result = nullptr; // Should already be the case, but...
107 }
108 return ScopedAddrinfo(result);
109}
Luke Huangfde82482019-06-04 01:04:53 +0800110
Mike Yu40e67072019-10-09 21:14:09 +0800111std::pair<ScopedAddrinfo, int> safe_getaddrinfo_time_taken(const char* node, const char* service,
112 const addrinfo& hints) {
113 Stopwatch s;
114 ScopedAddrinfo result = safe_getaddrinfo(node, service, &hints);
115 return {std::move(result), s.timeTakenUs() / 1000};
116}
117
Mike Yue2162e52020-03-04 18:43:46 +0800118struct NameserverStats {
119 NameserverStats() = delete;
120 NameserverStats(const std::string server) : server(server) {}
121 NameserverStats& setSuccesses(int val) {
122 successes = val;
123 return *this;
124 }
125 NameserverStats& setErrors(int val) {
126 errors = val;
127 return *this;
128 }
129 NameserverStats& setTimeouts(int val) {
130 timeouts = val;
131 return *this;
132 }
133 NameserverStats& setInternalErrors(int val) {
134 internal_errors = val;
135 return *this;
136 }
137
138 const std::string server;
139 int successes = 0;
140 int errors = 0;
141 int timeouts = 0;
142 int internal_errors = 0;
143};
144
Ken Chenb9fa2062018-11-13 21:51:13 +0800145} // namespace
146
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +0900147class ResolverTest : public ::testing::Test {
Hungming Chene8f970c2019-04-10 17:34:06 +0800148 public:
Hungming Chen473c4de2020-03-12 11:13:35 +0800149 static void SetUpTestSuite() {
Hungming Chen5bf09772019-04-25 11:16:13 +0800150 // Get binder service.
151 // Note that |mDnsClient| is not used for getting binder service in this static function.
152 // The reason is that wants to keep |mDnsClient| as a non-static data member. |mDnsClient|
153 // which sets up device network configuration could be independent from every test.
Luke Huangf8215372019-11-22 11:53:41 +0800154 // TODO: Perhaps add a static function in resolv_test_binder_utils.{cpp,h} to get binder
155 // service.
156
157 AIBinder* binder = AServiceManager_getService("dnsresolver");
158 ndk::SpAIBinder resolvBinder = ndk::SpAIBinder(binder);
159 auto resolvService = aidl::android::net::IDnsResolver::fromBinder(resolvBinder);
Hungming Chen5bf09772019-04-25 11:16:13 +0800160 ASSERT_NE(nullptr, resolvService.get());
161
162 // Subscribe the death recipient to the service IDnsResolver for detecting Netd death.
Luke Huang70070852019-11-25 18:25:50 +0800163 // GTEST assertion macros are not invoked for generating a test failure in the death
164 // recipient because the macros can't indicate failed test if Netd died between tests.
165 // Moreover, continuing testing may have no meaningful after Netd death. Therefore, the
166 // death recipient aborts process by GTEST_LOG_(FATAL) once Netd died.
Luke Huangf8215372019-11-22 11:53:41 +0800167 sResolvDeathRecipient = AIBinder_DeathRecipient_new([](void*) {
168 constexpr char errorMessage[] = "Netd died";
169 LOG(ERROR) << errorMessage;
170 GTEST_LOG_(FATAL) << errorMessage;
171 });
172 ASSERT_EQ(STATUS_OK, AIBinder_linkToDeath(binder, sResolvDeathRecipient, nullptr));
Hungming Chen5bf09772019-04-25 11:16:13 +0800173
174 // Subscribe the DNS listener for verifying DNS metrics event contents.
Luke Huangf8215372019-11-22 11:53:41 +0800175 sDnsMetricsListener = ndk::SharedRefBase::make<DnsMetricsListener>(
176 TEST_NETID /*monitor specific network*/);
Hungming Chen5bf09772019-04-25 11:16:13 +0800177 ASSERT_TRUE(resolvService->registerEventListener(sDnsMetricsListener).isOk());
178
179 // Start the binder thread pool for listening DNS metrics events and receiving death
180 // recipient.
Luke Huangf8215372019-11-22 11:53:41 +0800181 ABinderProcess_startThreadPool();
Hungming Chene8f970c2019-04-10 17:34:06 +0800182 }
Hungming Chen473c4de2020-03-12 11:13:35 +0800183 static void TearDownTestSuite() { AIBinder_DeathRecipient_delete(sResolvDeathRecipient); }
Hungming Chene8f970c2019-04-10 17:34:06 +0800184
Ken Chenb9fa2062018-11-13 21:51:13 +0800185 protected:
Hungming Chen5bf09772019-04-25 11:16:13 +0800186 void SetUp() { mDnsClient.SetUp(); }
Mike Yu960243d2020-01-17 19:02:15 +0800187 void TearDown() {
188 // Ensure the dump works at the end of each test.
189 DumpResolverService();
190
191 mDnsClient.TearDown();
192 }
nuccachena26cc2a2018-07-17 18:07:23 +0800193
Xiao Ma09b71022018-12-11 17:56:32 +0900194 void StartDns(test::DNSResponder& dns, const std::vector<DnsRecord>& records) {
195 for (const auto& r : records) {
196 dns.addMapping(r.host_name, r.type, r.addr);
197 }
198
199 ASSERT_TRUE(dns.startServer());
200 dns.clearQueries();
201 }
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +0900202
Mike Yu960243d2020-01-17 19:02:15 +0800203 void DumpResolverService() {
204 unique_fd fd(open("/dev/null", O_WRONLY));
205 EXPECT_EQ(mDnsClient.resolvService()->dump(fd, nullptr, 0), 0);
206
207 const char* querylogCmd[] = {"querylog"}; // Keep it sync with DnsQueryLog::DUMP_KEYWORD.
208 EXPECT_EQ(mDnsClient.resolvService()->dump(fd, querylogCmd, std::size(querylogCmd)), 0);
209 }
210
Hungming Chene8f970c2019-04-10 17:34:06 +0800211 bool WaitForNat64Prefix(ExpectNat64PrefixStatus status,
212 std::chrono::milliseconds timeout = std::chrono::milliseconds(1000)) {
Hungming Chen5bf09772019-04-25 11:16:13 +0800213 return sDnsMetricsListener->waitForNat64Prefix(status, timeout);
Hungming Chene8f970c2019-04-10 17:34:06 +0800214 }
215
Mike Yu724f77d2019-08-16 11:14:50 +0800216 bool WaitForPrivateDnsValidation(std::string serverAddr, bool validated) {
217 return sDnsMetricsListener->waitForPrivateDnsValidation(serverAddr, validated);
218 }
219
Mike Yue2162e52020-03-04 18:43:46 +0800220 bool expectStatsFromGetResolverInfo(const std::vector<NameserverStats>& nameserversStats) {
221 std::vector<std::string> res_servers;
222 std::vector<std::string> res_domains;
223 std::vector<std::string> res_tls_servers;
224 res_params res_params;
225 std::vector<ResolverStats> res_stats;
226 int wait_for_pending_req_timeout_count;
227
228 if (!DnsResponderClient::GetResolverInfo(mDnsClient.resolvService(), TEST_NETID,
229 &res_servers, &res_domains, &res_tls_servers,
230 &res_params, &res_stats,
231 &wait_for_pending_req_timeout_count)) {
232 ADD_FAILURE() << "GetResolverInfo failed";
233 return false;
234 }
235
236 if (res_servers.size() != res_stats.size()) {
237 ADD_FAILURE() << fmt::format("res_servers.size() != res_stats.size(): {} != {}",
238 res_servers.size(), res_stats.size());
239 return false;
240 }
241 if (res_servers.size() != nameserversStats.size()) {
242 ADD_FAILURE() << fmt::format("res_servers.size() != nameserversStats.size(): {} != {}",
243 res_servers.size(), nameserversStats.size());
244 return false;
245 }
246
247 for (const auto& stats : nameserversStats) {
248 SCOPED_TRACE(stats.server);
249 const auto it = std::find(res_servers.begin(), res_servers.end(), stats.server);
250 if (it == res_servers.end()) {
251 ADD_FAILURE() << fmt::format("nameserver {} not found in the list {{{}}}",
252 stats.server, fmt::join(res_servers, ", "));
253 return false;
254 }
255 const int index = std::distance(res_servers.begin(), it);
256
257 // The check excludes rtt_avg, last_sample_time, and usable since they will be obsolete
258 // after |res_stats| is retrieved from NetConfig.dnsStats rather than NetConfig.nsstats.
259 EXPECT_EQ(res_stats[index].successes, stats.successes);
260 EXPECT_EQ(res_stats[index].errors, stats.errors);
261 EXPECT_EQ(res_stats[index].timeouts, stats.timeouts);
262 EXPECT_EQ(res_stats[index].internal_errors, stats.internal_errors);
263 }
264
265 return true;
266 }
267
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +0900268 DnsResponderClient mDnsClient;
Xiao Ma09b71022018-12-11 17:56:32 +0900269
Hungming Chen5bf09772019-04-25 11:16:13 +0800270 // Use a shared static DNS listener for all tests to avoid registering lots of listeners
271 // which may be released late until process terminated. Currently, registered DNS listener
272 // is removed by binder death notification which is fired when the process hosting an
273 // IBinder has gone away. If every test in ResolverTest registers its DNS listener, Netd
274 // may temporarily hold lots of dead listeners until the unit test process terminates.
275 // TODO: Perhaps add an unregistering listener binder call or fork a listener process which
276 // could be terminated earlier.
Luke Huangf8215372019-11-22 11:53:41 +0800277 static std::shared_ptr<DnsMetricsListener>
Hungming Chen473c4de2020-03-12 11:13:35 +0800278 sDnsMetricsListener; // Initialized in SetUpTestSuite.
Hungming Chen5bf09772019-04-25 11:16:13 +0800279
280 // Use a shared static death recipient to monitor the service death. The static death
281 // recipient could monitor the death not only during the test but also between tests.
Hungming Chen473c4de2020-03-12 11:13:35 +0800282 static AIBinder_DeathRecipient* sResolvDeathRecipient; // Initialized in SetUpTestSuite.
Ken Chenb9fa2062018-11-13 21:51:13 +0800283};
284
Hungming Chen5bf09772019-04-25 11:16:13 +0800285// Initialize static member of class.
Luke Huangf8215372019-11-22 11:53:41 +0800286std::shared_ptr<DnsMetricsListener> ResolverTest::sDnsMetricsListener;
287AIBinder_DeathRecipient* ResolverTest::sResolvDeathRecipient;
Hungming Chen5bf09772019-04-25 11:16:13 +0800288
Ken Chenb9fa2062018-11-13 21:51:13 +0800289TEST_F(ResolverTest, GetHostByName) {
Xiao Ma09b71022018-12-11 17:56:32 +0900290 constexpr char nonexistent_host_name[] = "nonexistent.example.com.";
291
292 test::DNSResponder dns;
293 StartDns(dns, {{kHelloExampleCom, ns_type::ns_t_a, "1.2.3.3"}});
294 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +0800295
296 const hostent* result;
Ken Chenb9fa2062018-11-13 21:51:13 +0800297 result = gethostbyname("nonexistent");
298 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, nonexistent_host_name));
299 ASSERT_TRUE(result == nullptr);
300 ASSERT_EQ(HOST_NOT_FOUND, h_errno);
301
302 dns.clearQueries();
303 result = gethostbyname("hello");
Xiao Ma09b71022018-12-11 17:56:32 +0900304 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, kHelloExampleCom));
Ken Chenb9fa2062018-11-13 21:51:13 +0800305 ASSERT_FALSE(result == nullptr);
306 ASSERT_EQ(4, result->h_length);
307 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
308 EXPECT_EQ("1.2.3.3", ToString(result));
309 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
Ken Chenb9fa2062018-11-13 21:51:13 +0800310}
311
lifr4e4a2e02019-01-29 16:53:51 +0800312TEST_F(ResolverTest, GetHostByName_cnames) {
313 constexpr char host_name[] = "host.example.com.";
314 size_t cnamecount = 0;
315 test::DNSResponder dns;
316
317 const std::vector<DnsRecord> records = {
318 {kHelloExampleCom, ns_type::ns_t_cname, "a.example.com."},
319 {"a.example.com.", ns_type::ns_t_cname, "b.example.com."},
320 {"b.example.com.", ns_type::ns_t_cname, "c.example.com."},
321 {"c.example.com.", ns_type::ns_t_cname, "d.example.com."},
322 {"d.example.com.", ns_type::ns_t_cname, "e.example.com."},
323 {"e.example.com.", ns_type::ns_t_cname, host_name},
324 {host_name, ns_type::ns_t_a, "1.2.3.3"},
325 {host_name, ns_type::ns_t_aaaa, "2001:db8::42"},
326 };
327 StartDns(dns, records);
328 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
329
330 // using gethostbyname2() to resolve ipv4 hello.example.com. to 1.2.3.3
331 // Ensure the v4 address and cnames are correct
332 const hostent* result;
333 result = gethostbyname2("hello", AF_INET);
334 ASSERT_FALSE(result == nullptr);
335
336 for (int i = 0; result != nullptr && result->h_aliases[i] != nullptr; i++) {
337 std::string domain_name = records[i].host_name.substr(0, records[i].host_name.size() - 1);
338 EXPECT_EQ(result->h_aliases[i], domain_name);
339 cnamecount++;
340 }
341 // The size of "Non-cname type" record in DNS records is 2
342 ASSERT_EQ(cnamecount, records.size() - 2);
343 ASSERT_EQ(4, result->h_length);
344 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
345 EXPECT_EQ("1.2.3.3", ToString(result));
346 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
347 EXPECT_EQ(1U, dns.queries().size()) << dns.dumpQueries();
348
349 // using gethostbyname2() to resolve ipv6 hello.example.com. to 2001:db8::42
350 // Ensure the v6 address and cnames are correct
351 cnamecount = 0;
352 dns.clearQueries();
353 result = gethostbyname2("hello", AF_INET6);
354 for (unsigned i = 0; result != nullptr && result->h_aliases[i] != nullptr; i++) {
355 std::string domain_name = records[i].host_name.substr(0, records[i].host_name.size() - 1);
356 EXPECT_EQ(result->h_aliases[i], domain_name);
357 cnamecount++;
358 }
359 // The size of "Non-cname type" DNS record in records is 2
360 ASSERT_EQ(cnamecount, records.size() - 2);
361 ASSERT_FALSE(result == nullptr);
362 ASSERT_EQ(16, result->h_length);
363 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
364 EXPECT_EQ("2001:db8::42", ToString(result));
365 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
366}
367
368TEST_F(ResolverTest, GetHostByName_cnamesInfiniteLoop) {
369 test::DNSResponder dns;
370 const std::vector<DnsRecord> records = {
371 {kHelloExampleCom, ns_type::ns_t_cname, "a.example.com."},
372 {"a.example.com.", ns_type::ns_t_cname, kHelloExampleCom},
373 };
374 StartDns(dns, records);
375 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
376
377 const hostent* result;
378 result = gethostbyname2("hello", AF_INET);
379 ASSERT_TRUE(result == nullptr);
380
381 dns.clearQueries();
382 result = gethostbyname2("hello", AF_INET6);
383 ASSERT_TRUE(result == nullptr);
384}
385
Ken Chenb9fa2062018-11-13 21:51:13 +0800386TEST_F(ResolverTest, GetHostByName_localhost) {
Ken Chenb9fa2062018-11-13 21:51:13 +0800387 constexpr char name_camelcase[] = "LocalHost";
Ken Chenb9fa2062018-11-13 21:51:13 +0800388 constexpr char name_ip6_dot[] = "ip6-localhost.";
389 constexpr char name_ip6_fqdn[] = "ip6-localhost.example.com.";
390
391 // Add a dummy nameserver which shouldn't receive any queries
Xiao Ma09b71022018-12-11 17:56:32 +0900392 test::DNSResponder dns;
393 StartDns(dns, {});
394 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +0800395
396 // Expect no DNS queries; localhost is resolved via /etc/hosts
Xiao Ma09b71022018-12-11 17:56:32 +0900397 const hostent* result = gethostbyname(kLocalHost);
Ken Chenb9fa2062018-11-13 21:51:13 +0800398 EXPECT_TRUE(dns.queries().empty()) << dns.dumpQueries();
399 ASSERT_FALSE(result == nullptr);
400 ASSERT_EQ(4, result->h_length);
401 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
Xiao Ma09b71022018-12-11 17:56:32 +0900402 EXPECT_EQ(kLocalHostAddr, ToString(result));
Ken Chenb9fa2062018-11-13 21:51:13 +0800403 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
404
405 // Ensure the hosts file resolver ignores case of hostnames
406 result = gethostbyname(name_camelcase);
407 EXPECT_TRUE(dns.queries().empty()) << dns.dumpQueries();
408 ASSERT_FALSE(result == nullptr);
409 ASSERT_EQ(4, result->h_length);
410 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
Xiao Ma09b71022018-12-11 17:56:32 +0900411 EXPECT_EQ(kLocalHostAddr, ToString(result));
Ken Chenb9fa2062018-11-13 21:51:13 +0800412 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
413
414 // The hosts file also contains ip6-localhost, but gethostbyname() won't
chenbruce018fdb22019-06-12 18:08:04 +0800415 // return it. This would be easy to
Ken Chenb9fa2062018-11-13 21:51:13 +0800416 // change, but there's no point in changing the legacy behavior; new code
417 // should be calling getaddrinfo() anyway.
418 // So we check the legacy behavior, which results in amusing A-record
419 // lookups for ip6-localhost, with and without search domains appended.
420 dns.clearQueries();
Xiao Ma09b71022018-12-11 17:56:32 +0900421 result = gethostbyname(kIp6LocalHost);
Sehee Parkbbca0202018-11-16 10:53:16 +0900422 EXPECT_EQ(2U, dns.queries().size()) << dns.dumpQueries();
423 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, name_ip6_dot)) << dns.dumpQueries();
424 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, name_ip6_fqdn)) << dns.dumpQueries();
Ken Chenb9fa2062018-11-13 21:51:13 +0800425 ASSERT_TRUE(result == nullptr);
426
427 // Finally, use gethostbyname2() to resolve ip6-localhost to ::1 from
428 // the hosts file.
429 dns.clearQueries();
Xiao Ma09b71022018-12-11 17:56:32 +0900430 result = gethostbyname2(kIp6LocalHost, AF_INET6);
Ken Chenb9fa2062018-11-13 21:51:13 +0800431 EXPECT_TRUE(dns.queries().empty()) << dns.dumpQueries();
432 ASSERT_FALSE(result == nullptr);
433 ASSERT_EQ(16, result->h_length);
434 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
Xiao Ma09b71022018-12-11 17:56:32 +0900435 EXPECT_EQ(kIp6LocalHostAddr, ToString(result));
Ken Chenb9fa2062018-11-13 21:51:13 +0800436 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
Ken Chenb9fa2062018-11-13 21:51:13 +0800437}
438
439TEST_F(ResolverTest, GetHostByName_numeric) {
440 // Add a dummy nameserver which shouldn't receive any queries
Xiao Ma09b71022018-12-11 17:56:32 +0900441 test::DNSResponder dns;
442 StartDns(dns, {});
443 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +0800444
445 // Numeric v4 address: expect no DNS queries
446 constexpr char numeric_v4[] = "192.168.0.1";
Ken Chenb9fa2062018-11-13 21:51:13 +0800447 const hostent* result = gethostbyname(numeric_v4);
Sehee Parkbbca0202018-11-16 10:53:16 +0900448 EXPECT_EQ(0U, dns.queries().size());
Ken Chenb9fa2062018-11-13 21:51:13 +0800449 ASSERT_FALSE(result == nullptr);
450 ASSERT_EQ(4, result->h_length); // v4
451 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
452 EXPECT_EQ(numeric_v4, ToString(result));
453 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
454
455 // gethostbyname() recognizes a v6 address, and fails with no DNS queries
456 constexpr char numeric_v6[] = "2001:db8::42";
457 dns.clearQueries();
458 result = gethostbyname(numeric_v6);
Sehee Parkbbca0202018-11-16 10:53:16 +0900459 EXPECT_EQ(0U, dns.queries().size());
Ken Chenb9fa2062018-11-13 21:51:13 +0800460 EXPECT_TRUE(result == nullptr);
461
462 // Numeric v6 address with gethostbyname2(): succeeds with no DNS queries
463 dns.clearQueries();
464 result = gethostbyname2(numeric_v6, AF_INET6);
Sehee Parkbbca0202018-11-16 10:53:16 +0900465 EXPECT_EQ(0U, dns.queries().size());
Ken Chenb9fa2062018-11-13 21:51:13 +0800466 ASSERT_FALSE(result == nullptr);
467 ASSERT_EQ(16, result->h_length); // v6
468 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
469 EXPECT_EQ(numeric_v6, ToString(result));
470 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
471
472 // Numeric v6 address with scope work with getaddrinfo(),
473 // but gethostbyname2() does not understand them; it issues two dns
474 // queries, then fails. This hardly ever happens, there's no point
475 // in fixing this. This test simply verifies the current (bogus)
476 // behavior to avoid further regressions (like crashes, or leaks).
477 constexpr char numeric_v6_scope[] = "fe80::1%lo";
478 dns.clearQueries();
479 result = gethostbyname2(numeric_v6_scope, AF_INET6);
Sehee Parkbbca0202018-11-16 10:53:16 +0900480 EXPECT_EQ(2U, dns.queries().size()); // OUCH!
Ken Chenb9fa2062018-11-13 21:51:13 +0800481 ASSERT_TRUE(result == nullptr);
Ken Chenb9fa2062018-11-13 21:51:13 +0800482}
483
484TEST_F(ResolverTest, BinderSerialization) {
Ken Chenb9fa2062018-11-13 21:51:13 +0800485 std::vector<int> params_offsets = {
Luke Huang5bd827c2019-03-14 16:10:04 +0800486 IDnsResolver::RESOLVER_PARAMS_SAMPLE_VALIDITY,
487 IDnsResolver::RESOLVER_PARAMS_SUCCESS_THRESHOLD,
488 IDnsResolver::RESOLVER_PARAMS_MIN_SAMPLES,
489 IDnsResolver::RESOLVER_PARAMS_MAX_SAMPLES,
490 IDnsResolver::RESOLVER_PARAMS_BASE_TIMEOUT_MSEC,
491 IDnsResolver::RESOLVER_PARAMS_RETRY_COUNT,
Ken Chenb9fa2062018-11-13 21:51:13 +0800492 };
Bernie Innocentib102dd22018-12-04 14:57:48 +0900493 const int size = static_cast<int>(params_offsets.size());
Luke Huang5bd827c2019-03-14 16:10:04 +0800494 EXPECT_EQ(size, IDnsResolver::RESOLVER_PARAMS_COUNT);
Ken Chenb9fa2062018-11-13 21:51:13 +0800495 std::sort(params_offsets.begin(), params_offsets.end());
Bernie Innocentib102dd22018-12-04 14:57:48 +0900496 for (int i = 0; i < size; ++i) {
Ken Chenb9fa2062018-11-13 21:51:13 +0800497 EXPECT_EQ(params_offsets[i], i);
498 }
499}
500
501TEST_F(ResolverTest, GetHostByName_Binder) {
Luke Huangf8215372019-11-22 11:53:41 +0800502 std::vector<std::string> domains = {"example.com"};
Ken Chenb9fa2062018-11-13 21:51:13 +0800503 std::vector<std::unique_ptr<test::DNSResponder>> dns;
504 std::vector<std::string> servers;
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +0900505 std::vector<DnsResponderClient::Mapping> mappings;
506 ASSERT_NO_FATAL_FAILURE(mDnsClient.SetupMappings(1, domains, &mappings));
507 ASSERT_NO_FATAL_FAILURE(mDnsClient.SetupDNSServers(4, mappings, &dns, &servers));
Ken Chenb9fa2062018-11-13 21:51:13 +0800508 ASSERT_EQ(1U, mappings.size());
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +0900509 const DnsResponderClient::Mapping& mapping = mappings[0];
Ken Chenb9fa2062018-11-13 21:51:13 +0800510
Xiao Ma09b71022018-12-11 17:56:32 +0900511 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, domains, kDefaultParams));
Ken Chenb9fa2062018-11-13 21:51:13 +0800512
513 const hostent* result = gethostbyname(mapping.host.c_str());
Bernie Innocentib102dd22018-12-04 14:57:48 +0900514 const size_t total_queries =
Luke Huangfde82482019-06-04 01:04:53 +0800515 std::accumulate(dns.begin(), dns.end(), 0, [&mapping](size_t total, auto& d) {
Ken Chenb9fa2062018-11-13 21:51:13 +0800516 return total + GetNumQueriesForType(*d, ns_type::ns_t_a, mapping.entry.c_str());
517 });
518
519 EXPECT_LE(1U, total_queries);
520 ASSERT_FALSE(result == nullptr);
521 ASSERT_EQ(4, result->h_length);
522 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
523 EXPECT_EQ(mapping.ip4, ToString(result));
524 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
525
526 std::vector<std::string> res_servers;
527 std::vector<std::string> res_domains;
Mike Yu0a1c53d2018-11-26 13:26:21 +0900528 std::vector<std::string> res_tls_servers;
Bernie Innocenti758005f2019-02-19 18:08:36 +0900529 res_params res_params;
Ken Chenb9fa2062018-11-13 21:51:13 +0800530 std::vector<ResolverStats> res_stats;
Ken Chen92bed612018-12-22 21:46:55 +0800531 int wait_for_pending_req_timeout_count;
Luke Huangf8215372019-11-22 11:53:41 +0800532 ASSERT_TRUE(DnsResponderClient::GetResolverInfo(
533 mDnsClient.resolvService(), TEST_NETID, &res_servers, &res_domains, &res_tls_servers,
534 &res_params, &res_stats, &wait_for_pending_req_timeout_count));
Ken Chenb9fa2062018-11-13 21:51:13 +0800535 EXPECT_EQ(servers.size(), res_servers.size());
536 EXPECT_EQ(domains.size(), res_domains.size());
Mike Yu0a1c53d2018-11-26 13:26:21 +0900537 EXPECT_EQ(0U, res_tls_servers.size());
Luke Huang5bd827c2019-03-14 16:10:04 +0800538 ASSERT_EQ(static_cast<size_t>(IDnsResolver::RESOLVER_PARAMS_COUNT), kDefaultParams.size());
539 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_SAMPLE_VALIDITY],
540 res_params.sample_validity);
541 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_SUCCESS_THRESHOLD],
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +0900542 res_params.success_threshold);
Luke Huang5bd827c2019-03-14 16:10:04 +0800543 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_MIN_SAMPLES], res_params.min_samples);
544 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_MAX_SAMPLES], res_params.max_samples);
545 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_BASE_TIMEOUT_MSEC],
Ken Chenb9fa2062018-11-13 21:51:13 +0800546 res_params.base_timeout_msec);
547 EXPECT_EQ(servers.size(), res_stats.size());
548
Bernie Innocenti0c067e42019-04-01 15:33:16 +0900549 EXPECT_THAT(res_servers, testing::UnorderedElementsAreArray(servers));
550 EXPECT_THAT(res_domains, testing::UnorderedElementsAreArray(domains));
Ken Chenb9fa2062018-11-13 21:51:13 +0800551}
552
553TEST_F(ResolverTest, GetAddrInfo) {
Xiao Ma09b71022018-12-11 17:56:32 +0900554 constexpr char listen_addr[] = "127.0.0.4";
555 constexpr char listen_addr2[] = "127.0.0.5";
556 constexpr char host_name[] = "howdy.example.com.";
Ken Chenb9fa2062018-11-13 21:51:13 +0800557
Xiao Ma09b71022018-12-11 17:56:32 +0900558 const std::vector<DnsRecord> records = {
559 {host_name, ns_type::ns_t_a, "1.2.3.4"},
560 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
561 };
562 test::DNSResponder dns(listen_addr);
563 test::DNSResponder dns2(listen_addr2);
564 StartDns(dns, records);
565 StartDns(dns2, records);
Ken Chenb9fa2062018-11-13 21:51:13 +0800566
Xiao Ma09b71022018-12-11 17:56:32 +0900567 ASSERT_TRUE(mDnsClient.SetResolversForNetwork({listen_addr}));
Ken Chenb9fa2062018-11-13 21:51:13 +0800568 dns.clearQueries();
569 dns2.clearQueries();
570
571 ScopedAddrinfo result = safe_getaddrinfo("howdy", nullptr, nullptr);
572 EXPECT_TRUE(result != nullptr);
573 size_t found = GetNumQueries(dns, host_name);
574 EXPECT_LE(1U, found);
575 // Could be A or AAAA
576 std::string result_str = ToString(result);
577 EXPECT_TRUE(result_str == "1.2.3.4" || result_str == "::1.2.3.4")
Luke Huangf8215372019-11-22 11:53:41 +0800578 << ", result_str='" << result_str << "'";
Ken Chenb9fa2062018-11-13 21:51:13 +0800579
580 // Verify that the name is cached.
581 size_t old_found = found;
582 result = safe_getaddrinfo("howdy", nullptr, nullptr);
583 EXPECT_TRUE(result != nullptr);
584 found = GetNumQueries(dns, host_name);
585 EXPECT_LE(1U, found);
586 EXPECT_EQ(old_found, found);
587 result_str = ToString(result);
Luke Huangf8215372019-11-22 11:53:41 +0800588 EXPECT_TRUE(result_str == "1.2.3.4" || result_str == "::1.2.3.4") << result_str;
Ken Chenb9fa2062018-11-13 21:51:13 +0800589
590 // Change the DNS resolver, ensure that queries are still cached.
Xiao Ma09b71022018-12-11 17:56:32 +0900591 ASSERT_TRUE(mDnsClient.SetResolversForNetwork({listen_addr2}));
Ken Chenb9fa2062018-11-13 21:51:13 +0800592 dns.clearQueries();
593 dns2.clearQueries();
594
595 result = safe_getaddrinfo("howdy", nullptr, nullptr);
596 EXPECT_TRUE(result != nullptr);
597 found = GetNumQueries(dns, host_name);
598 size_t found2 = GetNumQueries(dns2, host_name);
599 EXPECT_EQ(0U, found);
600 EXPECT_LE(0U, found2);
601
602 // Could be A or AAAA
603 result_str = ToString(result);
604 EXPECT_TRUE(result_str == "1.2.3.4" || result_str == "::1.2.3.4")
Luke Huangf8215372019-11-22 11:53:41 +0800605 << ", result_str='" << result_str << "'";
Ken Chenb9fa2062018-11-13 21:51:13 +0800606}
607
608TEST_F(ResolverTest, GetAddrInfoV4) {
Xiao Ma09b71022018-12-11 17:56:32 +0900609 test::DNSResponder dns;
610 StartDns(dns, {{kHelloExampleCom, ns_type::ns_t_a, "1.2.3.5"}});
611 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +0800612
Xiao Ma09b71022018-12-11 17:56:32 +0900613 const addrinfo hints = {.ai_family = AF_INET};
614 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
Ken Chenb9fa2062018-11-13 21:51:13 +0800615 EXPECT_TRUE(result != nullptr);
Xiao Ma09b71022018-12-11 17:56:32 +0900616 EXPECT_EQ(1U, GetNumQueries(dns, kHelloExampleCom));
Ken Chenb9fa2062018-11-13 21:51:13 +0800617 EXPECT_EQ("1.2.3.5", ToString(result));
618}
619
620TEST_F(ResolverTest, GetAddrInfo_localhost) {
Ken Chenb9fa2062018-11-13 21:51:13 +0800621 // Add a dummy nameserver which shouldn't receive any queries
Xiao Ma09b71022018-12-11 17:56:32 +0900622 test::DNSResponder dns;
623 StartDns(dns, {});
624 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +0800625
Xiao Ma09b71022018-12-11 17:56:32 +0900626 ScopedAddrinfo result = safe_getaddrinfo(kLocalHost, nullptr, nullptr);
Ken Chenb9fa2062018-11-13 21:51:13 +0800627 EXPECT_TRUE(result != nullptr);
628 // Expect no DNS queries; localhost is resolved via /etc/hosts
629 EXPECT_TRUE(dns.queries().empty()) << dns.dumpQueries();
Xiao Ma09b71022018-12-11 17:56:32 +0900630 EXPECT_EQ(kLocalHostAddr, ToString(result));
Ken Chenb9fa2062018-11-13 21:51:13 +0800631
Xiao Ma09b71022018-12-11 17:56:32 +0900632 result = safe_getaddrinfo(kIp6LocalHost, nullptr, nullptr);
Ken Chenb9fa2062018-11-13 21:51:13 +0800633 EXPECT_TRUE(result != nullptr);
634 // Expect no DNS queries; ip6-localhost is resolved via /etc/hosts
635 EXPECT_TRUE(dns.queries().empty()) << dns.dumpQueries();
Xiao Ma09b71022018-12-11 17:56:32 +0900636 EXPECT_EQ(kIp6LocalHostAddr, ToString(result));
Ken Chenb9fa2062018-11-13 21:51:13 +0800637}
638
Luke Huangd8ac4752019-06-18 17:05:47 +0800639TEST_F(ResolverTest, GetAddrInfo_InvalidSocketType) {
640 test::DNSResponder dns;
641 StartDns(dns, {{kHelloExampleCom, ns_type::ns_t_a, "1.2.3.5"}});
642 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
643
644 // TODO: Test other invalid socket types.
645 const addrinfo hints = {
646 .ai_family = AF_UNSPEC,
Luke Huangd8ac4752019-06-18 17:05:47 +0800647 .ai_socktype = SOCK_PACKET,
648 };
649 addrinfo* result = nullptr;
650 // This is a valid hint, but the query won't be sent because the socket type is
651 // not supported.
652 EXPECT_EQ(EAI_NODATA, getaddrinfo("hello", nullptr, &hints, &result));
653 ScopedAddrinfo result_cleanup(result);
654 EXPECT_EQ(nullptr, result);
655}
656
Ken Chen92bed612018-12-22 21:46:55 +0800657// Verify if the resolver correctly handle multiple queries simultaneously
658// step 1: set dns server#1 into deferred responding mode.
659// step 2: thread#1 query "hello.example.com." --> resolver send query to server#1.
660// step 3: thread#2 query "hello.example.com." --> resolver hold the request and wait for
661// response of previous pending query sent by thread#1.
662// step 4: thread#3 query "konbanha.example.com." --> resolver send query to server#3. Server
663// respond to resolver immediately.
664// step 5: check if server#1 get 1 query by thread#1, server#2 get 0 query, server#3 get 1 query.
665// step 6: resume dns server#1 to respond dns query in step#2.
666// step 7: thread#1 and #2 should get returned from DNS query after step#6. Also, check the
667// number of queries in server#2 is 0 to ensure thread#2 does not wake up unexpectedly
668// before signaled by thread#1.
669TEST_F(ResolverTest, GetAddrInfoV4_deferred_resp) {
670 const char* listen_addr1 = "127.0.0.9";
671 const char* listen_addr2 = "127.0.0.10";
672 const char* listen_addr3 = "127.0.0.11";
673 const char* listen_srv = "53";
674 const char* host_name_deferred = "hello.example.com.";
675 const char* host_name_normal = "konbanha.example.com.";
Mike Yufc125e42019-05-15 20:41:28 +0800676 test::DNSResponder dns1(listen_addr1, listen_srv, ns_rcode::ns_r_servfail);
677 test::DNSResponder dns2(listen_addr2, listen_srv, ns_rcode::ns_r_servfail);
678 test::DNSResponder dns3(listen_addr3, listen_srv, ns_rcode::ns_r_servfail);
Ken Chen92bed612018-12-22 21:46:55 +0800679 dns1.addMapping(host_name_deferred, ns_type::ns_t_a, "1.2.3.4");
680 dns2.addMapping(host_name_deferred, ns_type::ns_t_a, "1.2.3.4");
681 dns3.addMapping(host_name_normal, ns_type::ns_t_a, "1.2.3.5");
682 ASSERT_TRUE(dns1.startServer());
683 ASSERT_TRUE(dns2.startServer());
684 ASSERT_TRUE(dns3.startServer());
685 const std::vector<std::string> servers_for_t1 = {listen_addr1};
686 const std::vector<std::string> servers_for_t2 = {listen_addr2};
687 const std::vector<std::string> servers_for_t3 = {listen_addr3};
688 addrinfo hints = {.ai_family = AF_INET};
689 const std::vector<int> params = {300, 25, 8, 8, 5000};
690 bool t3_task_done = false;
691
692 dns1.setDeferredResp(true);
693 std::thread t1([&, this]() {
694 ASSERT_TRUE(
695 mDnsClient.SetResolversForNetwork(servers_for_t1, kDefaultSearchDomains, params));
696 ScopedAddrinfo result = safe_getaddrinfo(host_name_deferred, nullptr, &hints);
697 // t3's dns query should got returned first
698 EXPECT_TRUE(t3_task_done);
699 EXPECT_EQ(1U, GetNumQueries(dns1, host_name_deferred));
700 EXPECT_TRUE(result != nullptr);
701 EXPECT_EQ("1.2.3.4", ToString(result));
702 });
703
704 // ensuring t1 and t2 handler functions are processed in order
705 usleep(100 * 1000);
706 std::thread t2([&, this]() {
707 ASSERT_TRUE(
708 mDnsClient.SetResolversForNetwork(servers_for_t2, kDefaultSearchDomains, params));
709 ScopedAddrinfo result = safe_getaddrinfo(host_name_deferred, nullptr, &hints);
710 EXPECT_TRUE(t3_task_done);
711 EXPECT_EQ(0U, GetNumQueries(dns2, host_name_deferred));
712 EXPECT_TRUE(result != nullptr);
713 EXPECT_EQ("1.2.3.4", ToString(result));
714
715 std::vector<std::string> res_servers;
716 std::vector<std::string> res_domains;
717 std::vector<std::string> res_tls_servers;
Bernie Innocenti758005f2019-02-19 18:08:36 +0900718 res_params res_params;
Ken Chen92bed612018-12-22 21:46:55 +0800719 std::vector<ResolverStats> res_stats;
720 int wait_for_pending_req_timeout_count;
Luke Huangf8215372019-11-22 11:53:41 +0800721 ASSERT_TRUE(DnsResponderClient::GetResolverInfo(
722 mDnsClient.resolvService(), TEST_NETID, &res_servers, &res_domains,
723 &res_tls_servers, &res_params, &res_stats, &wait_for_pending_req_timeout_count));
Ken Chen92bed612018-12-22 21:46:55 +0800724 EXPECT_EQ(0, wait_for_pending_req_timeout_count);
725 });
726
727 // ensuring t2 and t3 handler functions are processed in order
728 usleep(100 * 1000);
729 std::thread t3([&, this]() {
730 ASSERT_TRUE(
731 mDnsClient.SetResolversForNetwork(servers_for_t3, kDefaultSearchDomains, params));
732 ScopedAddrinfo result = safe_getaddrinfo(host_name_normal, nullptr, &hints);
733 EXPECT_EQ(1U, GetNumQueries(dns1, host_name_deferred));
734 EXPECT_EQ(0U, GetNumQueries(dns2, host_name_deferred));
735 EXPECT_EQ(1U, GetNumQueries(dns3, host_name_normal));
736 EXPECT_TRUE(result != nullptr);
737 EXPECT_EQ("1.2.3.5", ToString(result));
738
739 t3_task_done = true;
740 dns1.setDeferredResp(false);
741 });
742 t3.join();
743 t1.join();
744 t2.join();
745}
746
lifr4e4a2e02019-01-29 16:53:51 +0800747TEST_F(ResolverTest, GetAddrInfo_cnames) {
748 constexpr char host_name[] = "host.example.com.";
749 test::DNSResponder dns;
750 const std::vector<DnsRecord> records = {
751 {kHelloExampleCom, ns_type::ns_t_cname, "a.example.com."},
752 {"a.example.com.", ns_type::ns_t_cname, "b.example.com."},
753 {"b.example.com.", ns_type::ns_t_cname, "c.example.com."},
754 {"c.example.com.", ns_type::ns_t_cname, "d.example.com."},
755 {"d.example.com.", ns_type::ns_t_cname, "e.example.com."},
756 {"e.example.com.", ns_type::ns_t_cname, host_name},
757 {host_name, ns_type::ns_t_a, "1.2.3.3"},
758 {host_name, ns_type::ns_t_aaaa, "2001:db8::42"},
759 };
760 StartDns(dns, records);
761 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
762
763 addrinfo hints = {.ai_family = AF_INET};
764 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
765 EXPECT_TRUE(result != nullptr);
766 EXPECT_EQ("1.2.3.3", ToString(result));
767
768 dns.clearQueries();
769 hints = {.ai_family = AF_INET6};
770 result = safe_getaddrinfo("hello", nullptr, &hints);
771 EXPECT_TRUE(result != nullptr);
772 EXPECT_EQ("2001:db8::42", ToString(result));
773}
774
775TEST_F(ResolverTest, GetAddrInfo_cnamesNoIpAddress) {
776 test::DNSResponder dns;
777 const std::vector<DnsRecord> records = {
778 {kHelloExampleCom, ns_type::ns_t_cname, "a.example.com."},
779 };
780 StartDns(dns, records);
781 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
782
783 addrinfo hints = {.ai_family = AF_INET};
784 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
785 EXPECT_TRUE(result == nullptr);
786
787 dns.clearQueries();
788 hints = {.ai_family = AF_INET6};
789 result = safe_getaddrinfo("hello", nullptr, &hints);
790 EXPECT_TRUE(result == nullptr);
791}
792
793TEST_F(ResolverTest, GetAddrInfo_cnamesIllegalRdata) {
794 test::DNSResponder dns;
795 const std::vector<DnsRecord> records = {
796 {kHelloExampleCom, ns_type::ns_t_cname, ".!#?"},
797 };
798 StartDns(dns, records);
799 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
800
801 addrinfo hints = {.ai_family = AF_INET};
802 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
803 EXPECT_TRUE(result == nullptr);
804
805 dns.clearQueries();
806 hints = {.ai_family = AF_INET6};
807 result = safe_getaddrinfo("hello", nullptr, &hints);
808 EXPECT_TRUE(result == nullptr);
809}
810
Ken Chenb9fa2062018-11-13 21:51:13 +0800811TEST_F(ResolverTest, MultidomainResolution) {
Xiao Ma09b71022018-12-11 17:56:32 +0900812 constexpr char host_name[] = "nihao.example2.com.";
Luke Huangf8215372019-11-22 11:53:41 +0800813 std::vector<std::string> searchDomains = {"example1.com", "example2.com", "example3.com"};
Ken Chenb9fa2062018-11-13 21:51:13 +0800814
Xiao Ma09b71022018-12-11 17:56:32 +0900815 test::DNSResponder dns("127.0.0.6");
816 StartDns(dns, {{host_name, ns_type::ns_t_a, "1.2.3.3"}});
817 ASSERT_TRUE(mDnsClient.SetResolversForNetwork({"127.0.0.6"}, searchDomains));
818
Ken Chenb9fa2062018-11-13 21:51:13 +0800819 const hostent* result = gethostbyname("nihao");
Xiao Ma09b71022018-12-11 17:56:32 +0900820
Ken Chenb9fa2062018-11-13 21:51:13 +0800821 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, host_name));
822 ASSERT_FALSE(result == nullptr);
823 ASSERT_EQ(4, result->h_length);
824 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
825 EXPECT_EQ("1.2.3.3", ToString(result));
826 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
Ken Chenb9fa2062018-11-13 21:51:13 +0800827}
828
829TEST_F(ResolverTest, GetAddrInfoV6_numeric) {
Ken Chenb9fa2062018-11-13 21:51:13 +0800830 constexpr char host_name[] = "ohayou.example.com.";
831 constexpr char numeric_addr[] = "fe80::1%lo";
832
Xiao Ma09b71022018-12-11 17:56:32 +0900833 test::DNSResponder dns;
Ken Chenb9fa2062018-11-13 21:51:13 +0800834 dns.setResponseProbability(0.0);
Xiao Ma09b71022018-12-11 17:56:32 +0900835 StartDns(dns, {{host_name, ns_type::ns_t_aaaa, "2001:db8::5"}});
836 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +0800837
838 addrinfo hints = {.ai_family = AF_INET6};
839 ScopedAddrinfo result = safe_getaddrinfo(numeric_addr, nullptr, &hints);
840 EXPECT_TRUE(result != nullptr);
841 EXPECT_EQ(numeric_addr, ToString(result));
842 EXPECT_TRUE(dns.queries().empty()); // Ensure no DNS queries were sent out
843
844 // Now try a non-numeric hostname query with the AI_NUMERICHOST flag set.
845 // We should fail without sending out a DNS query.
846 hints.ai_flags |= AI_NUMERICHOST;
847 result = safe_getaddrinfo(host_name, nullptr, &hints);
848 EXPECT_TRUE(result == nullptr);
849 EXPECT_TRUE(dns.queries().empty()); // Ensure no DNS queries were sent out
850}
851
852TEST_F(ResolverTest, GetAddrInfoV6_failing) {
Xiao Ma09b71022018-12-11 17:56:32 +0900853 constexpr char listen_addr0[] = "127.0.0.7";
854 constexpr char listen_addr1[] = "127.0.0.8";
Ken Chenb9fa2062018-11-13 21:51:13 +0800855 const char* host_name = "ohayou.example.com.";
Xiao Ma09b71022018-12-11 17:56:32 +0900856
857 test::DNSResponder dns0(listen_addr0);
858 test::DNSResponder dns1(listen_addr1);
Ken Chenb9fa2062018-11-13 21:51:13 +0800859 dns0.setResponseProbability(0.0);
Xiao Ma09b71022018-12-11 17:56:32 +0900860 StartDns(dns0, {{host_name, ns_type::ns_t_aaaa, "2001:db8::5"}});
861 StartDns(dns1, {{host_name, ns_type::ns_t_aaaa, "2001:db8::6"}});
862
Luke Huangf8215372019-11-22 11:53:41 +0800863 std::vector<std::string> servers = {listen_addr0, listen_addr1};
Ken Chenb9fa2062018-11-13 21:51:13 +0800864 // <sample validity in s> <success threshold in percent> <min samples> <max samples>
865 int sample_count = 8;
Luke Huangf8215372019-11-22 11:53:41 +0800866 const std::vector<int> params = {300, 25, sample_count, sample_count};
Xiao Ma09b71022018-12-11 17:56:32 +0900867 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, kDefaultSearchDomains, params));
Ken Chenb9fa2062018-11-13 21:51:13 +0800868
869 // Repeatedly perform resolutions for non-existing domains until MAXNSSAMPLES resolutions have
870 // reached the dns0, which is set to fail. No more requests should then arrive at that server
871 // for the next sample_lifetime seconds.
872 // TODO: This approach is implementation-dependent, change once metrics reporting is available.
Xiao Ma09b71022018-12-11 17:56:32 +0900873 const addrinfo hints = {.ai_family = AF_INET6};
Bernie Innocentib102dd22018-12-04 14:57:48 +0900874 for (int i = 0; i < sample_count; ++i) {
Ken Chenb9fa2062018-11-13 21:51:13 +0800875 std::string domain = StringPrintf("nonexistent%d", i);
876 ScopedAddrinfo result = safe_getaddrinfo(domain.c_str(), nullptr, &hints);
877 }
878 // Due to 100% errors for all possible samples, the server should be ignored from now on and
879 // only the second one used for all following queries, until NSSAMPLE_VALIDITY is reached.
880 dns0.clearQueries();
881 dns1.clearQueries();
882 ScopedAddrinfo result = safe_getaddrinfo("ohayou", nullptr, &hints);
883 EXPECT_TRUE(result != nullptr);
884 EXPECT_EQ(0U, GetNumQueries(dns0, host_name));
885 EXPECT_EQ(1U, GetNumQueries(dns1, host_name));
886}
887
888TEST_F(ResolverTest, GetAddrInfoV6_nonresponsive) {
Xiao Ma09b71022018-12-11 17:56:32 +0900889 constexpr char listen_addr0[] = "127.0.0.7";
890 constexpr char listen_addr1[] = "127.0.0.8";
891 constexpr char listen_srv[] = "53";
892 constexpr char host_name1[] = "ohayou.example.com.";
893 constexpr char host_name2[] = "ciao.example.com.";
Luke Huang483cf332019-06-03 17:24:51 +0800894 const std::vector<std::string> defaultSearchDomain = {"example.com"};
895 // The minimal timeout is 1000ms, so we can't decrease timeout
896 // So reduce retry count.
897 const std::vector<int> reduceRetryParams = {
898 300, // sample validity in seconds
899 25, // success threshod in percent
900 8, 8, // {MIN,MAX}_SAMPLES
901 1000, // BASE_TIMEOUT_MSEC
902 1, // retry count
903 };
Xiao Ma09b71022018-12-11 17:56:32 +0900904 const std::vector<DnsRecord> records0 = {
905 {host_name1, ns_type::ns_t_aaaa, "2001:db8::5"},
906 {host_name2, ns_type::ns_t_aaaa, "2001:db8::5"},
907 };
908 const std::vector<DnsRecord> records1 = {
909 {host_name1, ns_type::ns_t_aaaa, "2001:db8::6"},
910 {host_name2, ns_type::ns_t_aaaa, "2001:db8::6"},
911 };
Ken Chenb9fa2062018-11-13 21:51:13 +0800912
913 // dns0 does not respond with 100% probability, while
914 // dns1 responds normally, at least initially.
Mike Yufc125e42019-05-15 20:41:28 +0800915 test::DNSResponder dns0(listen_addr0, listen_srv, static_cast<ns_rcode>(-1));
916 test::DNSResponder dns1(listen_addr1, listen_srv, static_cast<ns_rcode>(-1));
Ken Chenb9fa2062018-11-13 21:51:13 +0800917 dns0.setResponseProbability(0.0);
Xiao Ma09b71022018-12-11 17:56:32 +0900918 StartDns(dns0, records0);
919 StartDns(dns1, records1);
Luke Huang483cf332019-06-03 17:24:51 +0800920 ASSERT_TRUE(mDnsClient.SetResolversForNetwork({listen_addr0, listen_addr1}, defaultSearchDomain,
921 reduceRetryParams));
Ken Chenb9fa2062018-11-13 21:51:13 +0800922
Luke Huang483cf332019-06-03 17:24:51 +0800923 // Specify ai_socktype to make getaddrinfo will only query 1 time
924 const addrinfo hints = {.ai_family = AF_INET6, .ai_socktype = SOCK_STREAM};
Ken Chenb9fa2062018-11-13 21:51:13 +0800925
926 // dns0 will ignore the request, and we'll fallback to dns1 after the first
927 // retry.
928 ScopedAddrinfo result = safe_getaddrinfo(host_name1, nullptr, &hints);
929 EXPECT_TRUE(result != nullptr);
930 EXPECT_EQ(1U, GetNumQueries(dns0, host_name1));
931 EXPECT_EQ(1U, GetNumQueries(dns1, host_name1));
932
933 // Now make dns1 also ignore 100% requests... The resolve should alternate
Luke Huang483cf332019-06-03 17:24:51 +0800934 // queries between the nameservers and fail
Ken Chenb9fa2062018-11-13 21:51:13 +0800935 dns1.setResponseProbability(0.0);
936 addrinfo* result2 = nullptr;
937 EXPECT_EQ(EAI_NODATA, getaddrinfo(host_name2, nullptr, &hints, &result2));
938 EXPECT_EQ(nullptr, result2);
Luke Huang483cf332019-06-03 17:24:51 +0800939 EXPECT_EQ(1U, GetNumQueries(dns0, host_name2));
940 EXPECT_EQ(1U, GetNumQueries(dns1, host_name2));
Ken Chenb9fa2062018-11-13 21:51:13 +0800941}
942
943TEST_F(ResolverTest, GetAddrInfoV6_concurrent) {
Xiao Ma09b71022018-12-11 17:56:32 +0900944 constexpr char listen_addr0[] = "127.0.0.9";
945 constexpr char listen_addr1[] = "127.0.0.10";
946 constexpr char listen_addr2[] = "127.0.0.11";
947 constexpr char host_name[] = "konbanha.example.com.";
948
949 test::DNSResponder dns0(listen_addr0);
950 test::DNSResponder dns1(listen_addr1);
951 test::DNSResponder dns2(listen_addr2);
952 StartDns(dns0, {{host_name, ns_type::ns_t_aaaa, "2001:db8::5"}});
953 StartDns(dns1, {{host_name, ns_type::ns_t_aaaa, "2001:db8::6"}});
954 StartDns(dns2, {{host_name, ns_type::ns_t_aaaa, "2001:db8::7"}});
955
Luke Huangf8215372019-11-22 11:53:41 +0800956 const std::vector<std::string> servers = {listen_addr0, listen_addr1, listen_addr2};
Ken Chenb9fa2062018-11-13 21:51:13 +0800957 std::vector<std::thread> threads(10);
958 for (std::thread& thread : threads) {
Luke Huangf8215372019-11-22 11:53:41 +0800959 thread = std::thread([this, &servers]() {
960 unsigned delay = arc4random_uniform(1 * 1000 * 1000); // <= 1s
Ken Chenb9fa2062018-11-13 21:51:13 +0800961 usleep(delay);
962 std::vector<std::string> serverSubset;
963 for (const auto& server : servers) {
964 if (arc4random_uniform(2)) {
965 serverSubset.push_back(server);
966 }
967 }
968 if (serverSubset.empty()) serverSubset = servers;
Xiao Ma09b71022018-12-11 17:56:32 +0900969 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(serverSubset));
970 const addrinfo hints = {.ai_family = AF_INET6};
Ken Chenb9fa2062018-11-13 21:51:13 +0800971 addrinfo* result = nullptr;
972 int rv = getaddrinfo("konbanha", nullptr, &hints, &result);
973 EXPECT_EQ(0, rv) << "error [" << rv << "] " << gai_strerror(rv);
974 if (result) {
975 freeaddrinfo(result);
976 result = nullptr;
977 }
978 });
979 }
980 for (std::thread& thread : threads) {
981 thread.join();
982 }
Ken Chen92bed612018-12-22 21:46:55 +0800983
984 std::vector<std::string> res_servers;
985 std::vector<std::string> res_domains;
986 std::vector<std::string> res_tls_servers;
Bernie Innocenti758005f2019-02-19 18:08:36 +0900987 res_params res_params;
Ken Chen92bed612018-12-22 21:46:55 +0800988 std::vector<ResolverStats> res_stats;
989 int wait_for_pending_req_timeout_count;
Luke Huangf8215372019-11-22 11:53:41 +0800990 ASSERT_TRUE(DnsResponderClient::GetResolverInfo(
991 mDnsClient.resolvService(), TEST_NETID, &res_servers, &res_domains, &res_tls_servers,
992 &res_params, &res_stats, &wait_for_pending_req_timeout_count));
Ken Chen92bed612018-12-22 21:46:55 +0800993 EXPECT_EQ(0, wait_for_pending_req_timeout_count);
Ken Chenb9fa2062018-11-13 21:51:13 +0800994}
995
Mike Yu8ac63402019-12-02 15:28:38 +0800996TEST_F(ResolverTest, SkipBadServersDueToInternalError) {
997 constexpr char listen_addr1[] = "fe80::1";
998 constexpr char listen_addr2[] = "255.255.255.255";
999 constexpr char listen_addr3[] = "127.0.0.3";
1000
1001 test::DNSResponder dns(listen_addr3);
1002 ASSERT_TRUE(dns.startServer());
1003
1004 ResolverParamsParcel parcel = DnsResponderClient::GetDefaultResolverParamsParcel();
1005 parcel.servers = {listen_addr1, listen_addr2, listen_addr3};
1006
1007 // Bad servers can be distinguished after two attempts.
1008 parcel.minSamples = 2;
1009 ASSERT_TRUE(mDnsClient.SetResolversFromParcel(parcel));
1010
1011 // Start querying five times.
1012 for (int i = 0; i < 5; i++) {
1013 std::string hostName = StringPrintf("hello%d.com.", i);
1014 dns.addMapping(hostName, ns_type::ns_t_a, "1.2.3.4");
1015 const addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
1016 EXPECT_TRUE(safe_getaddrinfo(hostName.c_str(), nullptr, &hints) != nullptr);
1017 }
1018
Mike Yue2162e52020-03-04 18:43:46 +08001019 const std::vector<NameserverStats> expectedCleartextDnsStats = {
1020 NameserverStats(listen_addr1).setInternalErrors(2),
1021 NameserverStats(listen_addr2).setInternalErrors(2),
1022 NameserverStats(listen_addr3).setSuccesses(5),
1023 };
1024 EXPECT_TRUE(expectStatsFromGetResolverInfo(expectedCleartextDnsStats));
Mike Yu8ac63402019-12-02 15:28:38 +08001025}
1026
1027TEST_F(ResolverTest, SkipBadServersDueToTimeout) {
1028 constexpr char listen_addr1[] = "127.0.0.3";
1029 constexpr char listen_addr2[] = "127.0.0.4";
1030
1031 // Set dns1 non-responsive and dns2 workable.
1032 test::DNSResponder dns1(listen_addr1, test::kDefaultListenService, static_cast<ns_rcode>(-1));
1033 test::DNSResponder dns2(listen_addr2);
1034 dns1.setResponseProbability(0.0);
1035 ASSERT_TRUE(dns1.startServer());
1036 ASSERT_TRUE(dns2.startServer());
1037
1038 ResolverParamsParcel parcel = DnsResponderClient::GetDefaultResolverParamsParcel();
1039 parcel.servers = {listen_addr1, listen_addr2};
1040
1041 // Bad servers can be distinguished after two attempts.
1042 parcel.minSamples = 2;
1043 ASSERT_TRUE(mDnsClient.SetResolversFromParcel(parcel));
1044
1045 // Start querying five times.
1046 for (int i = 0; i < 5; i++) {
1047 std::string hostName = StringPrintf("hello%d.com.", i);
1048 dns1.addMapping(hostName, ns_type::ns_t_a, "1.2.3.4");
1049 dns2.addMapping(hostName, ns_type::ns_t_a, "1.2.3.5");
1050 const addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
1051 EXPECT_TRUE(safe_getaddrinfo(hostName.c_str(), nullptr, &hints) != nullptr);
1052 }
1053
Mike Yue2162e52020-03-04 18:43:46 +08001054 const std::vector<NameserverStats> expectedCleartextDnsStats = {
1055 NameserverStats(listen_addr1).setTimeouts(2),
1056 NameserverStats(listen_addr2).setSuccesses(5),
1057 };
1058 EXPECT_TRUE(expectStatsFromGetResolverInfo(expectedCleartextDnsStats));
Mike Yu8ac63402019-12-02 15:28:38 +08001059 EXPECT_EQ(dns1.queries().size(), 2U);
1060 EXPECT_EQ(dns2.queries().size(), 5U);
1061}
1062
chenbrucefd837fa2019-10-29 18:35:36 +08001063TEST_F(ResolverTest, GetAddrInfoFromCustTable_InvalidInput) {
1064 constexpr char hostnameNoip[] = "noip.example.com.";
1065 constexpr char hostnameInvalidip[] = "invalidip.example.com.";
1066 const std::vector<aidl::android::net::ResolverHostsParcel> invalidCustHosts = {
1067 {"", hostnameNoip},
1068 {"wrong IP", hostnameInvalidip},
1069 };
1070 test::DNSResponder dns;
1071 StartDns(dns, {});
1072 auto resolverParams = DnsResponderClient::GetDefaultResolverParamsParcel();
Ken Chen99344882020-01-01 14:59:38 +08001073 resolverParams.experimentalOptions.hosts = invalidCustHosts;
chenbrucefd837fa2019-10-29 18:35:36 +08001074 ASSERT_TRUE(mDnsClient.resolvService()->setResolverConfiguration(resolverParams).isOk());
1075 for (const auto& hostname : {hostnameNoip, hostnameInvalidip}) {
1076 // The query won't get data from customized table because of invalid customized table
1077 // and DNSResponder also has no records. hostnameNoip has never registered and
1078 // hostnameInvalidip has registered but wrong IP.
1079 const addrinfo hints = {.ai_family = AF_UNSPEC};
1080 ScopedAddrinfo result = safe_getaddrinfo(hostname, nullptr, &hints);
1081 ASSERT_TRUE(result == nullptr);
1082 EXPECT_EQ(4U, GetNumQueries(dns, hostname));
1083 }
1084}
1085
1086TEST_F(ResolverTest, GetAddrInfoFromCustTable) {
1087 constexpr char hostnameV4[] = "v4only.example.com.";
1088 constexpr char hostnameV6[] = "v6only.example.com.";
1089 constexpr char hostnameV4V6[] = "v4v6.example.com.";
1090 constexpr char custAddrV4[] = "1.2.3.4";
1091 constexpr char custAddrV6[] = "::1.2.3.4";
1092 constexpr char dnsSvAddrV4[] = "1.2.3.5";
1093 constexpr char dnsSvAddrV6[] = "::1.2.3.5";
1094 const std::vector<aidl::android::net::ResolverHostsParcel> custHostV4 = {
1095 {custAddrV4, hostnameV4},
1096 };
1097 const std::vector<aidl::android::net::ResolverHostsParcel> custHostV6 = {
1098 {custAddrV6, hostnameV6},
1099 };
1100 const std::vector<aidl::android::net::ResolverHostsParcel> custHostV4V6 = {
1101 {custAddrV4, hostnameV4V6},
1102 {custAddrV6, hostnameV4V6},
1103 };
1104 const std::vector<DnsRecord> dnsSvHostV4 = {
1105 {hostnameV4, ns_type::ns_t_a, dnsSvAddrV4},
1106 };
1107 const std::vector<DnsRecord> dnsSvHostV6 = {
1108 {hostnameV6, ns_type::ns_t_aaaa, dnsSvAddrV6},
1109 };
1110 const std::vector<DnsRecord> dnsSvHostV4V6 = {
1111 {hostnameV4V6, ns_type::ns_t_a, dnsSvAddrV4},
1112 {hostnameV4V6, ns_type::ns_t_aaaa, dnsSvAddrV6},
1113 };
1114 struct TestConfig {
1115 const std::string name;
1116 const std::vector<aidl::android::net::ResolverHostsParcel> customizedHosts;
1117 const std::vector<DnsRecord> dnsserverHosts;
1118 const std::vector<std::string> queryResult;
1119 std::string asParameters() const {
1120 return StringPrintf("name: %s, customizedHosts: %s, dnsserverHosts: %s", name.c_str(),
1121 customizedHosts.empty() ? "No" : "Yes",
1122 dnsserverHosts.empty() ? "No" : "Yes");
1123 }
1124 } testConfigs[]{
1125 // clang-format off
1126 {hostnameV4, {}, {}, {}},
1127 {hostnameV4, {}, dnsSvHostV4, {dnsSvAddrV4}},
1128 {hostnameV4, custHostV4, {}, {custAddrV4}},
1129 {hostnameV4, custHostV4, dnsSvHostV4, {custAddrV4}},
1130 {hostnameV6, {}, {}, {}},
1131 {hostnameV6, {}, dnsSvHostV6, {dnsSvAddrV6}},
1132 {hostnameV6, custHostV6, {}, {custAddrV6}},
1133 {hostnameV6, custHostV6, dnsSvHostV6, {custAddrV6}},
1134 {hostnameV4V6, {}, {}, {}},
1135 {hostnameV4V6, {}, dnsSvHostV4V6, {dnsSvAddrV4, dnsSvAddrV6}},
1136 {hostnameV4V6, custHostV4V6, {}, {custAddrV4, custAddrV6}},
1137 {hostnameV4V6, custHostV4V6, dnsSvHostV4V6, {custAddrV4, custAddrV6}},
1138 // clang-format on
1139 };
1140
1141 for (const auto& config : testConfigs) {
1142 SCOPED_TRACE(config.asParameters());
1143
1144 test::DNSResponder dns;
1145 StartDns(dns, config.dnsserverHosts);
1146
1147 auto resolverParams = DnsResponderClient::GetDefaultResolverParamsParcel();
Ken Chen99344882020-01-01 14:59:38 +08001148 resolverParams.experimentalOptions.hosts = config.customizedHosts;
chenbrucefd837fa2019-10-29 18:35:36 +08001149 ASSERT_TRUE(mDnsClient.resolvService()->setResolverConfiguration(resolverParams).isOk());
1150 const addrinfo hints = {.ai_family = AF_UNSPEC, .ai_socktype = SOCK_STREAM};
1151 ScopedAddrinfo result = safe_getaddrinfo(config.name.c_str(), nullptr, &hints);
1152 if (config.customizedHosts.empty() && config.dnsserverHosts.empty()) {
1153 ASSERT_TRUE(result == nullptr);
1154 EXPECT_EQ(2U, GetNumQueries(dns, config.name.c_str()));
1155 } else {
1156 ASSERT_TRUE(result != nullptr);
1157 EXPECT_THAT(ToStrings(result), testing::UnorderedElementsAreArray(config.queryResult));
1158 EXPECT_EQ(config.customizedHosts.empty() ? 2U : 0U,
1159 GetNumQueries(dns, config.name.c_str()));
1160 }
1161
1162 EXPECT_TRUE(mDnsClient.resolvService()->flushNetworkCache(TEST_NETID).isOk());
1163 }
1164}
1165
1166TEST_F(ResolverTest, GetAddrInfoFromCustTable_Modify) {
1167 constexpr char hostnameV4V6[] = "v4v6.example.com.";
1168 constexpr char custAddrV4[] = "1.2.3.4";
1169 constexpr char custAddrV6[] = "::1.2.3.4";
1170 constexpr char dnsSvAddrV4[] = "1.2.3.5";
1171 constexpr char dnsSvAddrV6[] = "::1.2.3.5";
1172 const std::vector<DnsRecord> dnsSvHostV4V6 = {
1173 {hostnameV4V6, ns_type::ns_t_a, dnsSvAddrV4},
1174 {hostnameV4V6, ns_type::ns_t_aaaa, dnsSvAddrV6},
1175 };
1176 const std::vector<aidl::android::net::ResolverHostsParcel> custHostV4V6 = {
1177 {custAddrV4, hostnameV4V6},
1178 {custAddrV6, hostnameV4V6},
1179 };
1180 test::DNSResponder dns;
1181 StartDns(dns, dnsSvHostV4V6);
1182 auto resolverParams = DnsResponderClient::GetDefaultResolverParamsParcel();
1183
Ken Chen99344882020-01-01 14:59:38 +08001184 resolverParams.experimentalOptions.hosts = custHostV4V6;
chenbrucefd837fa2019-10-29 18:35:36 +08001185 ASSERT_TRUE(mDnsClient.resolvService()->setResolverConfiguration(resolverParams).isOk());
1186 const addrinfo hints = {.ai_family = AF_UNSPEC, .ai_socktype = SOCK_STREAM};
1187 ScopedAddrinfo result = safe_getaddrinfo(hostnameV4V6, nullptr, &hints);
1188 ASSERT_TRUE(result != nullptr);
1189 EXPECT_THAT(ToStrings(result), testing::UnorderedElementsAreArray({custAddrV4, custAddrV6}));
1190 EXPECT_EQ(0U, GetNumQueries(dns, hostnameV4V6));
1191
Ken Chen99344882020-01-01 14:59:38 +08001192 resolverParams.experimentalOptions.hosts = {};
chenbrucefd837fa2019-10-29 18:35:36 +08001193 ASSERT_TRUE(mDnsClient.resolvService()->setResolverConfiguration(resolverParams).isOk());
1194 result = safe_getaddrinfo(hostnameV4V6, nullptr, &hints);
1195 ASSERT_TRUE(result != nullptr);
1196 EXPECT_THAT(ToStrings(result), testing::UnorderedElementsAreArray({dnsSvAddrV4, dnsSvAddrV6}));
1197 EXPECT_EQ(2U, GetNumQueries(dns, hostnameV4V6));
1198}
1199
Ken Chenb9fa2062018-11-13 21:51:13 +08001200TEST_F(ResolverTest, EmptySetup) {
Ken Chenb9fa2062018-11-13 21:51:13 +08001201 std::vector<std::string> servers;
1202 std::vector<std::string> domains;
Xiao Ma09b71022018-12-11 17:56:32 +09001203 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, domains));
Ken Chenb9fa2062018-11-13 21:51:13 +08001204 std::vector<std::string> res_servers;
1205 std::vector<std::string> res_domains;
Mike Yu0a1c53d2018-11-26 13:26:21 +09001206 std::vector<std::string> res_tls_servers;
Bernie Innocenti758005f2019-02-19 18:08:36 +09001207 res_params res_params;
Ken Chenb9fa2062018-11-13 21:51:13 +08001208 std::vector<ResolverStats> res_stats;
Ken Chen92bed612018-12-22 21:46:55 +08001209 int wait_for_pending_req_timeout_count;
Luke Huangf8215372019-11-22 11:53:41 +08001210 ASSERT_TRUE(DnsResponderClient::GetResolverInfo(
1211 mDnsClient.resolvService(), TEST_NETID, &res_servers, &res_domains, &res_tls_servers,
1212 &res_params, &res_stats, &wait_for_pending_req_timeout_count));
Ken Chenb9fa2062018-11-13 21:51:13 +08001213 EXPECT_EQ(0U, res_servers.size());
1214 EXPECT_EQ(0U, res_domains.size());
Mike Yu0a1c53d2018-11-26 13:26:21 +09001215 EXPECT_EQ(0U, res_tls_servers.size());
Luke Huang5bd827c2019-03-14 16:10:04 +08001216 ASSERT_EQ(static_cast<size_t>(IDnsResolver::RESOLVER_PARAMS_COUNT), kDefaultParams.size());
1217 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_SAMPLE_VALIDITY],
1218 res_params.sample_validity);
1219 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_SUCCESS_THRESHOLD],
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +09001220 res_params.success_threshold);
Luke Huang5bd827c2019-03-14 16:10:04 +08001221 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_MIN_SAMPLES], res_params.min_samples);
1222 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_MAX_SAMPLES], res_params.max_samples);
1223 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_BASE_TIMEOUT_MSEC],
Ken Chenb9fa2062018-11-13 21:51:13 +08001224 res_params.base_timeout_msec);
Luke Huang5bd827c2019-03-14 16:10:04 +08001225 EXPECT_EQ(kDefaultParams[IDnsResolver::RESOLVER_PARAMS_RETRY_COUNT], res_params.retry_count);
Ken Chenb9fa2062018-11-13 21:51:13 +08001226}
1227
1228TEST_F(ResolverTest, SearchPathChange) {
Xiao Ma09b71022018-12-11 17:56:32 +09001229 constexpr char listen_addr[] = "127.0.0.13";
1230 constexpr char host_name1[] = "test13.domain1.org.";
1231 constexpr char host_name2[] = "test13.domain2.org.";
Luke Huangf8215372019-11-22 11:53:41 +08001232 std::vector<std::string> servers = {listen_addr};
1233 std::vector<std::string> domains = {"domain1.org"};
Xiao Ma09b71022018-12-11 17:56:32 +09001234
1235 const std::vector<DnsRecord> records = {
1236 {host_name1, ns_type::ns_t_aaaa, "2001:db8::13"},
1237 {host_name2, ns_type::ns_t_aaaa, "2001:db8::1:13"},
1238 };
1239 test::DNSResponder dns(listen_addr);
1240 StartDns(dns, records);
1241 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, domains));
Ken Chenb9fa2062018-11-13 21:51:13 +08001242
1243 const addrinfo hints = {.ai_family = AF_INET6};
1244 ScopedAddrinfo result = safe_getaddrinfo("test13", nullptr, &hints);
1245 EXPECT_TRUE(result != nullptr);
1246 EXPECT_EQ(1U, dns.queries().size());
1247 EXPECT_EQ(1U, GetNumQueries(dns, host_name1));
1248 EXPECT_EQ("2001:db8::13", ToString(result));
1249
1250 // Test that changing the domain search path on its own works.
Luke Huangf8215372019-11-22 11:53:41 +08001251 domains = {"domain2.org"};
Xiao Ma09b71022018-12-11 17:56:32 +09001252 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, domains));
Ken Chenb9fa2062018-11-13 21:51:13 +08001253 dns.clearQueries();
1254
1255 result = safe_getaddrinfo("test13", nullptr, &hints);
1256 EXPECT_TRUE(result != nullptr);
1257 EXPECT_EQ(1U, dns.queries().size());
1258 EXPECT_EQ(1U, GetNumQueries(dns, host_name2));
1259 EXPECT_EQ("2001:db8::1:13", ToString(result));
1260}
1261
Luke Huang2dac4382019-06-24 13:28:44 +08001262namespace {
1263
Luke Huangf8215372019-11-22 11:53:41 +08001264std::vector<std::string> getResolverDomains(aidl::android::net::IDnsResolver* dnsResolverService,
Luke Huang2dac4382019-06-24 13:28:44 +08001265 unsigned netId) {
1266 std::vector<std::string> res_servers;
1267 std::vector<std::string> res_domains;
1268 std::vector<std::string> res_tls_servers;
1269 res_params res_params;
1270 std::vector<ResolverStats> res_stats;
1271 int wait_for_pending_req_timeout_count;
Luke Huangf8215372019-11-22 11:53:41 +08001272 DnsResponderClient::GetResolverInfo(dnsResolverService, netId, &res_servers, &res_domains,
1273 &res_tls_servers, &res_params, &res_stats,
1274 &wait_for_pending_req_timeout_count);
Luke Huang2dac4382019-06-24 13:28:44 +08001275 return res_domains;
1276}
1277
1278} // namespace
1279
1280TEST_F(ResolverTest, SearchPathPrune) {
1281 constexpr size_t DUPLICATED_DOMAIN_NUM = 3;
1282 constexpr char listen_addr[] = "127.0.0.13";
1283 constexpr char domian_name1[] = "domain13.org.";
1284 constexpr char domian_name2[] = "domain14.org.";
1285 constexpr char host_name1[] = "test13.domain13.org.";
1286 constexpr char host_name2[] = "test14.domain14.org.";
1287 std::vector<std::string> servers = {listen_addr};
1288
1289 std::vector<std::string> testDomains1;
1290 std::vector<std::string> testDomains2;
1291 // Domain length should be <= 255
1292 // Max number of domains in search path is 6
1293 for (size_t i = 0; i < MAXDNSRCH + 1; i++) {
1294 // Fill up with invalid domain
1295 testDomains1.push_back(std::string(300, i + '0'));
1296 // Fill up with valid but duplicated domain
1297 testDomains2.push_back(StringPrintf("domain%zu.org", i % DUPLICATED_DOMAIN_NUM));
1298 }
1299
1300 // Add valid domain used for query.
1301 testDomains1.push_back(domian_name1);
1302
1303 // Add valid domain twice used for query.
1304 testDomains2.push_back(domian_name2);
1305 testDomains2.push_back(domian_name2);
1306
1307 const std::vector<DnsRecord> records = {
1308 {host_name1, ns_type::ns_t_aaaa, "2001:db8::13"},
1309 {host_name2, ns_type::ns_t_aaaa, "2001:db8::1:13"},
1310 };
1311 test::DNSResponder dns(listen_addr);
1312 StartDns(dns, records);
1313 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, testDomains1));
1314
1315 const addrinfo hints = {.ai_family = AF_INET6};
1316 ScopedAddrinfo result = safe_getaddrinfo("test13", nullptr, &hints);
1317
1318 EXPECT_TRUE(result != nullptr);
1319
1320 EXPECT_EQ(1U, dns.queries().size());
1321 EXPECT_EQ(1U, GetNumQueries(dns, host_name1));
1322 EXPECT_EQ("2001:db8::13", ToString(result));
1323
1324 const auto& res_domains1 = getResolverDomains(mDnsClient.resolvService(), TEST_NETID);
1325 // Expect 1 valid domain, invalid domains are removed.
1326 ASSERT_EQ(1U, res_domains1.size());
1327 EXPECT_EQ(domian_name1, res_domains1[0]);
1328
1329 dns.clearQueries();
1330
1331 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, testDomains2));
1332
1333 result = safe_getaddrinfo("test14", nullptr, &hints);
1334 EXPECT_TRUE(result != nullptr);
1335
1336 // (3 domains * 2 retries) + 1 success query = 7
1337 EXPECT_EQ(7U, dns.queries().size());
1338 EXPECT_EQ(1U, GetNumQueries(dns, host_name2));
1339 EXPECT_EQ("2001:db8::1:13", ToString(result));
1340
1341 const auto& res_domains2 = getResolverDomains(mDnsClient.resolvService(), TEST_NETID);
1342 // Expect 4 valid domain, duplicate domains are removed.
1343 EXPECT_EQ(DUPLICATED_DOMAIN_NUM + 1U, res_domains2.size());
1344 EXPECT_THAT(
1345 std::vector<std::string>({"domain0.org", "domain1.org", "domain2.org", domian_name2}),
1346 testing::ElementsAreArray(res_domains2));
1347}
1348
Mike Yu0a1c53d2018-11-26 13:26:21 +09001349// If we move this function to dns_responder_client, it will complicate the dependency need of
1350// dns_tls_frontend.h.
1351static void setupTlsServers(const std::vector<std::string>& servers,
waynema0e73c2e2019-07-31 15:04:08 +08001352 std::vector<std::unique_ptr<test::DnsTlsFrontend>>* tls) {
Xiao Ma09b71022018-12-11 17:56:32 +09001353 constexpr char listen_udp[] = "53";
1354 constexpr char listen_tls[] = "853";
Mike Yu0a1c53d2018-11-26 13:26:21 +09001355
1356 for (const auto& server : servers) {
1357 auto t = std::make_unique<test::DnsTlsFrontend>(server, listen_tls, server, listen_udp);
1358 t = std::make_unique<test::DnsTlsFrontend>(server, listen_tls, server, listen_udp);
1359 t->startServer();
Mike Yu0a1c53d2018-11-26 13:26:21 +09001360 tls->push_back(std::move(t));
1361 }
1362}
1363
Mike Yu0a1c53d2018-11-26 13:26:21 +09001364TEST_F(ResolverTest, MaxServerPrune_Binder) {
Mike Yu0a1c53d2018-11-26 13:26:21 +09001365 std::vector<std::string> domains;
1366 std::vector<std::unique_ptr<test::DNSResponder>> dns;
1367 std::vector<std::unique_ptr<test::DnsTlsFrontend>> tls;
1368 std::vector<std::string> servers;
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +09001369 std::vector<DnsResponderClient::Mapping> mappings;
Mike Yu0a1c53d2018-11-26 13:26:21 +09001370
1371 for (unsigned i = 0; i < MAXDNSRCH + 1; i++) {
1372 domains.push_back(StringPrintf("example%u.com", i));
1373 }
Bernie Innocentia5c7b7b2019-01-17 21:28:24 +09001374 ASSERT_NO_FATAL_FAILURE(mDnsClient.SetupMappings(1, domains, &mappings));
1375 ASSERT_NO_FATAL_FAILURE(mDnsClient.SetupDNSServers(MAXNS + 1, mappings, &dns, &servers));
waynema0e73c2e2019-07-31 15:04:08 +08001376 ASSERT_NO_FATAL_FAILURE(setupTlsServers(servers, &tls));
Mike Yu0a1c53d2018-11-26 13:26:21 +09001377
waynema0e73c2e2019-07-31 15:04:08 +08001378 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, domains, kDefaultParams,
1379 kDefaultPrivateDnsHostName));
Mike Yu0a1c53d2018-11-26 13:26:21 +09001380
Mike Yu383855b2019-01-15 17:53:27 +08001381 // If the private DNS validation hasn't completed yet before backend DNS servers stop,
1382 // TLS servers will get stuck in handleOneRequest(), which causes this test stuck in
1383 // ~DnsTlsFrontend() because the TLS server loop threads can't be terminated.
1384 // So, wait for private DNS validation done before stopping backend DNS servers.
1385 for (int i = 0; i < MAXNS; i++) {
chenbruceaff85842019-05-31 15:46:42 +08001386 LOG(INFO) << "Waiting for private DNS validation on " << tls[i]->listen_address() << ".";
Mike Yu724f77d2019-08-16 11:14:50 +08001387 EXPECT_TRUE(WaitForPrivateDnsValidation(tls[i]->listen_address(), true));
chenbruceaff85842019-05-31 15:46:42 +08001388 LOG(INFO) << "private DNS validation on " << tls[i]->listen_address() << " done.";
Mike Yu383855b2019-01-15 17:53:27 +08001389 }
1390
Mike Yu0a1c53d2018-11-26 13:26:21 +09001391 std::vector<std::string> res_servers;
1392 std::vector<std::string> res_domains;
1393 std::vector<std::string> res_tls_servers;
Bernie Innocenti758005f2019-02-19 18:08:36 +09001394 res_params res_params;
Mike Yu0a1c53d2018-11-26 13:26:21 +09001395 std::vector<ResolverStats> res_stats;
Ken Chen92bed612018-12-22 21:46:55 +08001396 int wait_for_pending_req_timeout_count;
Luke Huangf8215372019-11-22 11:53:41 +08001397 ASSERT_TRUE(DnsResponderClient::GetResolverInfo(
1398 mDnsClient.resolvService(), TEST_NETID, &res_servers, &res_domains, &res_tls_servers,
1399 &res_params, &res_stats, &wait_for_pending_req_timeout_count));
Mike Yu0a1c53d2018-11-26 13:26:21 +09001400
1401 // Check the size of the stats and its contents.
1402 EXPECT_EQ(static_cast<size_t>(MAXNS), res_servers.size());
1403 EXPECT_EQ(static_cast<size_t>(MAXNS), res_tls_servers.size());
1404 EXPECT_EQ(static_cast<size_t>(MAXDNSRCH), res_domains.size());
1405 EXPECT_TRUE(std::equal(servers.begin(), servers.begin() + MAXNS, res_servers.begin()));
1406 EXPECT_TRUE(std::equal(servers.begin(), servers.begin() + MAXNS, res_tls_servers.begin()));
1407 EXPECT_TRUE(std::equal(domains.begin(), domains.begin() + MAXDNSRCH, res_domains.begin()));
Mike Yu0a1c53d2018-11-26 13:26:21 +09001408}
1409
1410TEST_F(ResolverTest, ResolverStats) {
Xiao Ma09b71022018-12-11 17:56:32 +09001411 constexpr char listen_addr1[] = "127.0.0.4";
1412 constexpr char listen_addr2[] = "127.0.0.5";
1413 constexpr char listen_addr3[] = "127.0.0.6";
Mike Yu0a1c53d2018-11-26 13:26:21 +09001414
1415 // Set server 1 timeout.
Mike Yufc125e42019-05-15 20:41:28 +08001416 test::DNSResponder dns1(listen_addr1, "53", static_cast<ns_rcode>(-1));
Mike Yu0a1c53d2018-11-26 13:26:21 +09001417 dns1.setResponseProbability(0.0);
1418 ASSERT_TRUE(dns1.startServer());
1419
1420 // Set server 2 responding server failure.
Xiao Ma09b71022018-12-11 17:56:32 +09001421 test::DNSResponder dns2(listen_addr2);
Mike Yu0a1c53d2018-11-26 13:26:21 +09001422 dns2.setResponseProbability(0.0);
1423 ASSERT_TRUE(dns2.startServer());
1424
1425 // Set server 3 workable.
Xiao Ma09b71022018-12-11 17:56:32 +09001426 test::DNSResponder dns3(listen_addr3);
1427 dns3.addMapping(kHelloExampleCom, ns_type::ns_t_a, "1.2.3.4");
Mike Yu0a1c53d2018-11-26 13:26:21 +09001428 ASSERT_TRUE(dns3.startServer());
1429
1430 std::vector<std::string> servers = {listen_addr1, listen_addr2, listen_addr3};
Xiao Ma09b71022018-12-11 17:56:32 +09001431 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Mike Yu0a1c53d2018-11-26 13:26:21 +09001432
1433 dns3.clearQueries();
Xiao Ma09b71022018-12-11 17:56:32 +09001434 const addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
Mike Yu0a1c53d2018-11-26 13:26:21 +09001435 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
Xiao Ma09b71022018-12-11 17:56:32 +09001436 size_t found = GetNumQueries(dns3, kHelloExampleCom);
Mike Yu0a1c53d2018-11-26 13:26:21 +09001437 EXPECT_LE(1U, found);
1438 std::string result_str = ToString(result);
1439 EXPECT_TRUE(result_str == "1.2.3.4") << ", result_str='" << result_str << "'";
1440
Mike Yue2162e52020-03-04 18:43:46 +08001441 const std::vector<NameserverStats> expectedCleartextDnsStats = {
1442 NameserverStats(listen_addr1).setTimeouts(1),
1443 NameserverStats(listen_addr2).setErrors(1),
1444 NameserverStats(listen_addr3).setSuccesses(1),
1445 };
1446 EXPECT_TRUE(expectStatsFromGetResolverInfo(expectedCleartextDnsStats));
Mike Yu0a1c53d2018-11-26 13:26:21 +09001447}
1448
Mike Yu15791832020-02-11 13:38:48 +08001449TEST_F(ResolverTest, AlwaysUseLatestSetupParamsInLookups) {
1450 constexpr char listen_addr1[] = "127.0.0.3";
1451 constexpr char listen_addr2[] = "255.255.255.255";
1452 constexpr char listen_addr3[] = "127.0.0.4";
1453 constexpr char hostname[] = "hello";
1454 constexpr char fqdn_with_search_domain[] = "hello.domain2.com.";
1455
1456 test::DNSResponder dns1(listen_addr1, test::kDefaultListenService, static_cast<ns_rcode>(-1));
1457 dns1.setResponseProbability(0.0);
1458 ASSERT_TRUE(dns1.startServer());
1459
1460 test::DNSResponder dns3(listen_addr3);
1461 StartDns(dns3, {{fqdn_with_search_domain, ns_type::ns_t_a, "1.2.3.4"}});
1462
1463 ResolverParamsParcel parcel = DnsResponderClient::GetDefaultResolverParamsParcel();
1464 parcel.tlsServers.clear();
1465 parcel.servers = {listen_addr1, listen_addr2};
1466 parcel.domains = {"domain1.com", "domain2.com"};
1467 ASSERT_TRUE(mDnsClient.SetResolversFromParcel(parcel));
1468
1469 // Expect the things happening in t1:
1470 // 1. The lookup starts using the first domain for query. It sends queries to the populated
1471 // nameserver list {listen_addr1, listen_addr2} for the hostname "hello.domain1.com".
1472 // 2. A different list of nameservers is updated to the resolver. Revision ID is incremented.
1473 // 3. The query for the hostname times out. The lookup fails to add the timeout record to the
1474 // the stats because of the unmatched revision ID.
1475 // 4. The lookup starts using the second domain for query. It sends queries to the populated
1476 // nameserver list {listen_addr3, listen_addr1, listen_addr2} for another hostname
1477 // "hello.domain2.com".
1478 // 5. The lookup gets the answer and updates a success record to the stats.
1479 std::thread t1([&hostname]() {
1480 const addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
1481 ScopedAddrinfo result = safe_getaddrinfo(hostname, nullptr, &hints);
1482 EXPECT_NE(result.get(), nullptr);
1483 EXPECT_EQ(ToString(result), "1.2.3.4");
1484 });
1485
1486 // Wait for t1 to start the step 1.
1487 while (dns1.queries().size() == 0) {
1488 usleep(1000);
1489 }
1490
1491 // Update the resolver with three nameservers. This will increment the revision ID.
1492 parcel.servers = {listen_addr3, listen_addr1, listen_addr2};
1493 ASSERT_TRUE(mDnsClient.SetResolversFromParcel(parcel));
1494
1495 t1.join();
1496 EXPECT_EQ(0U, GetNumQueriesForType(dns3, ns_type::ns_t_aaaa, fqdn_with_search_domain));
1497 EXPECT_EQ(1U, GetNumQueriesForType(dns3, ns_type::ns_t_a, fqdn_with_search_domain));
1498
Mike Yue2162e52020-03-04 18:43:46 +08001499 const std::vector<NameserverStats> expectedCleartextDnsStats = {
1500 NameserverStats(listen_addr1),
1501 NameserverStats(listen_addr2),
1502 NameserverStats(listen_addr3).setSuccesses(1),
1503 };
1504 EXPECT_TRUE(expectStatsFromGetResolverInfo(expectedCleartextDnsStats));
Mike Yu15791832020-02-11 13:38:48 +08001505}
1506
Ken Chenb9fa2062018-11-13 21:51:13 +08001507// Test what happens if the specified TLS server is nonexistent.
1508TEST_F(ResolverTest, GetHostByName_TlsMissing) {
Xiao Ma09b71022018-12-11 17:56:32 +09001509 constexpr char listen_addr[] = "127.0.0.3";
1510 constexpr char host_name[] = "tlsmissing.example.com.";
1511
1512 test::DNSResponder dns;
1513 StartDns(dns, {{host_name, ns_type::ns_t_a, "1.2.3.3"}});
Luke Huangf8215372019-11-22 11:53:41 +08001514 std::vector<std::string> servers = {listen_addr};
Ken Chenb9fa2062018-11-13 21:51:13 +08001515
1516 // There's nothing listening on this address, so validation will either fail or
1517 /// hang. Either way, queries will continue to flow to the DNSResponder.
waynema0e73c2e2019-07-31 15:04:08 +08001518 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams, ""));
Ken Chenb9fa2062018-11-13 21:51:13 +08001519
1520 const hostent* result;
1521
1522 result = gethostbyname("tlsmissing");
1523 ASSERT_FALSE(result == nullptr);
1524 EXPECT_EQ("1.2.3.3", ToString(result));
1525
1526 // Clear TLS bit.
Xiao Ma09b71022018-12-11 17:56:32 +09001527 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +08001528}
1529
1530// Test what happens if the specified TLS server replies with garbage.
1531TEST_F(ResolverTest, GetHostByName_TlsBroken) {
Xiao Ma09b71022018-12-11 17:56:32 +09001532 constexpr char listen_addr[] = "127.0.0.3";
1533 constexpr char host_name1[] = "tlsbroken1.example.com.";
1534 constexpr char host_name2[] = "tlsbroken2.example.com.";
1535 const std::vector<DnsRecord> records = {
1536 {host_name1, ns_type::ns_t_a, "1.2.3.1"},
1537 {host_name2, ns_type::ns_t_a, "1.2.3.2"},
1538 };
1539
1540 test::DNSResponder dns;
1541 StartDns(dns, records);
Luke Huangf8215372019-11-22 11:53:41 +08001542 std::vector<std::string> servers = {listen_addr};
Ken Chenb9fa2062018-11-13 21:51:13 +08001543
1544 // Bind the specified private DNS socket but don't respond to any client sockets yet.
1545 int s = socket(AF_INET, SOCK_STREAM | SOCK_CLOEXEC, IPPROTO_TCP);
1546 ASSERT_TRUE(s >= 0);
1547 struct sockaddr_in tlsServer = {
Luke Huangf8215372019-11-22 11:53:41 +08001548 .sin_family = AF_INET,
1549 .sin_port = htons(853),
Ken Chenb9fa2062018-11-13 21:51:13 +08001550 };
1551 ASSERT_TRUE(inet_pton(AF_INET, listen_addr, &tlsServer.sin_addr));
1552 ASSERT_TRUE(enableSockopt(s, SOL_SOCKET, SO_REUSEPORT).ok());
1553 ASSERT_TRUE(enableSockopt(s, SOL_SOCKET, SO_REUSEADDR).ok());
1554 ASSERT_FALSE(bind(s, reinterpret_cast<struct sockaddr*>(&tlsServer), sizeof(tlsServer)));
1555 ASSERT_FALSE(listen(s, 1));
1556
1557 // Trigger TLS validation.
waynema0e73c2e2019-07-31 15:04:08 +08001558 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams, ""));
Ken Chenb9fa2062018-11-13 21:51:13 +08001559
1560 struct sockaddr_storage cliaddr;
1561 socklen_t sin_size = sizeof(cliaddr);
Luke Huangf8215372019-11-22 11:53:41 +08001562 int new_fd = accept4(s, reinterpret_cast<struct sockaddr*>(&cliaddr), &sin_size, SOCK_CLOEXEC);
Ken Chenb9fa2062018-11-13 21:51:13 +08001563 ASSERT_TRUE(new_fd > 0);
1564
1565 // We've received the new file descriptor but not written to it or closed, so the
1566 // validation is still pending. Queries should still flow correctly because the
1567 // server is not used until validation succeeds.
1568 const hostent* result;
1569 result = gethostbyname("tlsbroken1");
1570 ASSERT_FALSE(result == nullptr);
1571 EXPECT_EQ("1.2.3.1", ToString(result));
1572
1573 // Now we cause the validation to fail.
1574 std::string garbage = "definitely not a valid TLS ServerHello";
1575 write(new_fd, garbage.data(), garbage.size());
1576 close(new_fd);
1577
1578 // Validation failure shouldn't interfere with lookups, because lookups won't be sent
1579 // to the TLS server unless validation succeeds.
1580 result = gethostbyname("tlsbroken2");
1581 ASSERT_FALSE(result == nullptr);
1582 EXPECT_EQ("1.2.3.2", ToString(result));
1583
1584 // Clear TLS bit.
Xiao Ma09b71022018-12-11 17:56:32 +09001585 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +08001586 close(s);
1587}
1588
1589TEST_F(ResolverTest, GetHostByName_Tls) {
Xiao Ma09b71022018-12-11 17:56:32 +09001590 constexpr char listen_addr[] = "127.0.0.3";
1591 constexpr char listen_udp[] = "53";
1592 constexpr char listen_tls[] = "853";
1593 constexpr char host_name1[] = "tls1.example.com.";
1594 constexpr char host_name2[] = "tls2.example.com.";
1595 constexpr char host_name3[] = "tls3.example.com.";
1596 const std::vector<DnsRecord> records = {
1597 {host_name1, ns_type::ns_t_a, "1.2.3.1"},
1598 {host_name2, ns_type::ns_t_a, "1.2.3.2"},
1599 {host_name3, ns_type::ns_t_a, "1.2.3.3"},
1600 };
1601
1602 test::DNSResponder dns;
1603 StartDns(dns, records);
Luke Huangf8215372019-11-22 11:53:41 +08001604 std::vector<std::string> servers = {listen_addr};
Ken Chenb9fa2062018-11-13 21:51:13 +08001605
1606 test::DnsTlsFrontend tls(listen_addr, listen_tls, listen_addr, listen_udp);
1607 ASSERT_TRUE(tls.startServer());
waynema0e73c2e2019-07-31 15:04:08 +08001608 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams, ""));
Mike Yu724f77d2019-08-16 11:14:50 +08001609 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
Ken Chenb9fa2062018-11-13 21:51:13 +08001610
Mike Yu724f77d2019-08-16 11:14:50 +08001611 const hostent* result = gethostbyname("tls1");
Ken Chenb9fa2062018-11-13 21:51:13 +08001612 ASSERT_FALSE(result == nullptr);
1613 EXPECT_EQ("1.2.3.1", ToString(result));
1614
1615 // Wait for query to get counted.
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001616 EXPECT_TRUE(tls.waitForQueries(2));
Ken Chenb9fa2062018-11-13 21:51:13 +08001617
1618 // Stop the TLS server. Since we're in opportunistic mode, queries will
1619 // fall back to the locally-assigned (clear text) nameservers.
1620 tls.stopServer();
1621
1622 dns.clearQueries();
1623 result = gethostbyname("tls2");
1624 EXPECT_FALSE(result == nullptr);
1625 EXPECT_EQ("1.2.3.2", ToString(result));
1626 const auto queries = dns.queries();
1627 EXPECT_EQ(1U, queries.size());
waynema29253052019-08-20 11:26:08 +08001628 EXPECT_EQ("tls2.example.com.", queries[0].name);
1629 EXPECT_EQ(ns_t_a, queries[0].type);
Ken Chenb9fa2062018-11-13 21:51:13 +08001630
1631 // Reset the resolvers without enabling TLS. Queries should still be routed
1632 // to the UDP endpoint.
Xiao Ma09b71022018-12-11 17:56:32 +09001633 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +08001634
1635 result = gethostbyname("tls3");
1636 ASSERT_FALSE(result == nullptr);
1637 EXPECT_EQ("1.2.3.3", ToString(result));
Ken Chenb9fa2062018-11-13 21:51:13 +08001638}
1639
Ken Chenb9fa2062018-11-13 21:51:13 +08001640TEST_F(ResolverTest, GetHostByName_TlsFailover) {
Xiao Ma09b71022018-12-11 17:56:32 +09001641 constexpr char listen_addr1[] = "127.0.0.3";
1642 constexpr char listen_addr2[] = "127.0.0.4";
1643 constexpr char listen_udp[] = "53";
1644 constexpr char listen_tls[] = "853";
1645 constexpr char host_name1[] = "tlsfailover1.example.com.";
1646 constexpr char host_name2[] = "tlsfailover2.example.com.";
1647 const std::vector<DnsRecord> records1 = {
1648 {host_name1, ns_type::ns_t_a, "1.2.3.1"},
1649 {host_name2, ns_type::ns_t_a, "1.2.3.2"},
1650 };
1651 const std::vector<DnsRecord> records2 = {
1652 {host_name1, ns_type::ns_t_a, "1.2.3.3"},
1653 {host_name2, ns_type::ns_t_a, "1.2.3.4"},
1654 };
1655
1656 test::DNSResponder dns1(listen_addr1);
1657 test::DNSResponder dns2(listen_addr2);
1658 StartDns(dns1, records1);
1659 StartDns(dns2, records2);
1660
Luke Huangf8215372019-11-22 11:53:41 +08001661 std::vector<std::string> servers = {listen_addr1, listen_addr2};
Ken Chenb9fa2062018-11-13 21:51:13 +08001662
1663 test::DnsTlsFrontend tls1(listen_addr1, listen_tls, listen_addr1, listen_udp);
1664 test::DnsTlsFrontend tls2(listen_addr2, listen_tls, listen_addr2, listen_udp);
1665 ASSERT_TRUE(tls1.startServer());
1666 ASSERT_TRUE(tls2.startServer());
waynema0e73c2e2019-07-31 15:04:08 +08001667 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams,
1668 kDefaultPrivateDnsHostName));
Mike Yu724f77d2019-08-16 11:14:50 +08001669 EXPECT_TRUE(WaitForPrivateDnsValidation(tls1.listen_address(), true));
1670 EXPECT_TRUE(WaitForPrivateDnsValidation(tls2.listen_address(), true));
Ken Chenb9fa2062018-11-13 21:51:13 +08001671
Mike Yu724f77d2019-08-16 11:14:50 +08001672 const hostent* result = gethostbyname("tlsfailover1");
Ken Chenb9fa2062018-11-13 21:51:13 +08001673 ASSERT_FALSE(result == nullptr);
1674 EXPECT_EQ("1.2.3.1", ToString(result));
1675
1676 // Wait for query to get counted.
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001677 EXPECT_TRUE(tls1.waitForQueries(2));
Ken Chenb9fa2062018-11-13 21:51:13 +08001678 // No new queries should have reached tls2.
1679 EXPECT_EQ(1, tls2.queries());
1680
1681 // Stop tls1. Subsequent queries should attempt to reach tls1, fail, and retry to tls2.
1682 tls1.stopServer();
1683
1684 result = gethostbyname("tlsfailover2");
1685 EXPECT_EQ("1.2.3.4", ToString(result));
1686
1687 // Wait for query to get counted.
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001688 EXPECT_TRUE(tls2.waitForQueries(2));
Ken Chenb9fa2062018-11-13 21:51:13 +08001689
1690 // No additional queries should have reached the insecure servers.
1691 EXPECT_EQ(2U, dns1.queries().size());
1692 EXPECT_EQ(2U, dns2.queries().size());
1693
1694 // Clear TLS bit.
Xiao Ma09b71022018-12-11 17:56:32 +09001695 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Ken Chenb9fa2062018-11-13 21:51:13 +08001696}
1697
1698TEST_F(ResolverTest, GetHostByName_BadTlsName) {
Xiao Ma09b71022018-12-11 17:56:32 +09001699 constexpr char listen_addr[] = "127.0.0.3";
1700 constexpr char listen_udp[] = "53";
1701 constexpr char listen_tls[] = "853";
1702 constexpr char host_name[] = "badtlsname.example.com.";
1703
1704 test::DNSResponder dns;
1705 StartDns(dns, {{host_name, ns_type::ns_t_a, "1.2.3.1"}});
Luke Huangf8215372019-11-22 11:53:41 +08001706 std::vector<std::string> servers = {listen_addr};
Ken Chenb9fa2062018-11-13 21:51:13 +08001707
1708 test::DnsTlsFrontend tls(listen_addr, listen_tls, listen_addr, listen_udp);
1709 ASSERT_TRUE(tls.startServer());
Xiao Ma09b71022018-12-11 17:56:32 +09001710 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams,
waynema0e73c2e2019-07-31 15:04:08 +08001711 kDefaultIncorrectPrivateDnsHostName));
Ken Chenb9fa2062018-11-13 21:51:13 +08001712
waynema0e73c2e2019-07-31 15:04:08 +08001713 // The TLS handshake would fail because the name of TLS server doesn't
1714 // match with TLS server's certificate.
Mike Yu724f77d2019-08-16 11:14:50 +08001715 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), false));
Ken Chenb9fa2062018-11-13 21:51:13 +08001716
1717 // The query should fail hard, because a name was specified.
1718 EXPECT_EQ(nullptr, gethostbyname("badtlsname"));
1719
1720 // Clear TLS bit.
Xiao Ma09b71022018-12-11 17:56:32 +09001721 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +08001722}
1723
1724TEST_F(ResolverTest, GetAddrInfo_Tls) {
Xiao Ma09b71022018-12-11 17:56:32 +09001725 constexpr char listen_addr[] = "127.0.0.3";
1726 constexpr char listen_udp[] = "53";
1727 constexpr char listen_tls[] = "853";
1728 constexpr char host_name[] = "addrinfotls.example.com.";
1729 const std::vector<DnsRecord> records = {
1730 {host_name, ns_type::ns_t_a, "1.2.3.4"},
1731 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
1732 };
1733
1734 test::DNSResponder dns;
1735 StartDns(dns, records);
Luke Huangf8215372019-11-22 11:53:41 +08001736 std::vector<std::string> servers = {listen_addr};
Ken Chenb9fa2062018-11-13 21:51:13 +08001737
1738 test::DnsTlsFrontend tls(listen_addr, listen_tls, listen_addr, listen_udp);
1739 ASSERT_TRUE(tls.startServer());
waynema0e73c2e2019-07-31 15:04:08 +08001740 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams,
1741 kDefaultPrivateDnsHostName));
Mike Yu724f77d2019-08-16 11:14:50 +08001742 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
Ken Chenb9fa2062018-11-13 21:51:13 +08001743
1744 dns.clearQueries();
1745 ScopedAddrinfo result = safe_getaddrinfo("addrinfotls", nullptr, nullptr);
1746 EXPECT_TRUE(result != nullptr);
1747 size_t found = GetNumQueries(dns, host_name);
1748 EXPECT_LE(1U, found);
1749 // Could be A or AAAA
1750 std::string result_str = ToString(result);
1751 EXPECT_TRUE(result_str == "1.2.3.4" || result_str == "::1.2.3.4")
Luke Huangf8215372019-11-22 11:53:41 +08001752 << ", result_str='" << result_str << "'";
Ken Chenb9fa2062018-11-13 21:51:13 +08001753 // Wait for both A and AAAA queries to get counted.
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001754 EXPECT_TRUE(tls.waitForQueries(3));
Ken Chenb9fa2062018-11-13 21:51:13 +08001755
1756 // Clear TLS bit.
Xiao Ma09b71022018-12-11 17:56:32 +09001757 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
Ken Chenb9fa2062018-11-13 21:51:13 +08001758}
1759
1760TEST_F(ResolverTest, TlsBypass) {
1761 const char OFF[] = "off";
1762 const char OPPORTUNISTIC[] = "opportunistic";
1763 const char STRICT[] = "strict";
1764
1765 const char GETHOSTBYNAME[] = "gethostbyname";
1766 const char GETADDRINFO[] = "getaddrinfo";
1767 const char GETADDRINFOFORNET[] = "getaddrinfofornet";
1768
1769 const unsigned BYPASS_NETID = NETID_USE_LOCAL_NAMESERVERS | TEST_NETID;
1770
Ken Chenb9fa2062018-11-13 21:51:13 +08001771 const char ADDR4[] = "192.0.2.1";
1772 const char ADDR6[] = "2001:db8::1";
1773
1774 const char cleartext_addr[] = "127.0.0.53";
1775 const char cleartext_port[] = "53";
1776 const char tls_port[] = "853";
Luke Huangf8215372019-11-22 11:53:41 +08001777 const std::vector<std::string> servers = {cleartext_addr};
Ken Chenb9fa2062018-11-13 21:51:13 +08001778
Xiao Ma09b71022018-12-11 17:56:32 +09001779 test::DNSResponder dns(cleartext_addr);
Ken Chenb9fa2062018-11-13 21:51:13 +08001780 ASSERT_TRUE(dns.startServer());
1781
1782 test::DnsTlsFrontend tls(cleartext_addr, tls_port, cleartext_addr, cleartext_port);
Mike Yudd4ac2d2019-05-31 16:52:11 +08001783 ASSERT_TRUE(tls.startServer());
Ken Chenb9fa2062018-11-13 21:51:13 +08001784
Luke Huangf8215372019-11-22 11:53:41 +08001785 // clang-format off
Ken Chenb9fa2062018-11-13 21:51:13 +08001786 struct TestConfig {
1787 const std::string mode;
1788 const bool withWorkingTLS;
1789 const std::string method;
1790
1791 std::string asHostName() const {
Luke Huangf8215372019-11-22 11:53:41 +08001792 return StringPrintf("%s.%s.%s.", mode.c_str(), withWorkingTLS ? "tlsOn" : "tlsOff",
Ken Chenb9fa2062018-11-13 21:51:13 +08001793 method.c_str());
1794 }
1795 } testConfigs[]{
Ken Chenb9fa2062018-11-13 21:51:13 +08001796 {OFF, true, GETHOSTBYNAME},
1797 {OPPORTUNISTIC, true, GETHOSTBYNAME},
1798 {STRICT, true, GETHOSTBYNAME},
Ken Chenb9fa2062018-11-13 21:51:13 +08001799 {OFF, true, GETADDRINFO},
1800 {OPPORTUNISTIC, true, GETADDRINFO},
1801 {STRICT, true, GETADDRINFO},
Ken Chenb9fa2062018-11-13 21:51:13 +08001802 {OFF, true, GETADDRINFOFORNET},
1803 {OPPORTUNISTIC, true, GETADDRINFOFORNET},
1804 {STRICT, true, GETADDRINFOFORNET},
Mike Yudd4ac2d2019-05-31 16:52:11 +08001805 {OFF, false, GETHOSTBYNAME},
1806 {OPPORTUNISTIC, false, GETHOSTBYNAME},
1807 {STRICT, false, GETHOSTBYNAME},
1808 {OFF, false, GETADDRINFO},
1809 {OPPORTUNISTIC, false, GETADDRINFO},
1810 {STRICT, false, GETADDRINFO},
1811 {OFF, false, GETADDRINFOFORNET},
1812 {OPPORTUNISTIC, false, GETADDRINFOFORNET},
1813 {STRICT, false, GETADDRINFOFORNET},
Ken Chenb9fa2062018-11-13 21:51:13 +08001814 };
Luke Huangf8215372019-11-22 11:53:41 +08001815 // clang-format on
Ken Chenb9fa2062018-11-13 21:51:13 +08001816
1817 for (const auto& config : testConfigs) {
1818 const std::string testHostName = config.asHostName();
1819 SCOPED_TRACE(testHostName);
1820
1821 // Don't tempt test bugs due to caching.
1822 const char* host_name = testHostName.c_str();
1823 dns.addMapping(host_name, ns_type::ns_t_a, ADDR4);
1824 dns.addMapping(host_name, ns_type::ns_t_aaaa, ADDR6);
1825
Mike Yudd4ac2d2019-05-31 16:52:11 +08001826 if (config.withWorkingTLS) {
1827 if (!tls.running()) {
1828 ASSERT_TRUE(tls.startServer());
1829 }
1830 } else {
1831 if (tls.running()) {
1832 ASSERT_TRUE(tls.stopServer());
1833 }
1834 }
Ken Chenb9fa2062018-11-13 21:51:13 +08001835
1836 if (config.mode == OFF) {
Xiao Ma09b71022018-12-11 17:56:32 +09001837 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers, kDefaultSearchDomains,
1838 kDefaultParams));
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001839 } else /* OPPORTUNISTIC or STRICT */ {
1840 const char* tls_hostname = (config.mode == STRICT) ? kDefaultPrivateDnsHostName : "";
Xiao Ma09b71022018-12-11 17:56:32 +09001841 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains,
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001842 kDefaultParams, tls_hostname));
Mike Yu724f77d2019-08-16 11:14:50 +08001843
1844 // Wait for the validation event. If the server is running, the validation should
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001845 // succeed; otherwise, the validation should fail.
Mike Yu724f77d2019-08-16 11:14:50 +08001846 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), config.withWorkingTLS));
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09001847 if (config.withWorkingTLS) {
1848 EXPECT_TRUE(tls.waitForQueries(1));
1849 tls.clearQueries();
1850 }
Ken Chenb9fa2062018-11-13 21:51:13 +08001851 }
Ken Chenb9fa2062018-11-13 21:51:13 +08001852
1853 const hostent* h_result = nullptr;
1854 ScopedAddrinfo ai_result;
1855
1856 if (config.method == GETHOSTBYNAME) {
1857 ASSERT_EQ(0, setNetworkForResolv(BYPASS_NETID));
1858 h_result = gethostbyname(host_name);
1859
1860 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, host_name));
1861 ASSERT_FALSE(h_result == nullptr);
1862 ASSERT_EQ(4, h_result->h_length);
1863 ASSERT_FALSE(h_result->h_addr_list[0] == nullptr);
1864 EXPECT_EQ(ADDR4, ToString(h_result));
1865 EXPECT_TRUE(h_result->h_addr_list[1] == nullptr);
1866 } else if (config.method == GETADDRINFO) {
1867 ASSERT_EQ(0, setNetworkForResolv(BYPASS_NETID));
1868 ai_result = safe_getaddrinfo(host_name, nullptr, nullptr);
1869 EXPECT_TRUE(ai_result != nullptr);
1870
1871 EXPECT_LE(1U, GetNumQueries(dns, host_name));
1872 // Could be A or AAAA
1873 const std::string result_str = ToString(ai_result);
1874 EXPECT_TRUE(result_str == ADDR4 || result_str == ADDR6)
Luke Huangf8215372019-11-22 11:53:41 +08001875 << ", result_str='" << result_str << "'";
Ken Chenb9fa2062018-11-13 21:51:13 +08001876 } else if (config.method == GETADDRINFOFORNET) {
1877 addrinfo* raw_ai_result = nullptr;
1878 EXPECT_EQ(0, android_getaddrinfofornet(host_name, /*servname=*/nullptr,
1879 /*hints=*/nullptr, BYPASS_NETID, MARK_UNSET,
1880 &raw_ai_result));
1881 ai_result.reset(raw_ai_result);
1882
1883 EXPECT_LE(1U, GetNumQueries(dns, host_name));
1884 // Could be A or AAAA
1885 const std::string result_str = ToString(ai_result);
1886 EXPECT_TRUE(result_str == ADDR4 || result_str == ADDR6)
Luke Huangf8215372019-11-22 11:53:41 +08001887 << ", result_str='" << result_str << "'";
Ken Chenb9fa2062018-11-13 21:51:13 +08001888 }
1889
Mike Yudd4ac2d2019-05-31 16:52:11 +08001890 EXPECT_EQ(0, tls.queries());
Ken Chenb9fa2062018-11-13 21:51:13 +08001891
1892 // Clear per-process resolv netid.
1893 ASSERT_EQ(0, setNetworkForResolv(NETID_UNSET));
Ken Chenb9fa2062018-11-13 21:51:13 +08001894 dns.clearQueries();
1895 }
Ken Chenb9fa2062018-11-13 21:51:13 +08001896}
1897
1898TEST_F(ResolverTest, StrictMode_NoTlsServers) {
Xiao Ma09b71022018-12-11 17:56:32 +09001899 constexpr char cleartext_addr[] = "127.0.0.53";
Luke Huangf8215372019-11-22 11:53:41 +08001900 const std::vector<std::string> servers = {cleartext_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09001901 constexpr char host_name[] = "strictmode.notlsips.example.com.";
1902 const std::vector<DnsRecord> records = {
1903 {host_name, ns_type::ns_t_a, "1.2.3.4"},
1904 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
1905 };
Ken Chenb9fa2062018-11-13 21:51:13 +08001906
Xiao Ma09b71022018-12-11 17:56:32 +09001907 test::DNSResponder dns(cleartext_addr);
1908 StartDns(dns, records);
Ken Chenb9fa2062018-11-13 21:51:13 +08001909
waynema0e73c2e2019-07-31 15:04:08 +08001910 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams,
1911 kDefaultIncorrectPrivateDnsHostName));
Ken Chenb9fa2062018-11-13 21:51:13 +08001912
1913 addrinfo* ai_result = nullptr;
1914 EXPECT_NE(0, getaddrinfo(host_name, nullptr, nullptr, &ai_result));
1915 EXPECT_EQ(0U, GetNumQueries(dns, host_name));
1916}
Luke Huang94b10b92018-11-21 20:13:38 +08001917
1918namespace {
1919
Luke Huang70931aa2019-01-31 11:57:41 +08001920int getAsyncResponse(int fd, int* rcode, uint8_t* buf, int bufLen) {
Luke Huang94b10b92018-11-21 20:13:38 +08001921 struct pollfd wait_fd[1];
1922 wait_fd[0].fd = fd;
1923 wait_fd[0].events = POLLIN;
1924 short revents;
1925 int ret;
1926
1927 ret = poll(wait_fd, 1, -1);
1928 revents = wait_fd[0].revents;
1929 if (revents & POLLIN) {
1930 int n = resNetworkResult(fd, rcode, buf, bufLen);
Luke Huangba7bef92018-12-26 16:53:03 +08001931 // Verify that resNetworkResult() closed the fd
1932 char dummy;
1933 EXPECT_EQ(-1, read(fd, &dummy, sizeof dummy));
1934 EXPECT_EQ(EBADF, errno);
Luke Huang94b10b92018-11-21 20:13:38 +08001935 return n;
1936 }
1937 return -1;
1938}
1939
Luke Huang70931aa2019-01-31 11:57:41 +08001940std::string toString(uint8_t* buf, int bufLen, int ipType) {
Luke Huang94b10b92018-11-21 20:13:38 +08001941 ns_msg handle;
1942 int ancount, n = 0;
1943 ns_rr rr;
1944
Luke Huangf8215372019-11-22 11:53:41 +08001945 if (ns_initparse((const uint8_t*)buf, bufLen, &handle) >= 0) {
Luke Huang94b10b92018-11-21 20:13:38 +08001946 ancount = ns_msg_count(handle, ns_s_an);
1947 if (ns_parserr(&handle, ns_s_an, n, &rr) == 0) {
Luke Huang70931aa2019-01-31 11:57:41 +08001948 const uint8_t* rdata = ns_rr_rdata(rr);
Luke Huang94b10b92018-11-21 20:13:38 +08001949 char buffer[INET6_ADDRSTRLEN];
Luke Huangf8215372019-11-22 11:53:41 +08001950 if (inet_ntop(ipType, (const char*)rdata, buffer, sizeof(buffer))) {
Luke Huang94b10b92018-11-21 20:13:38 +08001951 return buffer;
1952 }
1953 }
1954 }
1955 return "";
1956}
1957
1958int dns_open_proxy() {
1959 int s = socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0);
1960 if (s == -1) {
1961 return -1;
1962 }
1963 const int one = 1;
1964 setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &one, sizeof(one));
1965
1966 static const struct sockaddr_un proxy_addr = {
1967 .sun_family = AF_UNIX,
1968 .sun_path = "/dev/socket/dnsproxyd",
1969 };
1970
Luke Huangf8215372019-11-22 11:53:41 +08001971 if (TEMP_FAILURE_RETRY(connect(s, (const struct sockaddr*)&proxy_addr, sizeof(proxy_addr))) !=
Luke Huang94b10b92018-11-21 20:13:38 +08001972 0) {
1973 close(s);
1974 return -1;
1975 }
1976
1977 return s;
1978}
1979
Luke Huangba7bef92018-12-26 16:53:03 +08001980void expectAnswersValid(int fd, int ipType, const std::string& expectedAnswer) {
1981 int rcode = -1;
1982 uint8_t buf[MAXPACKET] = {};
1983
1984 int res = getAsyncResponse(fd, &rcode, buf, MAXPACKET);
1985 EXPECT_GT(res, 0);
1986 EXPECT_EQ(expectedAnswer, toString(buf, res, ipType));
1987}
1988
1989void expectAnswersNotValid(int fd, int expectedErrno) {
1990 int rcode = -1;
1991 uint8_t buf[MAXPACKET] = {};
1992
1993 int res = getAsyncResponse(fd, &rcode, buf, MAXPACKET);
1994 EXPECT_EQ(expectedErrno, res);
1995}
1996
Luke Huang94b10b92018-11-21 20:13:38 +08001997} // namespace
1998
1999TEST_F(ResolverTest, Async_NormalQueryV4V6) {
Xiao Ma09b71022018-12-11 17:56:32 +09002000 constexpr char listen_addr[] = "127.0.0.4";
2001 constexpr char host_name[] = "howdy.example.com.";
2002 const std::vector<DnsRecord> records = {
2003 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2004 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
2005 };
2006
2007 test::DNSResponder dns(listen_addr);
2008 StartDns(dns, records);
Luke Huang94b10b92018-11-21 20:13:38 +08002009 std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002010 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Luke Huang94b10b92018-11-21 20:13:38 +08002011
Luke Huangba7bef92018-12-26 16:53:03 +08002012 int fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
2013 int fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa, 0);
Luke Huang94b10b92018-11-21 20:13:38 +08002014 EXPECT_TRUE(fd1 != -1);
2015 EXPECT_TRUE(fd2 != -1);
2016
Luke Huang70931aa2019-01-31 11:57:41 +08002017 uint8_t buf[MAXPACKET] = {};
Luke Huang94b10b92018-11-21 20:13:38 +08002018 int rcode;
2019 int res = getAsyncResponse(fd2, &rcode, buf, MAXPACKET);
2020 EXPECT_GT(res, 0);
2021 EXPECT_EQ("::1.2.3.4", toString(buf, res, AF_INET6));
2022
2023 res = getAsyncResponse(fd1, &rcode, buf, MAXPACKET);
2024 EXPECT_GT(res, 0);
2025 EXPECT_EQ("1.2.3.4", toString(buf, res, AF_INET));
2026
2027 EXPECT_EQ(2U, GetNumQueries(dns, host_name));
2028
2029 // Re-query verify cache works
Luke Huangba7bef92018-12-26 16:53:03 +08002030 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
2031 fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa, 0);
Luke Huang94b10b92018-11-21 20:13:38 +08002032
2033 EXPECT_TRUE(fd1 != -1);
2034 EXPECT_TRUE(fd2 != -1);
2035
2036 res = getAsyncResponse(fd2, &rcode, buf, MAXPACKET);
2037 EXPECT_GT(res, 0);
2038 EXPECT_EQ("::1.2.3.4", toString(buf, res, AF_INET6));
2039
2040 res = getAsyncResponse(fd1, &rcode, buf, MAXPACKET);
2041 EXPECT_GT(res, 0);
2042 EXPECT_EQ("1.2.3.4", toString(buf, res, AF_INET));
2043
2044 EXPECT_EQ(2U, GetNumQueries(dns, host_name));
2045}
2046
2047TEST_F(ResolverTest, Async_BadQuery) {
Xiao Ma09b71022018-12-11 17:56:32 +09002048 constexpr char listen_addr[] = "127.0.0.4";
2049 constexpr char host_name[] = "howdy.example.com.";
2050 const std::vector<DnsRecord> records = {
2051 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2052 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
2053 };
2054
2055 test::DNSResponder dns(listen_addr);
2056 StartDns(dns, records);
Luke Huang94b10b92018-11-21 20:13:38 +08002057 std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002058 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Luke Huang94b10b92018-11-21 20:13:38 +08002059
2060 static struct {
2061 int fd;
2062 const char* dname;
2063 const int queryType;
2064 const int expectRcode;
2065 } kTestData[] = {
Luke Huangba7bef92018-12-26 16:53:03 +08002066 {-1, "", ns_t_aaaa, 0},
2067 {-1, "as65ass46", ns_t_aaaa, 0},
2068 {-1, "454564564564", ns_t_aaaa, 0},
2069 {-1, "h645235", ns_t_a, 0},
2070 {-1, "www.google.com", ns_t_a, 0},
Luke Huang94b10b92018-11-21 20:13:38 +08002071 };
2072
2073 for (auto& td : kTestData) {
2074 SCOPED_TRACE(td.dname);
Luke Huangba7bef92018-12-26 16:53:03 +08002075 td.fd = resNetworkQuery(TEST_NETID, td.dname, ns_c_in, td.queryType, 0);
Luke Huang94b10b92018-11-21 20:13:38 +08002076 EXPECT_TRUE(td.fd != -1);
2077 }
2078
2079 // dns_responder return empty resp(packet only contains query part) with no error currently
2080 for (const auto& td : kTestData) {
Luke Huang70931aa2019-01-31 11:57:41 +08002081 uint8_t buf[MAXPACKET] = {};
Luke Huang94b10b92018-11-21 20:13:38 +08002082 int rcode;
2083 SCOPED_TRACE(td.dname);
2084 int res = getAsyncResponse(td.fd, &rcode, buf, MAXPACKET);
2085 EXPECT_GT(res, 0);
2086 EXPECT_EQ(rcode, td.expectRcode);
2087 }
2088}
2089
2090TEST_F(ResolverTest, Async_EmptyAnswer) {
Xiao Ma09b71022018-12-11 17:56:32 +09002091 constexpr char listen_addr[] = "127.0.0.4";
2092 constexpr char host_name[] = "howdy.example.com.";
2093 const std::vector<DnsRecord> records = {
2094 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2095 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
2096 };
2097
2098 test::DNSResponder dns(listen_addr);
2099 StartDns(dns, records);
Luke Huang94b10b92018-11-21 20:13:38 +08002100 std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002101 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Luke Huang94b10b92018-11-21 20:13:38 +08002102
Luke Huang9c264bb2018-12-18 16:44:41 +08002103 // TODO: Disable retry to make this test explicit.
2104 auto& cv = dns.getCv();
2105 auto& cvMutex = dns.getCvMutex();
2106 int fd1;
2107 // Wait on the condition variable to ensure that the DNS server has handled our first query.
2108 {
2109 std::unique_lock lk(cvMutex);
Luke Huangba7bef92018-12-26 16:53:03 +08002110 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa, 0);
Luke Huang9c264bb2018-12-18 16:44:41 +08002111 EXPECT_TRUE(fd1 != -1);
2112 EXPECT_EQ(std::cv_status::no_timeout, cv.wait_for(lk, std::chrono::seconds(1)));
2113 }
Luke Huang94b10b92018-11-21 20:13:38 +08002114
Luke Huang94b10b92018-11-21 20:13:38 +08002115 dns.setResponseProbability(0.0);
Luke Huang94b10b92018-11-21 20:13:38 +08002116
Luke Huangba7bef92018-12-26 16:53:03 +08002117 int fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
Luke Huang94b10b92018-11-21 20:13:38 +08002118 EXPECT_TRUE(fd2 != -1);
2119
Luke Huangba7bef92018-12-26 16:53:03 +08002120 int fd3 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
Luke Huang94b10b92018-11-21 20:13:38 +08002121 EXPECT_TRUE(fd3 != -1);
2122
Luke Huang9c264bb2018-12-18 16:44:41 +08002123 uint8_t buf[MAXPACKET] = {};
Luke Huang94b10b92018-11-21 20:13:38 +08002124 int rcode;
2125
Luke Huang9c264bb2018-12-18 16:44:41 +08002126 // expect no response
2127 int res = getAsyncResponse(fd3, &rcode, buf, MAXPACKET);
2128 EXPECT_EQ(-ETIMEDOUT, res);
Luke Huang94b10b92018-11-21 20:13:38 +08002129
Luke Huang9c264bb2018-12-18 16:44:41 +08002130 // expect no response
Luke Huang94b10b92018-11-21 20:13:38 +08002131 memset(buf, 0, MAXPACKET);
Luke Huang9c264bb2018-12-18 16:44:41 +08002132 res = getAsyncResponse(fd2, &rcode, buf, MAXPACKET);
2133 EXPECT_EQ(-ETIMEDOUT, res);
Luke Huang94b10b92018-11-21 20:13:38 +08002134
Luke Huang94b10b92018-11-21 20:13:38 +08002135 dns.setResponseProbability(1.0);
Luke Huang94b10b92018-11-21 20:13:38 +08002136
Luke Huangba7bef92018-12-26 16:53:03 +08002137 int fd4 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
Luke Huang94b10b92018-11-21 20:13:38 +08002138 EXPECT_TRUE(fd4 != -1);
2139
2140 memset(buf, 0, MAXPACKET);
2141 res = getAsyncResponse(fd4, &rcode, buf, MAXPACKET);
2142 EXPECT_GT(res, 0);
2143 EXPECT_EQ("1.2.3.4", toString(buf, res, AF_INET));
2144
2145 memset(buf, 0, MAXPACKET);
2146 res = getAsyncResponse(fd1, &rcode, buf, MAXPACKET);
2147 EXPECT_GT(res, 0);
2148 EXPECT_EQ("::1.2.3.4", toString(buf, res, AF_INET6));
2149}
2150
2151TEST_F(ResolverTest, Async_MalformedQuery) {
Xiao Ma09b71022018-12-11 17:56:32 +09002152 constexpr char listen_addr[] = "127.0.0.4";
2153 constexpr char host_name[] = "howdy.example.com.";
2154 const std::vector<DnsRecord> records = {
2155 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2156 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
2157 };
2158
2159 test::DNSResponder dns(listen_addr);
2160 StartDns(dns, records);
Luke Huang94b10b92018-11-21 20:13:38 +08002161 std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002162 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Luke Huang94b10b92018-11-21 20:13:38 +08002163
2164 int fd = dns_open_proxy();
2165 EXPECT_TRUE(fd > 0);
2166
2167 const std::string badMsg = "16-52512#";
Xiao Ma09b71022018-12-11 17:56:32 +09002168 static const struct {
Luke Huang94b10b92018-11-21 20:13:38 +08002169 const std::string cmd;
2170 const int expectErr;
2171 } kTestData[] = {
Luke Huangba7bef92018-12-26 16:53:03 +08002172 // Too few arguments
Luke Huang94b10b92018-11-21 20:13:38 +08002173 {"resnsend " + badMsg + '\0', -EINVAL},
2174 // Bad netId
Luke Huangba7bef92018-12-26 16:53:03 +08002175 {"resnsend badnetId 0 " + badMsg + '\0', -EINVAL},
Luke Huang94b10b92018-11-21 20:13:38 +08002176 // Bad raw data
Luke Huangba7bef92018-12-26 16:53:03 +08002177 {"resnsend " + std::to_string(TEST_NETID) + " 0 " + badMsg + '\0', -EILSEQ},
Luke Huang94b10b92018-11-21 20:13:38 +08002178 };
2179
2180 for (unsigned int i = 0; i < std::size(kTestData); i++) {
2181 auto& td = kTestData[i];
2182 SCOPED_TRACE(td.cmd);
2183 ssize_t rc = TEMP_FAILURE_RETRY(write(fd, td.cmd.c_str(), td.cmd.size()));
2184 EXPECT_EQ(rc, static_cast<ssize_t>(td.cmd.size()));
2185
2186 int32_t tmp;
2187 rc = TEMP_FAILURE_RETRY(read(fd, &tmp, sizeof(tmp)));
2188 EXPECT_TRUE(rc > 0);
2189 EXPECT_EQ(static_cast<int>(ntohl(tmp)), td.expectErr);
2190 }
2191 // Normal query with answer buffer
2192 // This is raw data of query "howdy.example.com" type 1 class 1
2193 std::string query = "81sBAAABAAAAAAAABWhvd2R5B2V4YW1wbGUDY29tAAABAAE=";
Luke Huangba7bef92018-12-26 16:53:03 +08002194 std::string cmd = "resnsend " + std::to_string(TEST_NETID) + " 0 " + query + '\0';
Luke Huang94b10b92018-11-21 20:13:38 +08002195 ssize_t rc = TEMP_FAILURE_RETRY(write(fd, cmd.c_str(), cmd.size()));
2196 EXPECT_EQ(rc, static_cast<ssize_t>(cmd.size()));
2197
Luke Huang70931aa2019-01-31 11:57:41 +08002198 uint8_t smallBuf[1] = {};
Luke Huang94b10b92018-11-21 20:13:38 +08002199 int rcode;
2200 rc = getAsyncResponse(fd, &rcode, smallBuf, 1);
Luke Huangba7bef92018-12-26 16:53:03 +08002201 EXPECT_EQ(-EMSGSIZE, rc);
Luke Huang94b10b92018-11-21 20:13:38 +08002202
2203 // Do the normal test with large buffer again
2204 fd = dns_open_proxy();
2205 EXPECT_TRUE(fd > 0);
2206 rc = TEMP_FAILURE_RETRY(write(fd, cmd.c_str(), cmd.size()));
2207 EXPECT_EQ(rc, static_cast<ssize_t>(cmd.size()));
Luke Huang70931aa2019-01-31 11:57:41 +08002208 uint8_t buf[MAXPACKET] = {};
Luke Huang94b10b92018-11-21 20:13:38 +08002209 rc = getAsyncResponse(fd, &rcode, buf, MAXPACKET);
2210 EXPECT_EQ("1.2.3.4", toString(buf, rc, AF_INET));
Mike Yu4f3747b2018-12-02 17:54:29 +09002211}
2212
Luke Huangba7bef92018-12-26 16:53:03 +08002213TEST_F(ResolverTest, Async_CacheFlags) {
Xiao Ma09b71022018-12-11 17:56:32 +09002214 constexpr char listen_addr[] = "127.0.0.4";
2215 constexpr char host_name[] = "howdy.example.com.";
Luke Huang40f5f492019-05-09 19:37:35 +08002216 constexpr char another_host_name[] = "howdy.example2.com.";
Xiao Ma09b71022018-12-11 17:56:32 +09002217 const std::vector<DnsRecord> records = {
2218 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2219 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
Luke Huang40f5f492019-05-09 19:37:35 +08002220 {another_host_name, ns_type::ns_t_a, "1.2.3.5"},
2221 {another_host_name, ns_type::ns_t_aaaa, "::1.2.3.5"},
Xiao Ma09b71022018-12-11 17:56:32 +09002222 };
2223
2224 test::DNSResponder dns(listen_addr);
2225 StartDns(dns, records);
Luke Huangba7bef92018-12-26 16:53:03 +08002226 std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002227 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Luke Huangba7bef92018-12-26 16:53:03 +08002228
2229 // ANDROID_RESOLV_NO_CACHE_STORE
2230 int fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2231 ANDROID_RESOLV_NO_CACHE_STORE);
2232 EXPECT_TRUE(fd1 != -1);
2233 int fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2234 ANDROID_RESOLV_NO_CACHE_STORE);
2235 EXPECT_TRUE(fd2 != -1);
2236 int fd3 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2237 ANDROID_RESOLV_NO_CACHE_STORE);
2238 EXPECT_TRUE(fd3 != -1);
2239
2240 expectAnswersValid(fd3, AF_INET, "1.2.3.4");
2241 expectAnswersValid(fd2, AF_INET, "1.2.3.4");
2242 expectAnswersValid(fd1, AF_INET, "1.2.3.4");
2243
2244 // No cache exists, expect 3 queries
2245 EXPECT_EQ(3U, GetNumQueries(dns, host_name));
2246
2247 // Re-query and cache
2248 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
2249
2250 EXPECT_TRUE(fd1 != -1);
2251
2252 expectAnswersValid(fd1, AF_INET, "1.2.3.4");
2253
2254 // Now we have cache, expect 4 queries
2255 EXPECT_EQ(4U, GetNumQueries(dns, host_name));
2256
2257 // ANDROID_RESOLV_NO_CACHE_LOOKUP
2258 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2259 ANDROID_RESOLV_NO_CACHE_LOOKUP);
2260 fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2261 ANDROID_RESOLV_NO_CACHE_LOOKUP);
2262
2263 EXPECT_TRUE(fd1 != -1);
2264 EXPECT_TRUE(fd2 != -1);
2265
2266 expectAnswersValid(fd2, AF_INET, "1.2.3.4");
2267 expectAnswersValid(fd1, AF_INET, "1.2.3.4");
2268
2269 // Skip cache, expect 6 queries
2270 EXPECT_EQ(6U, GetNumQueries(dns, host_name));
2271
2272 // Re-query verify cache works
2273 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2274 ANDROID_RESOLV_NO_CACHE_STORE);
2275 EXPECT_TRUE(fd1 != -1);
2276 expectAnswersValid(fd1, AF_INET, "1.2.3.4");
2277
2278 // Cache hits, expect still 6 queries
2279 EXPECT_EQ(6U, GetNumQueries(dns, host_name));
Luke Huanga1d74182019-03-19 17:30:36 +08002280
2281 // Start to verify if ANDROID_RESOLV_NO_CACHE_LOOKUP does write response into cache
2282 dns.clearQueries();
2283
2284 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa,
2285 ANDROID_RESOLV_NO_CACHE_LOOKUP);
2286 fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa,
2287 ANDROID_RESOLV_NO_CACHE_LOOKUP);
2288
2289 EXPECT_TRUE(fd1 != -1);
2290 EXPECT_TRUE(fd2 != -1);
2291
2292 expectAnswersValid(fd2, AF_INET6, "::1.2.3.4");
2293 expectAnswersValid(fd1, AF_INET6, "::1.2.3.4");
2294
2295 // Skip cache, expect 2 queries
2296 EXPECT_EQ(2U, GetNumQueries(dns, host_name));
2297
2298 // Re-query without flags
2299 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa, 0);
2300 fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa, 0);
2301
2302 EXPECT_TRUE(fd1 != -1);
2303 EXPECT_TRUE(fd2 != -1);
2304
2305 expectAnswersValid(fd2, AF_INET6, "::1.2.3.4");
2306 expectAnswersValid(fd1, AF_INET6, "::1.2.3.4");
2307
2308 // Cache hits, expect still 2 queries
2309 EXPECT_EQ(2U, GetNumQueries(dns, host_name));
Luke Huang40f5f492019-05-09 19:37:35 +08002310
2311 // Test both ANDROID_RESOLV_NO_CACHE_STORE and ANDROID_RESOLV_NO_CACHE_LOOKUP are set
2312 dns.clearQueries();
2313
2314 // Make sure that the cache of "howdy.example2.com" exists.
2315 fd1 = resNetworkQuery(TEST_NETID, "howdy.example2.com", ns_c_in, ns_t_aaaa, 0);
2316 EXPECT_TRUE(fd1 != -1);
2317 expectAnswersValid(fd1, AF_INET6, "::1.2.3.5");
2318 EXPECT_EQ(1U, GetNumQueries(dns, another_host_name));
2319
2320 // Re-query with testFlags
2321 const int testFlag = ANDROID_RESOLV_NO_CACHE_STORE | ANDROID_RESOLV_NO_CACHE_LOOKUP;
2322 fd1 = resNetworkQuery(TEST_NETID, "howdy.example2.com", ns_c_in, ns_t_aaaa, testFlag);
2323 EXPECT_TRUE(fd1 != -1);
2324 expectAnswersValid(fd1, AF_INET6, "::1.2.3.5");
2325 // Expect cache lookup is skipped.
2326 EXPECT_EQ(2U, GetNumQueries(dns, another_host_name));
2327
2328 // Do another query with testFlags
2329 fd1 = resNetworkQuery(TEST_NETID, "howdy.example2.com", ns_c_in, ns_t_a, testFlag);
2330 EXPECT_TRUE(fd1 != -1);
2331 expectAnswersValid(fd1, AF_INET, "1.2.3.5");
2332 // Expect cache lookup is skipped.
2333 EXPECT_EQ(3U, GetNumQueries(dns, another_host_name));
2334
2335 // Re-query with no flags
2336 fd1 = resNetworkQuery(TEST_NETID, "howdy.example2.com", ns_c_in, ns_t_a, 0);
2337 EXPECT_TRUE(fd1 != -1);
2338 expectAnswersValid(fd1, AF_INET, "1.2.3.5");
2339 // Expect no cache hit because cache storing is also skipped in previous query.
2340 EXPECT_EQ(4U, GetNumQueries(dns, another_host_name));
Luke Huangba7bef92018-12-26 16:53:03 +08002341}
2342
Luke Huang08b13d22020-02-05 14:46:21 +08002343TEST_F(ResolverTest, Async_NoCacheStoreFlagDoesNotRefreshStaleCacheEntry) {
2344 constexpr char listen_addr[] = "127.0.0.4";
2345 constexpr char host_name[] = "howdy.example.com.";
2346 const std::vector<DnsRecord> records = {
2347 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2348 };
2349
2350 test::DNSResponder dns(listen_addr);
2351 StartDns(dns, records);
2352 std::vector<std::string> servers = {listen_addr};
2353 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
2354
2355 const unsigned SHORT_TTL_SEC = 1;
2356 dns.setTtl(SHORT_TTL_SEC);
2357
2358 // Refer to b/148842821 for the purpose of below test steps.
2359 // Basically, this test is used to ensure stale cache case is handled
2360 // correctly with ANDROID_RESOLV_NO_CACHE_STORE.
2361 int fd = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
2362 EXPECT_TRUE(fd != -1);
2363 expectAnswersValid(fd, AF_INET, "1.2.3.4");
2364
2365 EXPECT_EQ(1U, GetNumQueries(dns, host_name));
2366 dns.clearQueries();
2367
2368 // Wait until cache expired
2369 sleep(SHORT_TTL_SEC + 0.5);
2370
2371 // Now request the same hostname again.
2372 // We should see a new DNS query because the entry in cache has become stale.
2373 // Due to ANDROID_RESOLV_NO_CACHE_STORE, this query must *not* refresh that stale entry.
2374 fd = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2375 ANDROID_RESOLV_NO_CACHE_STORE);
2376 EXPECT_TRUE(fd != -1);
2377 expectAnswersValid(fd, AF_INET, "1.2.3.4");
2378 EXPECT_EQ(1U, GetNumQueries(dns, host_name));
2379 dns.clearQueries();
2380
2381 // If the cache is still stale, we expect to see one more DNS query
2382 // (this time the cache will be refreshed, but we're not checking for it).
2383 fd = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
2384 EXPECT_TRUE(fd != -1);
2385 expectAnswersValid(fd, AF_INET, "1.2.3.4");
2386 EXPECT_EQ(1U, GetNumQueries(dns, host_name));
2387}
2388
Luke Huangba7bef92018-12-26 16:53:03 +08002389TEST_F(ResolverTest, Async_NoRetryFlag) {
Luke Huang70931aa2019-01-31 11:57:41 +08002390 constexpr char listen_addr0[] = "127.0.0.4";
2391 constexpr char listen_addr1[] = "127.0.0.6";
Xiao Ma09b71022018-12-11 17:56:32 +09002392 constexpr char host_name[] = "howdy.example.com.";
2393 const std::vector<DnsRecord> records = {
2394 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2395 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
2396 };
2397
Luke Huang70931aa2019-01-31 11:57:41 +08002398 test::DNSResponder dns0(listen_addr0);
2399 test::DNSResponder dns1(listen_addr1);
2400 StartDns(dns0, records);
2401 StartDns(dns1, records);
2402 ASSERT_TRUE(mDnsClient.SetResolversForNetwork({listen_addr0, listen_addr1}));
Luke Huangba7bef92018-12-26 16:53:03 +08002403
Luke Huang70931aa2019-01-31 11:57:41 +08002404 dns0.clearQueries();
2405 dns1.clearQueries();
2406
2407 dns0.setResponseProbability(0.0);
2408 dns1.setResponseProbability(0.0);
Luke Huangba7bef92018-12-26 16:53:03 +08002409
2410 int fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a,
2411 ANDROID_RESOLV_NO_RETRY);
2412 EXPECT_TRUE(fd1 != -1);
2413
2414 int fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa,
2415 ANDROID_RESOLV_NO_RETRY);
2416 EXPECT_TRUE(fd2 != -1);
2417
2418 // expect no response
2419 expectAnswersNotValid(fd1, -ETIMEDOUT);
2420 expectAnswersNotValid(fd2, -ETIMEDOUT);
2421
Luke Huang70931aa2019-01-31 11:57:41 +08002422 // No retry case, expect total 2 queries. The server is selected randomly.
2423 EXPECT_EQ(2U, GetNumQueries(dns0, host_name) + GetNumQueries(dns1, host_name));
Luke Huangba7bef92018-12-26 16:53:03 +08002424
Luke Huang70931aa2019-01-31 11:57:41 +08002425 dns0.clearQueries();
2426 dns1.clearQueries();
Luke Huangba7bef92018-12-26 16:53:03 +08002427
2428 fd1 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_a, 0);
2429 EXPECT_TRUE(fd1 != -1);
2430
2431 fd2 = resNetworkQuery(TEST_NETID, "howdy.example.com", ns_c_in, ns_t_aaaa, 0);
2432 EXPECT_TRUE(fd2 != -1);
2433
2434 // expect no response
2435 expectAnswersNotValid(fd1, -ETIMEDOUT);
2436 expectAnswersNotValid(fd2, -ETIMEDOUT);
2437
2438 // Retry case, expect 4 queries
Luke Huang70931aa2019-01-31 11:57:41 +08002439 EXPECT_EQ(4U, GetNumQueries(dns0, host_name));
2440 EXPECT_EQ(4U, GetNumQueries(dns1, host_name));
2441}
2442
2443TEST_F(ResolverTest, Async_VerifyQueryID) {
2444 constexpr char listen_addr[] = "127.0.0.4";
2445 constexpr char host_name[] = "howdy.example.com.";
2446 const std::vector<DnsRecord> records = {
2447 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2448 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
2449 };
2450
2451 test::DNSResponder dns(listen_addr);
2452 StartDns(dns, records);
2453 std::vector<std::string> servers = {listen_addr};
2454 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
2455
2456 const uint8_t queryBuf1[] = {
2457 /* Header */
2458 0x55, 0x66, /* Transaction ID */
2459 0x01, 0x00, /* Flags */
2460 0x00, 0x01, /* Questions */
2461 0x00, 0x00, /* Answer RRs */
2462 0x00, 0x00, /* Authority RRs */
2463 0x00, 0x00, /* Additional RRs */
2464 /* Queries */
2465 0x05, 0x68, 0x6f, 0x77, 0x64, 0x79, 0x07, 0x65, 0x78, 0x61, 0x6d, 0x70, 0x6c, 0x65,
2466 0x03, 0x63, 0x6f, 0x6d, 0x00, /* Name */
2467 0x00, 0x01, /* Type */
2468 0x00, 0x01 /* Class */
2469 };
2470
2471 int fd = resNetworkSend(TEST_NETID, queryBuf1, sizeof(queryBuf1), 0);
2472 EXPECT_TRUE(fd != -1);
2473
2474 uint8_t buf[MAXPACKET] = {};
2475 int rcode;
2476
2477 int res = getAsyncResponse(fd, &rcode, buf, MAXPACKET);
2478 EXPECT_GT(res, 0);
2479 EXPECT_EQ("1.2.3.4", toString(buf, res, AF_INET));
2480
2481 auto hp = reinterpret_cast<HEADER*>(buf);
2482 EXPECT_EQ(21862U, htons(hp->id));
2483
2484 EXPECT_EQ(1U, GetNumQueries(dns, host_name));
2485
2486 const uint8_t queryBuf2[] = {
2487 /* Header */
2488 0x00, 0x53, /* Transaction ID */
2489 0x01, 0x00, /* Flags */
2490 0x00, 0x01, /* Questions */
2491 0x00, 0x00, /* Answer RRs */
2492 0x00, 0x00, /* Authority RRs */
2493 0x00, 0x00, /* Additional RRs */
2494 /* Queries */
2495 0x05, 0x68, 0x6f, 0x77, 0x64, 0x79, 0x07, 0x65, 0x78, 0x61, 0x6d, 0x70, 0x6c, 0x65,
2496 0x03, 0x63, 0x6f, 0x6d, 0x00, /* Name */
2497 0x00, 0x01, /* Type */
2498 0x00, 0x01 /* Class */
2499 };
2500
2501 // Re-query verify cache works and query id is correct
2502 fd = resNetworkSend(TEST_NETID, queryBuf2, sizeof(queryBuf2), 0);
2503
2504 EXPECT_TRUE(fd != -1);
2505
2506 res = getAsyncResponse(fd, &rcode, buf, MAXPACKET);
2507 EXPECT_GT(res, 0);
2508 EXPECT_EQ("1.2.3.4", toString(buf, res, AF_INET));
2509
2510 EXPECT_EQ(0x0053U, htons(hp->id));
2511
2512 EXPECT_EQ(1U, GetNumQueries(dns, host_name));
Luke Huangba7bef92018-12-26 16:53:03 +08002513}
2514
Mike Yu4f3747b2018-12-02 17:54:29 +09002515// This test checks that the resolver should not generate the request containing OPT RR when using
Ken Chen0a015532019-01-02 14:59:38 +08002516// cleartext DNS. If we query the DNS server not supporting EDNS0 and it reponds with
2517// FORMERR_ON_EDNS, we will fallback to no EDNS0 and try again. If the server does no response, we
2518// won't retry so that we get no answer.
Mike Yu4f3747b2018-12-02 17:54:29 +09002519TEST_F(ResolverTest, BrokenEdns) {
2520 typedef test::DNSResponder::Edns Edns;
2521 enum ExpectResult { EXPECT_FAILURE, EXPECT_SUCCESS };
2522
Mike Yu3977d482020-02-26 17:18:57 +08002523 // Perform cleartext query in off mode.
Mike Yu4f3747b2018-12-02 17:54:29 +09002524 const char OFF[] = "off";
Mike Yu3977d482020-02-26 17:18:57 +08002525
2526 // Perform cleartext query when there's no private DNS server validated in opportunistic mode.
Mike Yu4f3747b2018-12-02 17:54:29 +09002527 const char OPPORTUNISTIC_UDP[] = "opportunistic_udp";
Mike Yu3977d482020-02-26 17:18:57 +08002528
2529 // Perform cleartext query when there is a private DNS server validated in opportunistic mode.
2530 const char OPPORTUNISTIC_FALLBACK_UDP[] = "opportunistic_fallback_udp";
2531
2532 // Perform cyphertext query in opportunistic mode.
Mike Yu4f3747b2018-12-02 17:54:29 +09002533 const char OPPORTUNISTIC_TLS[] = "opportunistic_tls";
Mike Yu3977d482020-02-26 17:18:57 +08002534
2535 // Perform cyphertext query in strict mode.
Mike Yu4f3747b2018-12-02 17:54:29 +09002536 const char STRICT[] = "strict";
Mike Yu3977d482020-02-26 17:18:57 +08002537
Mike Yu4f3747b2018-12-02 17:54:29 +09002538 const char GETHOSTBYNAME[] = "gethostbyname";
2539 const char GETADDRINFO[] = "getaddrinfo";
Mike Yu4f3747b2018-12-02 17:54:29 +09002540 const char ADDR4[] = "192.0.2.1";
2541 const char CLEARTEXT_ADDR[] = "127.0.0.53";
2542 const char CLEARTEXT_PORT[] = "53";
2543 const char TLS_PORT[] = "853";
Luke Huangf8215372019-11-22 11:53:41 +08002544 const std::vector<std::string> servers = {CLEARTEXT_ADDR};
Mike Yu3977d482020-02-26 17:18:57 +08002545 ResolverParamsParcel paramsForCleanup = DnsResponderClient::GetDefaultResolverParamsParcel();
2546 paramsForCleanup.servers.clear();
2547 paramsForCleanup.tlsServers.clear();
Mike Yu4f3747b2018-12-02 17:54:29 +09002548
Mike Yufc125e42019-05-15 20:41:28 +08002549 test::DNSResponder dns(CLEARTEXT_ADDR, CLEARTEXT_PORT, ns_rcode::ns_r_servfail);
Mike Yu4f3747b2018-12-02 17:54:29 +09002550 ASSERT_TRUE(dns.startServer());
2551
2552 test::DnsTlsFrontend tls(CLEARTEXT_ADDR, TLS_PORT, CLEARTEXT_ADDR, CLEARTEXT_PORT);
2553
Luke Huangf8215372019-11-22 11:53:41 +08002554 // clang-format off
Mike Yu4f3747b2018-12-02 17:54:29 +09002555 static const struct TestConfig {
2556 std::string mode;
2557 std::string method;
2558 Edns edns;
2559 ExpectResult expectResult;
2560
2561 std::string asHostName() const {
2562 const char* ednsString;
2563 switch (edns) {
2564 case Edns::ON:
2565 ednsString = "ednsOn";
2566 break;
Ken Chen0a015532019-01-02 14:59:38 +08002567 case Edns::FORMERR_ON_EDNS:
Mike Yu4f3747b2018-12-02 17:54:29 +09002568 ednsString = "ednsFormerr";
2569 break;
2570 case Edns::DROP:
2571 ednsString = "ednsDrop";
2572 break;
2573 default:
2574 ednsString = "";
2575 break;
2576 }
2577 return StringPrintf("%s.%s.%s.", mode.c_str(), method.c_str(), ednsString);
2578 }
2579 } testConfigs[] = {
Mike Yu3977d482020-02-26 17:18:57 +08002580 // In OPPORTUNISTIC_TLS, if the DNS server doesn't support EDNS0 but TLS, the lookup
2581 // fails. Could such server exist? if so, we might need to fix it to fallback to
2582 // cleartext query. If the server still make no response for the queries with EDNS0, we
2583 // might also need to fix it to retry without EDNS0.
Mike Yu4f3747b2018-12-02 17:54:29 +09002584 // Another thing is that {OPPORTUNISTIC_TLS, Edns::DROP} and {STRICT, Edns::DROP} are
2585 // commented out since TLS timeout is not configurable.
2586 // TODO: Uncomment them after TLS timeout is configurable.
Mike Yu3977d482020-02-26 17:18:57 +08002587 {OFF, GETHOSTBYNAME, Edns::ON, EXPECT_SUCCESS},
2588 {OPPORTUNISTIC_UDP, GETHOSTBYNAME, Edns::ON, EXPECT_SUCCESS},
2589 {OPPORTUNISTIC_FALLBACK_UDP, GETHOSTBYNAME, Edns::ON, EXPECT_SUCCESS},
2590 {OPPORTUNISTIC_TLS, GETHOSTBYNAME, Edns::ON, EXPECT_SUCCESS},
2591 {STRICT, GETHOSTBYNAME, Edns::ON, EXPECT_SUCCESS},
2592 {OFF, GETHOSTBYNAME, Edns::FORMERR_ON_EDNS, EXPECT_SUCCESS},
2593 {OPPORTUNISTIC_UDP, GETHOSTBYNAME, Edns::FORMERR_ON_EDNS, EXPECT_SUCCESS},
2594 {OPPORTUNISTIC_FALLBACK_UDP, GETHOSTBYNAME, Edns::FORMERR_ON_EDNS, EXPECT_SUCCESS},
2595 {OPPORTUNISTIC_TLS, GETHOSTBYNAME, Edns::FORMERR_ON_EDNS, EXPECT_FAILURE},
2596 {STRICT, GETHOSTBYNAME, Edns::FORMERR_ON_EDNS, EXPECT_FAILURE},
2597 {OFF, GETHOSTBYNAME, Edns::DROP, EXPECT_SUCCESS},
2598 {OPPORTUNISTIC_UDP, GETHOSTBYNAME, Edns::DROP, EXPECT_SUCCESS},
2599
2600 // The failure is due to no retry on timeout. Maybe fix it?
2601 {OPPORTUNISTIC_FALLBACK_UDP, GETHOSTBYNAME, Edns::DROP, EXPECT_FAILURE},
2602
2603 //{OPPORTUNISTIC_TLS, GETHOSTBYNAME, Edns::DROP, EXPECT_FAILURE},
2604 //{STRICT, GETHOSTBYNAME, Edns::DROP, EXPECT_FAILURE},
2605 {OFF, GETADDRINFO, Edns::ON, EXPECT_SUCCESS},
2606 {OPPORTUNISTIC_UDP, GETADDRINFO, Edns::ON, EXPECT_SUCCESS},
2607 {OPPORTUNISTIC_FALLBACK_UDP, GETADDRINFO, Edns::ON, EXPECT_SUCCESS},
2608 {OPPORTUNISTIC_TLS, GETADDRINFO, Edns::ON, EXPECT_SUCCESS},
2609 {STRICT, GETADDRINFO, Edns::ON, EXPECT_SUCCESS},
2610 {OFF, GETADDRINFO, Edns::FORMERR_ON_EDNS, EXPECT_SUCCESS},
2611 {OPPORTUNISTIC_UDP, GETADDRINFO, Edns::FORMERR_ON_EDNS, EXPECT_SUCCESS},
2612 {OPPORTUNISTIC_FALLBACK_UDP, GETADDRINFO, Edns::FORMERR_ON_EDNS, EXPECT_SUCCESS},
2613 {OPPORTUNISTIC_TLS, GETADDRINFO, Edns::FORMERR_ON_EDNS, EXPECT_FAILURE},
2614 {STRICT, GETADDRINFO, Edns::FORMERR_ON_EDNS, EXPECT_FAILURE},
2615 {OFF, GETADDRINFO, Edns::DROP, EXPECT_SUCCESS},
2616 {OPPORTUNISTIC_UDP, GETADDRINFO, Edns::DROP, EXPECT_SUCCESS},
2617
2618 // The failure is due to no retry on timeout. Maybe fix it?
2619 {OPPORTUNISTIC_FALLBACK_UDP, GETADDRINFO, Edns::DROP, EXPECT_FAILURE},
2620
Mike Yu4f3747b2018-12-02 17:54:29 +09002621 //{OPPORTUNISTIC_TLS, GETADDRINFO, Edns::DROP, EXPECT_FAILURE},
2622 //{STRICT, GETADDRINFO, Edns::DROP, EXPECT_FAILURE},
2623 };
Luke Huangf8215372019-11-22 11:53:41 +08002624 // clang-format on
Mike Yu4f3747b2018-12-02 17:54:29 +09002625
2626 for (const auto& config : testConfigs) {
2627 const std::string testHostName = config.asHostName();
2628 SCOPED_TRACE(testHostName);
2629
2630 const char* host_name = testHostName.c_str();
2631 dns.addMapping(host_name, ns_type::ns_t_a, ADDR4);
2632 dns.setEdns(config.edns);
2633
2634 if (config.mode == OFF) {
Mike Yu0f20cdd2019-06-11 11:52:37 +08002635 if (tls.running()) {
2636 ASSERT_TRUE(tls.stopServer());
2637 }
Xiao Ma09b71022018-12-11 17:56:32 +09002638 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
Mike Yu4f3747b2018-12-02 17:54:29 +09002639 } else if (config.mode == OPPORTUNISTIC_UDP) {
Mike Yu0f20cdd2019-06-11 11:52:37 +08002640 if (tls.running()) {
2641 ASSERT_TRUE(tls.stopServer());
2642 }
Xiao Ma09b71022018-12-11 17:56:32 +09002643 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains,
waynema0e73c2e2019-07-31 15:04:08 +08002644 kDefaultParams, ""));
Mike Yu724f77d2019-08-16 11:14:50 +08002645 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), false));
Mike Yu3977d482020-02-26 17:18:57 +08002646 } else if (config.mode == OPPORTUNISTIC_TLS || config.mode == OPPORTUNISTIC_FALLBACK_UDP) {
Mike Yu0f20cdd2019-06-11 11:52:37 +08002647 if (!tls.running()) {
2648 ASSERT_TRUE(tls.startServer());
2649 }
Xiao Ma09b71022018-12-11 17:56:32 +09002650 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains,
waynema0e73c2e2019-07-31 15:04:08 +08002651 kDefaultParams, ""));
Mike Yu724f77d2019-08-16 11:14:50 +08002652 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
Mike Yu3977d482020-02-26 17:18:57 +08002653
2654 if (config.mode == OPPORTUNISTIC_FALLBACK_UDP) {
2655 // Force the resolver to fallback to cleartext queries.
2656 ASSERT_TRUE(tls.stopServer());
2657 }
Mike Yu4f3747b2018-12-02 17:54:29 +09002658 } else if (config.mode == STRICT) {
Mike Yu0f20cdd2019-06-11 11:52:37 +08002659 if (!tls.running()) {
2660 ASSERT_TRUE(tls.startServer());
2661 }
Xiao Ma09b71022018-12-11 17:56:32 +09002662 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains,
waynema0e73c2e2019-07-31 15:04:08 +08002663 kDefaultParams, kDefaultPrivateDnsHostName));
Mike Yu724f77d2019-08-16 11:14:50 +08002664 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
Mike Yu4f3747b2018-12-02 17:54:29 +09002665 }
2666
2667 if (config.method == GETHOSTBYNAME) {
2668 const hostent* h_result = gethostbyname(host_name);
2669 if (config.expectResult == EXPECT_SUCCESS) {
2670 EXPECT_LE(1U, GetNumQueries(dns, host_name));
2671 ASSERT_TRUE(h_result != nullptr);
2672 ASSERT_EQ(4, h_result->h_length);
2673 ASSERT_FALSE(h_result->h_addr_list[0] == nullptr);
2674 EXPECT_EQ(ADDR4, ToString(h_result));
2675 EXPECT_TRUE(h_result->h_addr_list[1] == nullptr);
2676 } else {
2677 EXPECT_EQ(0U, GetNumQueriesForType(dns, ns_type::ns_t_a, host_name));
2678 ASSERT_TRUE(h_result == nullptr);
2679 ASSERT_EQ(HOST_NOT_FOUND, h_errno);
2680 }
2681 } else if (config.method == GETADDRINFO) {
2682 ScopedAddrinfo ai_result;
2683 addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
2684 ai_result = safe_getaddrinfo(host_name, nullptr, &hints);
2685 if (config.expectResult == EXPECT_SUCCESS) {
2686 EXPECT_TRUE(ai_result != nullptr);
2687 EXPECT_EQ(1U, GetNumQueries(dns, host_name));
2688 const std::string result_str = ToString(ai_result);
2689 EXPECT_EQ(ADDR4, result_str);
2690 } else {
2691 EXPECT_TRUE(ai_result == nullptr);
2692 EXPECT_EQ(0U, GetNumQueries(dns, host_name));
2693 }
2694 } else {
2695 FAIL() << "Unsupported query method: " << config.method;
2696 }
2697
Mike Yudd4ac2d2019-05-31 16:52:11 +08002698 tls.clearQueries();
Mike Yu4f3747b2018-12-02 17:54:29 +09002699 dns.clearQueries();
Mike Yu3977d482020-02-26 17:18:57 +08002700
2701 // Clear the setup to force the resolver to validate private DNS servers in every test.
2702 ASSERT_TRUE(mDnsClient.SetResolversFromParcel(paramsForCleanup));
Mike Yu4f3747b2018-12-02 17:54:29 +09002703 }
Mike Yu4f3747b2018-12-02 17:54:29 +09002704}
nuccachena26cc2a2018-07-17 18:07:23 +08002705
Ken Chen0a015532019-01-02 14:59:38 +08002706// DNS-over-TLS validation success, but server does not respond to TLS query after a while.
2707// Resolver should have a reasonable number of retries instead of spinning forever. We don't have
2708// an efficient way to know if resolver is stuck in an infinite loop. However, test case will be
2709// failed due to timeout.
2710TEST_F(ResolverTest, UnstableTls) {
2711 const char CLEARTEXT_ADDR[] = "127.0.0.53";
2712 const char CLEARTEXT_PORT[] = "53";
2713 const char TLS_PORT[] = "853";
2714 const char* host_name1 = "nonexistent1.example.com.";
2715 const char* host_name2 = "nonexistent2.example.com.";
2716 const std::vector<std::string> servers = {CLEARTEXT_ADDR};
2717
Mike Yufc125e42019-05-15 20:41:28 +08002718 test::DNSResponder dns(CLEARTEXT_ADDR, CLEARTEXT_PORT, ns_rcode::ns_r_servfail);
Ken Chen0a015532019-01-02 14:59:38 +08002719 ASSERT_TRUE(dns.startServer());
2720 dns.setEdns(test::DNSResponder::Edns::FORMERR_ON_EDNS);
2721 test::DnsTlsFrontend tls(CLEARTEXT_ADDR, TLS_PORT, CLEARTEXT_ADDR, CLEARTEXT_PORT);
2722 ASSERT_TRUE(tls.startServer());
waynema0e73c2e2019-07-31 15:04:08 +08002723 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams, ""));
Mike Yu724f77d2019-08-16 11:14:50 +08002724 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
2725
Ken Chen0a015532019-01-02 14:59:38 +08002726 // Shutdown TLS server to get an error. It's similar to no response case but without waiting.
2727 tls.stopServer();
2728
2729 const hostent* h_result = gethostbyname(host_name1);
2730 EXPECT_EQ(1U, GetNumQueries(dns, host_name1));
2731 ASSERT_TRUE(h_result == nullptr);
2732 ASSERT_EQ(HOST_NOT_FOUND, h_errno);
2733
2734 addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
2735 ScopedAddrinfo ai_result = safe_getaddrinfo(host_name2, nullptr, &hints);
2736 EXPECT_TRUE(ai_result == nullptr);
2737 EXPECT_EQ(1U, GetNumQueries(dns, host_name2));
2738}
2739
2740// DNS-over-TLS validation success, but server does not respond to TLS query after a while.
2741// Moreover, server responds RCODE=FORMERR even on non-EDNS query.
2742TEST_F(ResolverTest, BogusDnsServer) {
2743 const char CLEARTEXT_ADDR[] = "127.0.0.53";
2744 const char CLEARTEXT_PORT[] = "53";
2745 const char TLS_PORT[] = "853";
2746 const char* host_name1 = "nonexistent1.example.com.";
2747 const char* host_name2 = "nonexistent2.example.com.";
2748 const std::vector<std::string> servers = {CLEARTEXT_ADDR};
2749
Mike Yufc125e42019-05-15 20:41:28 +08002750 test::DNSResponder dns(CLEARTEXT_ADDR, CLEARTEXT_PORT, ns_rcode::ns_r_servfail);
Ken Chen0a015532019-01-02 14:59:38 +08002751 ASSERT_TRUE(dns.startServer());
2752 test::DnsTlsFrontend tls(CLEARTEXT_ADDR, TLS_PORT, CLEARTEXT_ADDR, CLEARTEXT_PORT);
2753 ASSERT_TRUE(tls.startServer());
waynema0e73c2e2019-07-31 15:04:08 +08002754 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams, ""));
Mike Yu724f77d2019-08-16 11:14:50 +08002755 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
2756
Ken Chen0a015532019-01-02 14:59:38 +08002757 // Shutdown TLS server to get an error. It's similar to no response case but without waiting.
2758 tls.stopServer();
2759 dns.setEdns(test::DNSResponder::Edns::FORMERR_UNCOND);
2760
2761 const hostent* h_result = gethostbyname(host_name1);
2762 EXPECT_EQ(0U, GetNumQueries(dns, host_name1));
2763 ASSERT_TRUE(h_result == nullptr);
2764 ASSERT_EQ(HOST_NOT_FOUND, h_errno);
2765
2766 addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
2767 ScopedAddrinfo ai_result = safe_getaddrinfo(host_name2, nullptr, &hints);
2768 EXPECT_TRUE(ai_result == nullptr);
2769 EXPECT_EQ(0U, GetNumQueries(dns, host_name2));
2770}
2771
nuccachena26cc2a2018-07-17 18:07:23 +08002772TEST_F(ResolverTest, GetAddrInfo_Dns64Synthesize) {
2773 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08002774 constexpr char dns64_name[] = "ipv4only.arpa.";
2775 constexpr char host_name[] = "v4only.example.com.";
Xiao Ma09b71022018-12-11 17:56:32 +09002776 const std::vector<DnsRecord> records = {
2777 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
2778 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2779 };
nuccachena26cc2a2018-07-17 18:07:23 +08002780
Xiao Ma09b71022018-12-11 17:56:32 +09002781 test::DNSResponder dns(listen_addr);
Xiao Ma09b71022018-12-11 17:56:32 +09002782 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08002783
2784 std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002785 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08002786
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002787 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08002788 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08002789 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08002790
2791 // hints are necessary in order to let netd know which type of addresses the caller is
2792 // interested in.
Xiao Ma09b71022018-12-11 17:56:32 +09002793 const addrinfo hints = {.ai_family = AF_UNSPEC};
nuccachena26cc2a2018-07-17 18:07:23 +08002794 ScopedAddrinfo result = safe_getaddrinfo("v4only", nullptr, &hints);
2795 EXPECT_TRUE(result != nullptr);
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002796 // TODO: BUG: there should only be two queries, one AAAA (which returns no records) and one A
2797 // (which returns 1.2.3.4). But there is an extra AAAA.
2798 EXPECT_EQ(3U, GetNumQueries(dns, host_name));
nuccachena26cc2a2018-07-17 18:07:23 +08002799
2800 std::string result_str = ToString(result);
2801 EXPECT_EQ(result_str, "64:ff9b::102:304");
2802
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002803 // Stopping NAT64 prefix discovery disables synthesis.
Luke Huang5bd827c2019-03-14 16:10:04 +08002804 EXPECT_TRUE(mDnsClient.resolvService()->stopPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08002805 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_NOT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08002806
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002807 dns.clearQueries();
nuccachena26cc2a2018-07-17 18:07:23 +08002808
2809 result = safe_getaddrinfo("v4only", nullptr, &hints);
2810 EXPECT_TRUE(result != nullptr);
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002811 // TODO: BUG: there should only be one query, an AAAA (which returns no records), because the
2812 // A is already cached. But there is an extra AAAA.
2813 EXPECT_EQ(2U, GetNumQueries(dns, host_name));
nuccachena26cc2a2018-07-17 18:07:23 +08002814
2815 result_str = ToString(result);
2816 EXPECT_EQ(result_str, "1.2.3.4");
2817}
2818
nuccachena26cc2a2018-07-17 18:07:23 +08002819TEST_F(ResolverTest, GetAddrInfo_Dns64QuerySpecified) {
2820 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08002821 constexpr char dns64_name[] = "ipv4only.arpa.";
2822 constexpr char host_name[] = "v4only.example.com.";
Xiao Ma09b71022018-12-11 17:56:32 +09002823 const std::vector<DnsRecord> records = {
2824 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
2825 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2826 };
nuccachena26cc2a2018-07-17 18:07:23 +08002827
Xiao Ma09b71022018-12-11 17:56:32 +09002828 test::DNSResponder dns(listen_addr);
2829 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08002830 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002831 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08002832
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002833 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08002834 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08002835 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08002836
2837 // Ensure to synthesize AAAA if AF_INET6 is specified, and not to synthesize AAAA
2838 // in AF_INET case.
2839 addrinfo hints;
2840 memset(&hints, 0, sizeof(hints));
2841 hints.ai_family = AF_INET6;
2842 ScopedAddrinfo result = safe_getaddrinfo("v4only", nullptr, &hints);
2843 EXPECT_TRUE(result != nullptr);
2844 std::string result_str = ToString(result);
2845 EXPECT_EQ(result_str, "64:ff9b::102:304");
2846
2847 hints.ai_family = AF_INET;
2848 result = safe_getaddrinfo("v4only", nullptr, &hints);
2849 EXPECT_TRUE(result != nullptr);
2850 EXPECT_LE(2U, GetNumQueries(dns, host_name));
2851 result_str = ToString(result);
2852 EXPECT_EQ(result_str, "1.2.3.4");
2853}
nuccachena26cc2a2018-07-17 18:07:23 +08002854
2855TEST_F(ResolverTest, GetAddrInfo_Dns64QueryUnspecifiedV6) {
2856 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08002857 constexpr char dns64_name[] = "ipv4only.arpa.";
2858 constexpr char host_name[] = "v4v6.example.com.";
Xiao Ma09b71022018-12-11 17:56:32 +09002859 const std::vector<DnsRecord> records = {
2860 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
2861 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2862 {host_name, ns_type::ns_t_aaaa, "2001:db8::1.2.3.4"},
2863 };
nuccachena26cc2a2018-07-17 18:07:23 +08002864
Xiao Ma09b71022018-12-11 17:56:32 +09002865 test::DNSResponder dns(listen_addr);
2866 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08002867 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002868 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08002869
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002870 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08002871 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08002872 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08002873
Xiao Ma09b71022018-12-11 17:56:32 +09002874 const addrinfo hints = {.ai_family = AF_UNSPEC};
nuccachena26cc2a2018-07-17 18:07:23 +08002875 ScopedAddrinfo result = safe_getaddrinfo("v4v6", nullptr, &hints);
2876 EXPECT_TRUE(result != nullptr);
2877 EXPECT_LE(2U, GetNumQueries(dns, host_name));
2878
2879 // In AF_UNSPEC case, do not synthesize AAAA if there's at least one AAAA answer.
Xiao Ma09b71022018-12-11 17:56:32 +09002880 const std::vector<std::string> result_strs = ToStrings(result);
nuccachena26cc2a2018-07-17 18:07:23 +08002881 for (const auto& str : result_strs) {
2882 EXPECT_TRUE(str == "1.2.3.4" || str == "2001:db8::102:304")
2883 << ", result_str='" << str << "'";
2884 }
2885}
2886
2887TEST_F(ResolverTest, GetAddrInfo_Dns64QueryUnspecifiedNoV6) {
2888 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08002889 constexpr char dns64_name[] = "ipv4only.arpa.";
2890 constexpr char host_name[] = "v4v6.example.com.";
Xiao Ma09b71022018-12-11 17:56:32 +09002891 const std::vector<DnsRecord> records = {
2892 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
2893 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2894 };
nuccachena26cc2a2018-07-17 18:07:23 +08002895
Xiao Ma09b71022018-12-11 17:56:32 +09002896 test::DNSResponder dns(listen_addr);
2897 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08002898 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002899 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08002900
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002901 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08002902 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08002903 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08002904
Xiao Ma09b71022018-12-11 17:56:32 +09002905 const addrinfo hints = {.ai_family = AF_UNSPEC};
nuccachena26cc2a2018-07-17 18:07:23 +08002906 ScopedAddrinfo result = safe_getaddrinfo("v4v6", nullptr, &hints);
2907 EXPECT_TRUE(result != nullptr);
2908 EXPECT_LE(2U, GetNumQueries(dns, host_name));
2909
2910 // In AF_UNSPEC case, synthesize AAAA if there's no AAAA answer.
2911 std::string result_str = ToString(result);
2912 EXPECT_EQ(result_str, "64:ff9b::102:304");
2913}
2914
2915TEST_F(ResolverTest, GetAddrInfo_Dns64QuerySpecialUseIPv4Addresses) {
2916 constexpr char THIS_NETWORK[] = "this_network";
2917 constexpr char LOOPBACK[] = "loopback";
2918 constexpr char LINK_LOCAL[] = "link_local";
2919 constexpr char MULTICAST[] = "multicast";
2920 constexpr char LIMITED_BROADCAST[] = "limited_broadcast";
2921
2922 constexpr char ADDR_THIS_NETWORK[] = "0.0.0.1";
2923 constexpr char ADDR_LOOPBACK[] = "127.0.0.1";
2924 constexpr char ADDR_LINK_LOCAL[] = "169.254.0.1";
2925 constexpr char ADDR_MULTICAST[] = "224.0.0.1";
2926 constexpr char ADDR_LIMITED_BROADCAST[] = "255.255.255.255";
2927
2928 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08002929 constexpr char dns64_name[] = "ipv4only.arpa.";
2930
Xiao Ma09b71022018-12-11 17:56:32 +09002931 test::DNSResponder dns(listen_addr);
2932 StartDns(dns, {{dns64_name, ns_type::ns_t_aaaa, "64:ff9b::"}});
nuccachena26cc2a2018-07-17 18:07:23 +08002933 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002934 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08002935
Lorenzo Colittid39345c2019-02-18 10:59:29 +09002936 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08002937 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08002938 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08002939
Luke Huangf8215372019-11-22 11:53:41 +08002940 // clang-format off
nuccachena26cc2a2018-07-17 18:07:23 +08002941 static const struct TestConfig {
2942 std::string name;
2943 std::string addr;
2944
2945 std::string asHostName() const { return StringPrintf("%s.example.com.", name.c_str()); }
2946 } testConfigs[]{
2947 {THIS_NETWORK, ADDR_THIS_NETWORK},
2948 {LOOPBACK, ADDR_LOOPBACK},
2949 {LINK_LOCAL, ADDR_LINK_LOCAL},
2950 {MULTICAST, ADDR_MULTICAST},
2951 {LIMITED_BROADCAST, ADDR_LIMITED_BROADCAST}
2952 };
Luke Huangf8215372019-11-22 11:53:41 +08002953 // clang-format on
nuccachena26cc2a2018-07-17 18:07:23 +08002954
2955 for (const auto& config : testConfigs) {
2956 const std::string testHostName = config.asHostName();
2957 SCOPED_TRACE(testHostName);
2958
2959 const char* host_name = testHostName.c_str();
2960 dns.addMapping(host_name, ns_type::ns_t_a, config.addr.c_str());
2961
2962 addrinfo hints;
2963 memset(&hints, 0, sizeof(hints));
2964 hints.ai_family = AF_INET6;
2965 ScopedAddrinfo result = safe_getaddrinfo(config.name.c_str(), nullptr, &hints);
2966 // In AF_INET6 case, don't return IPv4 answers
2967 EXPECT_TRUE(result == nullptr);
2968 EXPECT_LE(2U, GetNumQueries(dns, host_name));
2969 dns.clearQueries();
2970
2971 memset(&hints, 0, sizeof(hints));
2972 hints.ai_family = AF_UNSPEC;
2973 result = safe_getaddrinfo(config.name.c_str(), nullptr, &hints);
2974 EXPECT_TRUE(result != nullptr);
2975 // Expect IPv6 query only. IPv4 answer has been cached in previous query.
2976 EXPECT_LE(1U, GetNumQueries(dns, host_name));
2977 // In AF_UNSPEC case, don't synthesize special use IPv4 address.
2978 std::string result_str = ToString(result);
2979 EXPECT_EQ(result_str, config.addr.c_str());
2980 dns.clearQueries();
2981 }
2982}
2983
2984TEST_F(ResolverTest, GetAddrInfo_Dns64QueryWithNullArgumentHints) {
2985 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08002986 constexpr char dns64_name[] = "ipv4only.arpa.";
2987 constexpr char host_name[] = "v4only.example.com.";
2988 constexpr char host_name2[] = "v4v6.example.com.";
Xiao Ma09b71022018-12-11 17:56:32 +09002989 const std::vector<DnsRecord> records = {
2990 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
2991 {host_name, ns_type::ns_t_a, "1.2.3.4"},
2992 {host_name2, ns_type::ns_t_a, "1.2.3.4"},
2993 {host_name2, ns_type::ns_t_aaaa, "2001:db8::1.2.3.4"},
2994 };
nuccachena26cc2a2018-07-17 18:07:23 +08002995
Xiao Ma09b71022018-12-11 17:56:32 +09002996 test::DNSResponder dns(listen_addr);
2997 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08002998 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09002999 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003000
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003001 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003002 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003003 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003004
3005 // Assign argument hints of getaddrinfo() as null is equivalent to set ai_family AF_UNSPEC.
3006 // In AF_UNSPEC case, synthesize AAAA if there has A answer only.
3007 ScopedAddrinfo result = safe_getaddrinfo("v4only", nullptr, nullptr);
3008 EXPECT_TRUE(result != nullptr);
3009 EXPECT_LE(2U, GetNumQueries(dns, host_name));
3010 std::string result_str = ToString(result);
3011 EXPECT_EQ(result_str, "64:ff9b::102:304");
3012 dns.clearQueries();
3013
3014 // In AF_UNSPEC case, do not synthesize AAAA if there's at least one AAAA answer.
3015 result = safe_getaddrinfo("v4v6", nullptr, nullptr);
3016 EXPECT_TRUE(result != nullptr);
3017 EXPECT_LE(2U, GetNumQueries(dns, host_name2));
3018 std::vector<std::string> result_strs = ToStrings(result);
3019 for (const auto& str : result_strs) {
3020 EXPECT_TRUE(str == "1.2.3.4" || str == "2001:db8::102:304")
3021 << ", result_str='" << str << "'";
3022 }
3023}
3024
3025TEST_F(ResolverTest, GetAddrInfo_Dns64QueryNullArgumentNode) {
3026 constexpr char ADDR_ANYADDR_V4[] = "0.0.0.0";
3027 constexpr char ADDR_ANYADDR_V6[] = "::";
3028 constexpr char ADDR_LOCALHOST_V4[] = "127.0.0.1";
3029 constexpr char ADDR_LOCALHOST_V6[] = "::1";
3030
3031 constexpr char PORT_NAME_HTTP[] = "http";
3032 constexpr char PORT_NUMBER_HTTP[] = "80";
3033
3034 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08003035 constexpr char dns64_name[] = "ipv4only.arpa.";
3036
Xiao Ma09b71022018-12-11 17:56:32 +09003037 test::DNSResponder dns(listen_addr);
3038 StartDns(dns, {{dns64_name, ns_type::ns_t_aaaa, "64:ff9b::"}});
nuccachena26cc2a2018-07-17 18:07:23 +08003039 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003040 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003041
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003042 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003043 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003044 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003045
Luke Huangf8215372019-11-22 11:53:41 +08003046 // clang-format off
nuccachena26cc2a2018-07-17 18:07:23 +08003047 // If node is null, return address is listed by libc/getaddrinfo.c as follows.
3048 // - passive socket -> anyaddr (0.0.0.0 or ::)
3049 // - non-passive socket -> localhost (127.0.0.1 or ::1)
3050 static const struct TestConfig {
3051 int flag;
3052 std::string addr_v4;
3053 std::string addr_v6;
3054
3055 std::string asParameters() const {
3056 return StringPrintf("flag=%d, addr_v4=%s, addr_v6=%s", flag, addr_v4.c_str(),
3057 addr_v6.c_str());
3058 }
3059 } testConfigs[]{
3060 {0 /* non-passive */, ADDR_LOCALHOST_V4, ADDR_LOCALHOST_V6},
3061 {AI_PASSIVE, ADDR_ANYADDR_V4, ADDR_ANYADDR_V6}
3062 };
Luke Huangf8215372019-11-22 11:53:41 +08003063 // clang-format on
nuccachena26cc2a2018-07-17 18:07:23 +08003064
3065 for (const auto& config : testConfigs) {
3066 SCOPED_TRACE(config.asParameters());
3067
Xiao Ma09b71022018-12-11 17:56:32 +09003068 addrinfo hints = {
Nick Desaulnierscd6395a2019-10-11 09:15:24 -07003069 .ai_flags = config.flag,
Xiao Ma09b71022018-12-11 17:56:32 +09003070 .ai_family = AF_UNSPEC, // any address family
3071 .ai_socktype = 0, // any type
3072 .ai_protocol = 0, // any protocol
Xiao Ma09b71022018-12-11 17:56:32 +09003073 };
nuccachena26cc2a2018-07-17 18:07:23 +08003074
3075 // Assign hostname as null and service as port name.
3076 ScopedAddrinfo result = safe_getaddrinfo(nullptr, PORT_NAME_HTTP, &hints);
3077 ASSERT_TRUE(result != nullptr);
3078
3079 // Can't be synthesized because it should not get into Netd.
3080 std::vector<std::string> result_strs = ToStrings(result);
3081 for (const auto& str : result_strs) {
3082 EXPECT_TRUE(str == config.addr_v4 || str == config.addr_v6)
3083 << ", result_str='" << str << "'";
3084 }
3085
3086 // Assign hostname as null and service as numeric port number.
3087 hints.ai_flags = config.flag | AI_NUMERICSERV;
3088 result = safe_getaddrinfo(nullptr, PORT_NUMBER_HTTP, &hints);
3089 ASSERT_TRUE(result != nullptr);
3090
3091 // Can't be synthesized because it should not get into Netd.
3092 result_strs = ToStrings(result);
3093 for (const auto& str : result_strs) {
3094 EXPECT_TRUE(str == config.addr_v4 || str == config.addr_v6)
3095 << ", result_str='" << str << "'";
3096 }
3097 }
3098}
3099
3100TEST_F(ResolverTest, GetHostByAddr_ReverseDnsQueryWithHavingNat64Prefix) {
3101 struct hostent* result = nullptr;
3102 struct in_addr v4addr;
3103 struct in6_addr v6addr;
3104
3105 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08003106 constexpr char dns64_name[] = "ipv4only.arpa.";
3107 constexpr char ptr_name[] = "v4v6.example.com.";
3108 // PTR record for IPv4 address 1.2.3.4
3109 constexpr char ptr_addr_v4[] = "4.3.2.1.in-addr.arpa.";
3110 // PTR record for IPv6 address 2001:db8::102:304
3111 constexpr char ptr_addr_v6[] =
3112 "4.0.3.0.2.0.1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.8.b.d.0.1.0.0.2.ip6.arpa.";
Xiao Ma09b71022018-12-11 17:56:32 +09003113 const std::vector<DnsRecord> records = {
3114 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
3115 {ptr_addr_v4, ns_type::ns_t_ptr, ptr_name},
3116 {ptr_addr_v6, ns_type::ns_t_ptr, ptr_name},
3117 };
nuccachena26cc2a2018-07-17 18:07:23 +08003118
Xiao Ma09b71022018-12-11 17:56:32 +09003119 test::DNSResponder dns(listen_addr);
3120 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08003121 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003122 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003123
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003124 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003125 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003126 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003127
3128 // Reverse IPv4 DNS query. Prefix should have no effect on it.
3129 inet_pton(AF_INET, "1.2.3.4", &v4addr);
3130 result = gethostbyaddr(&v4addr, sizeof(v4addr), AF_INET);
3131 ASSERT_TRUE(result != nullptr);
3132 std::string result_str = result->h_name ? result->h_name : "null";
3133 EXPECT_EQ(result_str, "v4v6.example.com");
3134
3135 // Reverse IPv6 DNS query. Prefix should have no effect on it.
3136 inet_pton(AF_INET6, "2001:db8::102:304", &v6addr);
3137 result = gethostbyaddr(&v6addr, sizeof(v6addr), AF_INET6);
3138 ASSERT_TRUE(result != nullptr);
3139 result_str = result->h_name ? result->h_name : "null";
3140 EXPECT_EQ(result_str, "v4v6.example.com");
3141}
3142
3143TEST_F(ResolverTest, GetHostByAddr_ReverseDns64Query) {
3144 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08003145 constexpr char dns64_name[] = "ipv4only.arpa.";
3146 constexpr char ptr_name[] = "v4only.example.com.";
3147 // PTR record for IPv4 address 1.2.3.4
3148 constexpr char ptr_addr_v4[] = "4.3.2.1.in-addr.arpa.";
3149 // PTR record for IPv6 address 64:ff9b::1.2.3.4
3150 constexpr char ptr_addr_v6_nomapping[] =
3151 "4.0.3.0.2.0.1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.b.9.f.f.4.6.0.0.ip6.arpa.";
3152 constexpr char ptr_name_v6_synthesis[] = "v6synthesis.example.com.";
3153 // PTR record for IPv6 address 64:ff9b::5.6.7.8
3154 constexpr char ptr_addr_v6_synthesis[] =
3155 "8.0.7.0.6.0.5.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.b.9.f.f.4.6.0.0.ip6.arpa.";
Xiao Ma09b71022018-12-11 17:56:32 +09003156 const std::vector<DnsRecord> records = {
3157 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
3158 {ptr_addr_v4, ns_type::ns_t_ptr, ptr_name},
3159 {ptr_addr_v6_synthesis, ns_type::ns_t_ptr, ptr_name_v6_synthesis},
3160 };
nuccachena26cc2a2018-07-17 18:07:23 +08003161
Xiao Ma09b71022018-12-11 17:56:32 +09003162 test::DNSResponder dns(listen_addr);
3163 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08003164 // "ptr_addr_v6_nomapping" is not mapped in DNS server
nuccachena26cc2a2018-07-17 18:07:23 +08003165 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003166 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003167
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003168 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003169 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003170 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003171
3172 // Synthesized PTR record doesn't exist on DNS server
3173 // Reverse IPv6 DNS64 query while DNS server doesn't have an answer for synthesized address.
3174 // After querying synthesized address failed, expect that prefix is removed from IPv6
3175 // synthesized address and do reverse IPv4 query instead.
3176 struct in6_addr v6addr;
3177 inet_pton(AF_INET6, "64:ff9b::1.2.3.4", &v6addr);
3178 struct hostent* result = gethostbyaddr(&v6addr, sizeof(v6addr), AF_INET6);
3179 ASSERT_TRUE(result != nullptr);
3180 EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v6_nomapping)); // PTR record not exist
3181 EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v4)); // PTR record exist
3182 std::string result_str = result->h_name ? result->h_name : "null";
3183 EXPECT_EQ(result_str, "v4only.example.com");
3184 // Check that return address has been mapped from IPv4 to IPv6 address because Netd
3185 // removes NAT64 prefix and does IPv4 DNS reverse lookup in this case. Then, Netd
3186 // fakes the return IPv4 address as original queried IPv6 address.
3187 result_str = ToString(result);
3188 EXPECT_EQ(result_str, "64:ff9b::102:304");
3189 dns.clearQueries();
3190
3191 // Synthesized PTR record exists on DNS server
3192 // Reverse IPv6 DNS64 query while DNS server has an answer for synthesized address.
3193 // Expect to Netd pass through synthesized address for DNS queries.
3194 inet_pton(AF_INET6, "64:ff9b::5.6.7.8", &v6addr);
3195 result = gethostbyaddr(&v6addr, sizeof(v6addr), AF_INET6);
3196 ASSERT_TRUE(result != nullptr);
3197 EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v6_synthesis));
3198 result_str = result->h_name ? result->h_name : "null";
3199 EXPECT_EQ(result_str, "v6synthesis.example.com");
3200}
3201
3202TEST_F(ResolverTest, GetHostByAddr_ReverseDns64QueryFromHostFile) {
3203 constexpr char dns64_name[] = "ipv4only.arpa.";
3204 constexpr char host_name[] = "localhost";
3205 // The address is synthesized by prefix64:localhost.
3206 constexpr char host_addr[] = "64:ff9b::7f00:1";
nuccachena26cc2a2018-07-17 18:07:23 +08003207 constexpr char listen_addr[] = "::1";
Xiao Ma09b71022018-12-11 17:56:32 +09003208
3209 test::DNSResponder dns(listen_addr);
3210 StartDns(dns, {{dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"}});
nuccachena26cc2a2018-07-17 18:07:23 +08003211 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003212 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003213
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003214 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003215 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003216 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003217
3218 // Using synthesized "localhost" address to be a trick for resolving host name
3219 // from host file /etc/hosts and "localhost" is the only name in /etc/hosts. Note that this is
3220 // not realistic: the code never synthesizes AAAA records for addresses in 127.0.0.0/8.
3221 struct in6_addr v6addr;
3222 inet_pton(AF_INET6, host_addr, &v6addr);
3223 struct hostent* result = gethostbyaddr(&v6addr, sizeof(v6addr), AF_INET6);
3224 ASSERT_TRUE(result != nullptr);
3225 // Expect no DNS queries; localhost is resolved via /etc/hosts.
3226 EXPECT_EQ(0U, GetNumQueries(dns, host_name));
3227
Luke Huangf8215372019-11-22 11:53:41 +08003228 ASSERT_EQ(sizeof(in6_addr), (unsigned)result->h_length);
nuccachena26cc2a2018-07-17 18:07:23 +08003229 ASSERT_EQ(AF_INET6, result->h_addrtype);
3230 std::string result_str = ToString(result);
3231 EXPECT_EQ(result_str, host_addr);
3232 result_str = result->h_name ? result->h_name : "null";
3233 EXPECT_EQ(result_str, host_name);
3234}
3235
Hungming Chen9e6185a2019-06-04 16:09:19 +08003236TEST_F(ResolverTest, GetHostByAddr_cnamesClasslessReverseDelegation) {
3237 // IPv4 addresses in the subnet with notation '/' or '-'.
3238 constexpr char addr_slash[] = "192.0.2.1";
3239 constexpr char addr_hyphen[] = "192.0.3.1";
3240
3241 // Used to verify DNS reverse query for classless reverse lookup zone. See detail in RFC 2317
3242 // section 4.
3243 const static std::vector<DnsRecord> records = {
3244 // The records for reverse querying "192.0.2.1" in the subnet with notation '/'.
3245 {"1.2.0.192.in-addr.arpa.", ns_type::ns_t_cname, "1.0/25.2.0.192.in-addr.arpa."},
3246 {"1.0/25.2.0.192.in-addr.arpa.", ns_type::ns_t_ptr, kHelloExampleCom},
3247
3248 // The records for reverse querying "192.0.3.1" in the subnet with notation '-'.
3249 {"1.3.0.192.in-addr.arpa.", ns_type::ns_t_cname, "1.0-127.3.0.192.in-addr.arpa."},
3250 {"1.0-127.3.0.192.in-addr.arpa.", ns_type::ns_t_ptr, kHelloExampleCom},
3251 };
3252
3253 test::DNSResponder dns;
3254 StartDns(dns, records);
3255 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
3256
3257 for (const auto& address : {addr_slash, addr_hyphen}) {
3258 SCOPED_TRACE(address);
3259
3260 in_addr v4addr;
3261 ASSERT_TRUE(inet_pton(AF_INET, address, &v4addr));
3262 hostent* result = gethostbyaddr(&v4addr, sizeof(v4addr), AF_INET);
3263 ASSERT_TRUE(result != nullptr);
3264 EXPECT_STREQ("hello.example.com", result->h_name);
3265 }
3266}
3267
nuccachena26cc2a2018-07-17 18:07:23 +08003268TEST_F(ResolverTest, GetNameInfo_ReverseDnsQueryWithHavingNat64Prefix) {
3269 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08003270 constexpr char dns64_name[] = "ipv4only.arpa.";
3271 constexpr char ptr_name[] = "v4v6.example.com.";
3272 // PTR record for IPv4 address 1.2.3.4
3273 constexpr char ptr_addr_v4[] = "4.3.2.1.in-addr.arpa.";
3274 // PTR record for IPv6 address 2001:db8::102:304
3275 constexpr char ptr_addr_v6[] =
3276 "4.0.3.0.2.0.1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.8.b.d.0.1.0.0.2.ip6.arpa.";
Xiao Ma09b71022018-12-11 17:56:32 +09003277 const std::vector<DnsRecord> records = {
3278 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
3279 {ptr_addr_v4, ns_type::ns_t_ptr, ptr_name},
3280 {ptr_addr_v6, ns_type::ns_t_ptr, ptr_name},
3281 };
nuccachena26cc2a2018-07-17 18:07:23 +08003282
Xiao Ma09b71022018-12-11 17:56:32 +09003283 test::DNSResponder dns(listen_addr);
3284 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08003285 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003286 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003287
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003288 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003289 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003290 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003291
Luke Huangf8215372019-11-22 11:53:41 +08003292 // clang-format off
nuccachena26cc2a2018-07-17 18:07:23 +08003293 static const struct TestConfig {
3294 int flag;
3295 int family;
3296 std::string addr;
3297 std::string host;
3298
3299 std::string asParameters() const {
3300 return StringPrintf("flag=%d, family=%d, addr=%s, host=%s", flag, family, addr.c_str(),
3301 host.c_str());
3302 }
3303 } testConfigs[]{
3304 {NI_NAMEREQD, AF_INET, "1.2.3.4", "v4v6.example.com"},
3305 {NI_NUMERICHOST, AF_INET, "1.2.3.4", "1.2.3.4"},
3306 {0, AF_INET, "1.2.3.4", "v4v6.example.com"},
3307 {0, AF_INET, "5.6.7.8", "5.6.7.8"}, // unmapped
3308 {NI_NAMEREQD, AF_INET6, "2001:db8::102:304", "v4v6.example.com"},
3309 {NI_NUMERICHOST, AF_INET6, "2001:db8::102:304", "2001:db8::102:304"},
3310 {0, AF_INET6, "2001:db8::102:304", "v4v6.example.com"},
3311 {0, AF_INET6, "2001:db8::506:708", "2001:db8::506:708"}, // unmapped
3312 };
Luke Huangf8215372019-11-22 11:53:41 +08003313 // clang-format on
nuccachena26cc2a2018-07-17 18:07:23 +08003314
3315 // Reverse IPv4/IPv6 DNS query. Prefix should have no effect on it.
3316 for (const auto& config : testConfigs) {
3317 SCOPED_TRACE(config.asParameters());
3318
3319 int rv;
3320 char host[NI_MAXHOST];
3321 struct sockaddr_in sin;
3322 struct sockaddr_in6 sin6;
3323 if (config.family == AF_INET) {
3324 memset(&sin, 0, sizeof(sin));
3325 sin.sin_family = AF_INET;
3326 inet_pton(AF_INET, config.addr.c_str(), &sin.sin_addr);
Luke Huangf8215372019-11-22 11:53:41 +08003327 rv = getnameinfo((const struct sockaddr*)&sin, sizeof(sin), host, sizeof(host), nullptr,
3328 0, config.flag);
nuccachena26cc2a2018-07-17 18:07:23 +08003329 if (config.flag == NI_NAMEREQD) EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v4));
3330 } else if (config.family == AF_INET6) {
3331 memset(&sin6, 0, sizeof(sin6));
3332 sin6.sin6_family = AF_INET6;
3333 inet_pton(AF_INET6, config.addr.c_str(), &sin6.sin6_addr);
Luke Huangf8215372019-11-22 11:53:41 +08003334 rv = getnameinfo((const struct sockaddr*)&sin6, sizeof(sin6), host, sizeof(host),
nuccachena26cc2a2018-07-17 18:07:23 +08003335 nullptr, 0, config.flag);
3336 if (config.flag == NI_NAMEREQD) EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v6));
3337 }
3338 ASSERT_EQ(0, rv);
3339 std::string result_str = host;
3340 EXPECT_EQ(result_str, config.host);
3341 dns.clearQueries();
3342 }
3343}
3344
3345TEST_F(ResolverTest, GetNameInfo_ReverseDns64Query) {
3346 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08003347 constexpr char dns64_name[] = "ipv4only.arpa.";
3348 constexpr char ptr_name[] = "v4only.example.com.";
3349 // PTR record for IPv4 address 1.2.3.4
3350 constexpr char ptr_addr_v4[] = "4.3.2.1.in-addr.arpa.";
3351 // PTR record for IPv6 address 64:ff9b::1.2.3.4
3352 constexpr char ptr_addr_v6_nomapping[] =
3353 "4.0.3.0.2.0.1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.b.9.f.f.4.6.0.0.ip6.arpa.";
3354 constexpr char ptr_name_v6_synthesis[] = "v6synthesis.example.com.";
3355 // PTR record for IPv6 address 64:ff9b::5.6.7.8
3356 constexpr char ptr_addr_v6_synthesis[] =
3357 "8.0.7.0.6.0.5.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.b.9.f.f.4.6.0.0.ip6.arpa.";
Xiao Ma09b71022018-12-11 17:56:32 +09003358 const std::vector<DnsRecord> records = {
3359 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
3360 {ptr_addr_v4, ns_type::ns_t_ptr, ptr_name},
3361 {ptr_addr_v6_synthesis, ns_type::ns_t_ptr, ptr_name_v6_synthesis},
3362 };
nuccachena26cc2a2018-07-17 18:07:23 +08003363
Xiao Ma09b71022018-12-11 17:56:32 +09003364 test::DNSResponder dns(listen_addr);
3365 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08003366 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003367 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003368
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003369 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003370 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003371 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003372
Luke Huangf8215372019-11-22 11:53:41 +08003373 // clang-format off
nuccachena26cc2a2018-07-17 18:07:23 +08003374 static const struct TestConfig {
3375 bool hasSynthesizedPtrRecord;
3376 int flag;
3377 std::string addr;
3378 std::string host;
3379
3380 std::string asParameters() const {
3381 return StringPrintf("hasSynthesizedPtrRecord=%d, flag=%d, addr=%s, host=%s",
3382 hasSynthesizedPtrRecord, flag, addr.c_str(), host.c_str());
3383 }
3384 } testConfigs[]{
3385 {false, NI_NAMEREQD, "64:ff9b::102:304", "v4only.example.com"},
3386 {false, NI_NUMERICHOST, "64:ff9b::102:304", "64:ff9b::102:304"},
3387 {false, 0, "64:ff9b::102:304", "v4only.example.com"},
3388 {true, NI_NAMEREQD, "64:ff9b::506:708", "v6synthesis.example.com"},
3389 {true, NI_NUMERICHOST, "64:ff9b::506:708", "64:ff9b::506:708"},
3390 {true, 0, "64:ff9b::506:708", "v6synthesis.example.com"}
3391 };
Luke Huangf8215372019-11-22 11:53:41 +08003392 // clang-format on
nuccachena26cc2a2018-07-17 18:07:23 +08003393
3394 // hasSynthesizedPtrRecord = false
3395 // Synthesized PTR record doesn't exist on DNS server
3396 // Reverse IPv6 DNS64 query while DNS server doesn't have an answer for synthesized address.
3397 // After querying synthesized address failed, expect that prefix is removed from IPv6
3398 // synthesized address and do reverse IPv4 query instead.
3399 //
3400 // hasSynthesizedPtrRecord = true
3401 // Synthesized PTR record exists on DNS server
3402 // Reverse IPv6 DNS64 query while DNS server has an answer for synthesized address.
3403 // Expect to just pass through synthesized address for DNS queries.
3404 for (const auto& config : testConfigs) {
3405 SCOPED_TRACE(config.asParameters());
3406
3407 char host[NI_MAXHOST];
3408 struct sockaddr_in6 sin6;
3409 memset(&sin6, 0, sizeof(sin6));
3410 sin6.sin6_family = AF_INET6;
3411 inet_pton(AF_INET6, config.addr.c_str(), &sin6.sin6_addr);
Luke Huangf8215372019-11-22 11:53:41 +08003412 int rv = getnameinfo((const struct sockaddr*)&sin6, sizeof(sin6), host, sizeof(host),
nuccachena26cc2a2018-07-17 18:07:23 +08003413 nullptr, 0, config.flag);
3414 ASSERT_EQ(0, rv);
3415 if (config.flag == NI_NAMEREQD) {
3416 if (config.hasSynthesizedPtrRecord) {
3417 EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v6_synthesis));
3418 } else {
3419 EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v6_nomapping)); // PTR record not exist.
3420 EXPECT_LE(1U, GetNumQueries(dns, ptr_addr_v4)); // PTR record exist.
3421 }
3422 }
3423 std::string result_str = host;
3424 EXPECT_EQ(result_str, config.host);
3425 dns.clearQueries();
3426 }
3427}
3428
3429TEST_F(ResolverTest, GetNameInfo_ReverseDns64QueryFromHostFile) {
3430 constexpr char dns64_name[] = "ipv4only.arpa.";
3431 constexpr char host_name[] = "localhost";
3432 // The address is synthesized by prefix64:localhost.
3433 constexpr char host_addr[] = "64:ff9b::7f00:1";
nuccachena26cc2a2018-07-17 18:07:23 +08003434 constexpr char listen_addr[] = "::1";
Xiao Ma09b71022018-12-11 17:56:32 +09003435
3436 test::DNSResponder dns(listen_addr);
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09003437
Xiao Ma09b71022018-12-11 17:56:32 +09003438 StartDns(dns, {{dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"}});
nuccachena26cc2a2018-07-17 18:07:23 +08003439 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003440 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003441
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003442 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003443 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003444 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003445
3446 // Using synthesized "localhost" address to be a trick for resolving host name
3447 // from host file /etc/hosts and "localhost" is the only name in /etc/hosts. Note that this is
3448 // not realistic: the code never synthesizes AAAA records for addresses in 127.0.0.0/8.
3449 char host[NI_MAXHOST];
Xiao Ma09b71022018-12-11 17:56:32 +09003450 struct sockaddr_in6 sin6 = {.sin6_family = AF_INET6};
nuccachena26cc2a2018-07-17 18:07:23 +08003451 inet_pton(AF_INET6, host_addr, &sin6.sin6_addr);
Luke Huangf8215372019-11-22 11:53:41 +08003452 int rv = getnameinfo((const struct sockaddr*)&sin6, sizeof(sin6), host, sizeof(host), nullptr,
nuccachena26cc2a2018-07-17 18:07:23 +08003453 0, NI_NAMEREQD);
3454 ASSERT_EQ(0, rv);
3455 // Expect no DNS queries; localhost is resolved via /etc/hosts.
3456 EXPECT_EQ(0U, GetNumQueries(dns, host_name));
3457
3458 std::string result_str = host;
3459 EXPECT_EQ(result_str, host_name);
3460}
3461
Hungming Chen9e6185a2019-06-04 16:09:19 +08003462TEST_F(ResolverTest, GetNameInfo_cnamesClasslessReverseDelegation) {
3463 // IPv4 addresses in the subnet with notation '/' or '-'.
3464 constexpr char addr_slash[] = "192.0.2.1";
3465 constexpr char addr_hyphen[] = "192.0.3.1";
3466
3467 // Used to verify DNS reverse query for classless reverse lookup zone. See detail in RFC 2317
3468 // section 4.
3469 const static std::vector<DnsRecord> records = {
3470 // The records for reverse querying "192.0.2.1" in the subnet with notation '/'.
3471 {"1.2.0.192.in-addr.arpa.", ns_type::ns_t_cname, "1.0/25.2.0.192.in-addr.arpa."},
3472 {"1.0/25.2.0.192.in-addr.arpa.", ns_type::ns_t_ptr, kHelloExampleCom},
3473
3474 // The records for reverse querying "192.0.3.1" in the subnet with notation '-'.
3475 {"1.3.0.192.in-addr.arpa.", ns_type::ns_t_cname, "1.0-127.3.0.192.in-addr.arpa."},
3476 {"1.0-127.3.0.192.in-addr.arpa.", ns_type::ns_t_ptr, kHelloExampleCom},
3477 };
3478
3479 test::DNSResponder dns;
3480 StartDns(dns, records);
3481 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
3482
3483 for (const auto& address : {addr_slash, addr_hyphen}) {
3484 SCOPED_TRACE(address);
3485
3486 char host[NI_MAXHOST];
3487 sockaddr_in sin = {.sin_family = AF_INET};
3488 ASSERT_TRUE(inet_pton(AF_INET, address, &sin.sin_addr));
3489 int rv = getnameinfo((const sockaddr*)&sin, sizeof(sin), host, sizeof(host), nullptr, 0,
3490 NI_NAMEREQD);
3491 ASSERT_EQ(0, rv);
3492 EXPECT_STREQ("hello.example.com", host);
3493 }
3494}
3495
nuccachena26cc2a2018-07-17 18:07:23 +08003496TEST_F(ResolverTest, GetHostByName2_Dns64Synthesize) {
Xiao Ma09b71022018-12-11 17:56:32 +09003497 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08003498 constexpr char dns64_name[] = "ipv4only.arpa.";
3499 constexpr char host_name[] = "ipv4only.example.com.";
Xiao Ma09b71022018-12-11 17:56:32 +09003500 const std::vector<DnsRecord> records = {
3501 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
3502 {host_name, ns_type::ns_t_a, "1.2.3.4"},
3503 };
nuccachena26cc2a2018-07-17 18:07:23 +08003504
Xiao Ma09b71022018-12-11 17:56:32 +09003505 test::DNSResponder dns(listen_addr);
3506 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08003507 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003508 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003509
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003510 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003511 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003512 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003513
3514 // Query an IPv4-only hostname. Expect that gets a synthesized address.
3515 struct hostent* result = gethostbyname2("ipv4only", AF_INET6);
3516 ASSERT_TRUE(result != nullptr);
3517 EXPECT_LE(1U, GetNumQueries(dns, host_name));
3518 std::string result_str = ToString(result);
3519 EXPECT_EQ(result_str, "64:ff9b::102:304");
3520}
nuccachena26cc2a2018-07-17 18:07:23 +08003521
3522TEST_F(ResolverTest, GetHostByName2_DnsQueryWithHavingNat64Prefix) {
3523 constexpr char dns64_name[] = "ipv4only.arpa.";
3524 constexpr char host_name[] = "v4v6.example.com.";
nuccachena26cc2a2018-07-17 18:07:23 +08003525 constexpr char listen_addr[] = "::1";
Xiao Ma09b71022018-12-11 17:56:32 +09003526 const std::vector<DnsRecord> records = {
3527 {dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"},
3528 {host_name, ns_type::ns_t_a, "1.2.3.4"},
3529 {host_name, ns_type::ns_t_aaaa, "2001:db8::1.2.3.4"},
3530 };
3531
3532 test::DNSResponder dns(listen_addr);
3533 StartDns(dns, records);
nuccachena26cc2a2018-07-17 18:07:23 +08003534 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003535 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003536
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003537 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003538 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003539 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003540
3541 // IPv4 DNS query. Prefix should have no effect on it.
3542 struct hostent* result = gethostbyname2("v4v6", AF_INET);
3543 ASSERT_TRUE(result != nullptr);
3544 EXPECT_LE(1U, GetNumQueries(dns, host_name));
3545 std::string result_str = ToString(result);
3546 EXPECT_EQ(result_str, "1.2.3.4");
3547 dns.clearQueries();
3548
3549 // IPv6 DNS query. Prefix should have no effect on it.
3550 result = gethostbyname2("v4v6", AF_INET6);
3551 ASSERT_TRUE(result != nullptr);
3552 EXPECT_LE(1U, GetNumQueries(dns, host_name));
3553 result_str = ToString(result);
3554 EXPECT_EQ(result_str, "2001:db8::102:304");
3555}
3556
3557TEST_F(ResolverTest, GetHostByName2_Dns64QuerySpecialUseIPv4Addresses) {
3558 constexpr char THIS_NETWORK[] = "this_network";
3559 constexpr char LOOPBACK[] = "loopback";
3560 constexpr char LINK_LOCAL[] = "link_local";
3561 constexpr char MULTICAST[] = "multicast";
3562 constexpr char LIMITED_BROADCAST[] = "limited_broadcast";
3563
3564 constexpr char ADDR_THIS_NETWORK[] = "0.0.0.1";
3565 constexpr char ADDR_LOOPBACK[] = "127.0.0.1";
3566 constexpr char ADDR_LINK_LOCAL[] = "169.254.0.1";
3567 constexpr char ADDR_MULTICAST[] = "224.0.0.1";
3568 constexpr char ADDR_LIMITED_BROADCAST[] = "255.255.255.255";
3569
3570 constexpr char listen_addr[] = "::1";
nuccachena26cc2a2018-07-17 18:07:23 +08003571 constexpr char dns64_name[] = "ipv4only.arpa.";
3572
Xiao Ma09b71022018-12-11 17:56:32 +09003573 test::DNSResponder dns(listen_addr);
3574 StartDns(dns, {{dns64_name, ns_type::ns_t_aaaa, "64:ff9b::"}});
nuccachena26cc2a2018-07-17 18:07:23 +08003575 const std::vector<std::string> servers = {listen_addr};
Xiao Ma09b71022018-12-11 17:56:32 +09003576 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
nuccachena26cc2a2018-07-17 18:07:23 +08003577
Lorenzo Colittid39345c2019-02-18 10:59:29 +09003578 // Start NAT64 prefix discovery and wait for it to complete.
Luke Huang5bd827c2019-03-14 16:10:04 +08003579 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003580 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
nuccachena26cc2a2018-07-17 18:07:23 +08003581
Luke Huangf8215372019-11-22 11:53:41 +08003582 // clang-format off
nuccachena26cc2a2018-07-17 18:07:23 +08003583 static const struct TestConfig {
3584 std::string name;
3585 std::string addr;
3586
3587 std::string asHostName() const {
Luke Huangf8215372019-11-22 11:53:41 +08003588 return StringPrintf("%s.example.com.", name.c_str());
nuccachena26cc2a2018-07-17 18:07:23 +08003589 }
3590 } testConfigs[]{
3591 {THIS_NETWORK, ADDR_THIS_NETWORK},
3592 {LOOPBACK, ADDR_LOOPBACK},
3593 {LINK_LOCAL, ADDR_LINK_LOCAL},
3594 {MULTICAST, ADDR_MULTICAST},
3595 {LIMITED_BROADCAST, ADDR_LIMITED_BROADCAST}
3596 };
Luke Huangf8215372019-11-22 11:53:41 +08003597 // clang-format on
nuccachena26cc2a2018-07-17 18:07:23 +08003598
3599 for (const auto& config : testConfigs) {
3600 const std::string testHostName = config.asHostName();
3601 SCOPED_TRACE(testHostName);
3602
3603 const char* host_name = testHostName.c_str();
3604 dns.addMapping(host_name, ns_type::ns_t_a, config.addr.c_str());
3605
3606 struct hostent* result = gethostbyname2(config.name.c_str(), AF_INET6);
3607 EXPECT_LE(1U, GetNumQueries(dns, host_name));
3608
3609 // In AF_INET6 case, don't synthesize special use IPv4 address.
3610 // Expect to have no answer
3611 EXPECT_EQ(nullptr, result);
3612
3613 dns.clearQueries();
3614 }
Bernie Innocenti2fef2b82018-12-20 15:56:40 +09003615}
Mike Yuf14e1a92019-05-10 13:54:58 +08003616
3617TEST_F(ResolverTest, PrefixDiscoveryBypassTls) {
3618 constexpr char listen_addr[] = "::1";
3619 constexpr char cleartext_port[] = "53";
3620 constexpr char tls_port[] = "853";
3621 constexpr char dns64_name[] = "ipv4only.arpa.";
3622 const std::vector<std::string> servers = {listen_addr};
3623
3624 test::DNSResponder dns(listen_addr);
3625 StartDns(dns, {{dns64_name, ns_type::ns_t_aaaa, "64:ff9b::192.0.0.170"}});
3626 test::DnsTlsFrontend tls(listen_addr, tls_port, listen_addr, cleartext_port);
3627 ASSERT_TRUE(tls.startServer());
3628
3629 // Setup OPPORTUNISTIC mode and wait for the validation complete.
waynema0e73c2e2019-07-31 15:04:08 +08003630 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams, ""));
Mike Yu724f77d2019-08-16 11:14:50 +08003631 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09003632 EXPECT_TRUE(tls.waitForQueries(1));
Mike Yuf14e1a92019-05-10 13:54:58 +08003633 tls.clearQueries();
3634
3635 // Start NAT64 prefix discovery and wait for it complete.
3636 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003637 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
Mike Yuf14e1a92019-05-10 13:54:58 +08003638
3639 // Verify it bypassed TLS even though there's a TLS server available.
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09003640 EXPECT_EQ(0, tls.queries()) << dns.dumpQueries();
3641 EXPECT_EQ(1U, GetNumQueries(dns, dns64_name)) << dns.dumpQueries();
Mike Yuf14e1a92019-05-10 13:54:58 +08003642
3643 // Restart the testing network to reset the cache.
3644 mDnsClient.TearDown();
3645 mDnsClient.SetUp();
3646 dns.clearQueries();
3647
3648 // Setup STRICT mode and wait for the validation complete.
waynema0e73c2e2019-07-31 15:04:08 +08003649 ASSERT_TRUE(mDnsClient.SetResolversWithTls(servers, kDefaultSearchDomains, kDefaultParams,
3650 kDefaultPrivateDnsHostName));
Mike Yu724f77d2019-08-16 11:14:50 +08003651 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09003652 EXPECT_TRUE(tls.waitForQueries(1));
Mike Yuf14e1a92019-05-10 13:54:58 +08003653 tls.clearQueries();
3654
3655 // Start NAT64 prefix discovery and wait for it to complete.
3656 EXPECT_TRUE(mDnsClient.resolvService()->startPrefix64Discovery(TEST_NETID).isOk());
Hungming Chene8f970c2019-04-10 17:34:06 +08003657 EXPECT_TRUE(WaitForNat64Prefix(EXPECT_FOUND));
Mike Yuf14e1a92019-05-10 13:54:58 +08003658
3659 // Verify it bypassed TLS despite STRICT mode.
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09003660 EXPECT_EQ(0, tls.queries()) << dns.dumpQueries();
3661 EXPECT_EQ(1U, GetNumQueries(dns, dns64_name)) << dns.dumpQueries();
Mike Yuf14e1a92019-05-10 13:54:58 +08003662}
Luke Huang9807e6b2019-05-20 16:17:12 +08003663
3664namespace {
3665
Luke Huang0d592bc2019-05-25 18:24:03 +08003666class ScopedSetNetworkForProcess {
3667 public:
3668 explicit ScopedSetNetworkForProcess(unsigned netId) {
3669 mStoredNetId = getNetworkForProcess();
3670 if (netId == mStoredNetId) return;
3671 EXPECT_EQ(0, setNetworkForProcess(netId));
3672 }
3673 ~ScopedSetNetworkForProcess() { EXPECT_EQ(0, setNetworkForProcess(mStoredNetId)); }
3674
3675 private:
3676 unsigned mStoredNetId;
3677};
3678
3679class ScopedSetNetworkForResolv {
3680 public:
3681 explicit ScopedSetNetworkForResolv(unsigned netId) { EXPECT_EQ(0, setNetworkForResolv(netId)); }
3682 ~ScopedSetNetworkForResolv() { EXPECT_EQ(0, setNetworkForResolv(NETID_UNSET)); }
3683};
3684
Luke Huang9807e6b2019-05-20 16:17:12 +08003685void sendCommand(int fd, const std::string& cmd) {
3686 ssize_t rc = TEMP_FAILURE_RETRY(write(fd, cmd.c_str(), cmd.size() + 1));
3687 EXPECT_EQ(rc, static_cast<ssize_t>(cmd.size() + 1));
3688}
3689
3690int32_t readBE32(int fd) {
3691 int32_t tmp;
3692 int n = TEMP_FAILURE_RETRY(read(fd, &tmp, sizeof(tmp)));
3693 EXPECT_TRUE(n > 0);
3694 return ntohl(tmp);
3695}
3696
Luke Huang0d592bc2019-05-25 18:24:03 +08003697int readResponseCode(int fd) {
Luke Huang9807e6b2019-05-20 16:17:12 +08003698 char buf[4];
3699 int n = TEMP_FAILURE_RETRY(read(fd, &buf, sizeof(buf)));
3700 EXPECT_TRUE(n > 0);
3701 // The format of response code is that 4 bytes for the code & null.
3702 buf[3] = '\0';
3703 int result;
3704 EXPECT_TRUE(ParseInt(buf, &result));
3705 return result;
3706}
3707
Luke Huang0d592bc2019-05-25 18:24:03 +08003708bool checkAndClearUseLocalNameserversFlag(unsigned* netid) {
3709 if (netid == nullptr || ((*netid) & NETID_USE_LOCAL_NAMESERVERS) == 0) {
3710 return false;
3711 }
3712 *netid = (*netid) & ~NETID_USE_LOCAL_NAMESERVERS;
3713 return true;
3714}
3715
Luke Huangf8215372019-11-22 11:53:41 +08003716aidl::android::net::UidRangeParcel makeUidRangeParcel(int start, int stop) {
3717 aidl::android::net::UidRangeParcel res;
Luke Huang0d592bc2019-05-25 18:24:03 +08003718 res.start = start;
3719 res.stop = stop;
3720
3721 return res;
3722}
3723
3724void expectNetIdWithLocalNameserversFlag(unsigned netId) {
3725 unsigned dnsNetId = 0;
3726 EXPECT_EQ(0, getNetworkForDns(&dnsNetId));
3727 EXPECT_TRUE(checkAndClearUseLocalNameserversFlag(&dnsNetId));
3728 EXPECT_EQ(netId, static_cast<unsigned>(dnsNetId));
3729}
3730
3731void expectDnsNetIdEquals(unsigned netId) {
3732 unsigned dnsNetId = 0;
3733 EXPECT_EQ(0, getNetworkForDns(&dnsNetId));
3734 EXPECT_EQ(netId, static_cast<unsigned>(dnsNetId));
3735}
3736
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +09003737void expectDnsNetIdIsDefaultNetwork(INetd* netdService) {
Luke Huang0d592bc2019-05-25 18:24:03 +08003738 int currentNetid;
3739 EXPECT_TRUE(netdService->networkGetDefault(&currentNetid).isOk());
3740 expectDnsNetIdEquals(currentNetid);
3741}
3742
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +09003743void expectDnsNetIdWithVpn(INetd* netdService, unsigned vpnNetId, unsigned expectedNetId) {
Luke Huang0d592bc2019-05-25 18:24:03 +08003744 EXPECT_TRUE(netdService->networkCreateVpn(vpnNetId, false /* secure */).isOk());
3745 uid_t uid = getuid();
3746 // Add uid to VPN
3747 EXPECT_TRUE(netdService->networkAddUidRanges(vpnNetId, {makeUidRangeParcel(uid, uid)}).isOk());
3748 expectDnsNetIdEquals(expectedNetId);
3749 EXPECT_TRUE(netdService->networkDestroy(vpnNetId).isOk());
3750}
3751
Luke Huang9807e6b2019-05-20 16:17:12 +08003752} // namespace
3753
3754TEST_F(ResolverTest, getDnsNetId) {
3755 // We've called setNetworkForProcess in SetupOemNetwork, so reset to default first.
3756 setNetworkForProcess(NETID_UNSET);
Luke Huang0d592bc2019-05-25 18:24:03 +08003757
3758 expectDnsNetIdIsDefaultNetwork(mDnsClient.netdService());
3759 expectDnsNetIdWithVpn(mDnsClient.netdService(), TEST_VPN_NETID, TEST_VPN_NETID);
Luke Huang9807e6b2019-05-20 16:17:12 +08003760
3761 // Test with setNetworkForProcess
Luke Huang0d592bc2019-05-25 18:24:03 +08003762 {
3763 ScopedSetNetworkForProcess scopedSetNetworkForProcess(TEST_NETID);
3764 expectDnsNetIdEquals(TEST_NETID);
3765 }
3766
3767 // Test with setNetworkForProcess with NETID_USE_LOCAL_NAMESERVERS
3768 {
3769 ScopedSetNetworkForProcess scopedSetNetworkForProcess(TEST_NETID |
3770 NETID_USE_LOCAL_NAMESERVERS);
3771 expectNetIdWithLocalNameserversFlag(TEST_NETID);
3772 }
Luke Huang9807e6b2019-05-20 16:17:12 +08003773
3774 // Test with setNetworkForResolv
Luke Huang0d592bc2019-05-25 18:24:03 +08003775 {
3776 ScopedSetNetworkForResolv scopedSetNetworkForResolv(TEST_NETID);
3777 expectDnsNetIdEquals(TEST_NETID);
3778 }
3779
3780 // Test with setNetworkForResolv with NETID_USE_LOCAL_NAMESERVERS
3781 {
3782 ScopedSetNetworkForResolv scopedSetNetworkForResolv(TEST_NETID |
3783 NETID_USE_LOCAL_NAMESERVERS);
3784 expectNetIdWithLocalNameserversFlag(TEST_NETID);
3785 }
3786
3787 // Test with setNetworkForResolv under bypassable vpn
3788 {
3789 ScopedSetNetworkForResolv scopedSetNetworkForResolv(TEST_NETID);
3790 expectDnsNetIdWithVpn(mDnsClient.netdService(), TEST_VPN_NETID, TEST_NETID);
3791 }
Luke Huang9807e6b2019-05-20 16:17:12 +08003792
3793 // Create socket connected to DnsProxyListener
3794 int fd = dns_open_proxy();
3795 EXPECT_TRUE(fd > 0);
3796 unique_fd ufd(fd);
3797
3798 // Test command with wrong netId
3799 sendCommand(fd, "getdnsnetid abc");
Luke Huang0d592bc2019-05-25 18:24:03 +08003800 EXPECT_EQ(ResponseCode::DnsProxyQueryResult, readResponseCode(fd));
Luke Huang9807e6b2019-05-20 16:17:12 +08003801 EXPECT_EQ(-EINVAL, readBE32(fd));
3802
3803 // Test unsupported command
3804 sendCommand(fd, "getdnsnetidNotSupported");
3805 // Keep in sync with FrameworkListener.cpp (500, "Command not recognized")
Luke Huang0d592bc2019-05-25 18:24:03 +08003806 EXPECT_EQ(500, readResponseCode(fd));
Luke Huang9807e6b2019-05-20 16:17:12 +08003807}
Sehee Park2c118782019-05-07 13:02:45 +09003808
3809TEST_F(ResolverTest, BlockDnsQueryWithUidRule) {
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +09003810 // This test relies on blocking traffic on loopback, which xt_qtaguid does not do.
3811 // See aosp/358413 and b/34444781 for why.
3812 SKIP_IF_BPF_NOT_SUPPORTED;
3813
Sehee Park2c118782019-05-07 13:02:45 +09003814 constexpr char listen_addr1[] = "127.0.0.4";
3815 constexpr char listen_addr2[] = "::1";
3816 constexpr char host_name[] = "howdy.example.com.";
3817 const std::vector<DnsRecord> records = {
3818 {host_name, ns_type::ns_t_a, "1.2.3.4"},
3819 {host_name, ns_type::ns_t_aaaa, "::1.2.3.4"},
3820 };
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +09003821 INetd* netdService = mDnsClient.netdService();
Sehee Park2c118782019-05-07 13:02:45 +09003822
3823 test::DNSResponder dns1(listen_addr1);
3824 test::DNSResponder dns2(listen_addr2);
3825 StartDns(dns1, records);
3826 StartDns(dns2, records);
3827
3828 std::vector<std::string> servers = {listen_addr1, listen_addr2};
3829 ASSERT_TRUE(mDnsClient.SetResolversForNetwork(servers));
3830 dns1.clearQueries();
3831 dns2.clearQueries();
3832
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +09003833 // Add drop rule for TEST_UID. Also enable the standby chain because it might not be enabled.
3834 // Unfortunately we cannot use FIREWALL_CHAIN_NONE, or custom iptables rules, for this purpose
3835 // because netd calls fchown() on the DNS query sockets, and "iptables -m owner" matches the
3836 // UID of the socket creator, not the UID set by fchown().
3837 //
3838 // TODO: migrate FIREWALL_CHAIN_NONE to eBPF as well.
3839 EXPECT_TRUE(netdService->firewallEnableChildChain(INetd::FIREWALL_CHAIN_STANDBY, true).isOk());
3840 EXPECT_TRUE(netdService
Sehee Park2c118782019-05-07 13:02:45 +09003841 ->firewallSetUidRule(INetd::FIREWALL_CHAIN_STANDBY, TEST_UID,
3842 INetd::FIREWALL_RULE_DENY)
3843 .isOk());
3844
3845 // Save uid
3846 int suid = getuid();
3847
3848 // Switch to TEST_UID
3849 EXPECT_TRUE(seteuid(TEST_UID) == 0);
3850
3851 // Dns Query
3852 int fd1 = resNetworkQuery(TEST_NETID, host_name, ns_c_in, ns_t_a, 0);
3853 int fd2 = resNetworkQuery(TEST_NETID, host_name, ns_c_in, ns_t_aaaa, 0);
3854 EXPECT_TRUE(fd1 != -1);
3855 EXPECT_TRUE(fd2 != -1);
3856
3857 uint8_t buf[MAXPACKET] = {};
3858 int rcode;
3859 int res = getAsyncResponse(fd2, &rcode, buf, MAXPACKET);
3860 EXPECT_EQ(-ECONNREFUSED, res);
3861
3862 memset(buf, 0, MAXPACKET);
3863 res = getAsyncResponse(fd1, &rcode, buf, MAXPACKET);
3864 EXPECT_EQ(-ECONNREFUSED, res);
3865
3866 // Restore uid
3867 EXPECT_TRUE(seteuid(suid) == 0);
3868
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +09003869 // Remove drop rule for TEST_UID, and disable the standby chain.
3870 EXPECT_TRUE(netdService
Sehee Park2c118782019-05-07 13:02:45 +09003871 ->firewallSetUidRule(INetd::FIREWALL_CHAIN_STANDBY, TEST_UID,
3872 INetd::FIREWALL_RULE_ALLOW)
3873 .isOk());
Lorenzo Colittieb9aeec2019-06-26 19:53:55 +09003874 EXPECT_TRUE(netdService->firewallEnableChildChain(INetd::FIREWALL_CHAIN_STANDBY, false).isOk());
Sehee Park2c118782019-05-07 13:02:45 +09003875}
Mike Yua772c202019-09-23 17:47:21 +08003876
Mike Yu40e67072019-10-09 21:14:09 +08003877namespace {
3878
3879const std::string kDotConnectTimeoutMsFlag(
3880 "persist.device_config.netd_native.dot_connect_timeout_ms");
3881
3882class ScopedSystemProperties {
3883 public:
3884 explicit ScopedSystemProperties(const std::string& key, const std::string& value)
3885 : mStoredKey(key) {
3886 mStoredValue = android::base::GetProperty(key, "");
3887 android::base::SetProperty(key, value);
3888 }
3889 ~ScopedSystemProperties() { android::base::SetProperty(mStoredKey, mStoredValue); }
3890
3891 private:
3892 std::string mStoredKey;
3893 std::string mStoredValue;
3894};
3895
3896} // namespace
3897
Mike Yua772c202019-09-23 17:47:21 +08003898TEST_F(ResolverTest, ConnectTlsServerTimeout) {
Mike Yu40e67072019-10-09 21:14:09 +08003899 constexpr int expectedTimeout = 1000;
3900 constexpr char hostname1[] = "query1.example.com.";
3901 constexpr char hostname2[] = "query2.example.com.";
Mike Yua772c202019-09-23 17:47:21 +08003902 const std::vector<DnsRecord> records = {
Mike Yu40e67072019-10-09 21:14:09 +08003903 {hostname1, ns_type::ns_t_a, "1.2.3.4"},
3904 {hostname2, ns_type::ns_t_a, "1.2.3.5"},
Mike Yua772c202019-09-23 17:47:21 +08003905 };
3906
3907 test::DNSResponder dns;
3908 StartDns(dns, records);
Mike Yu40e67072019-10-09 21:14:09 +08003909 test::DnsTlsFrontend tls;
Mike Yua772c202019-09-23 17:47:21 +08003910 ASSERT_TRUE(tls.startServer());
3911
Mike Yu40e67072019-10-09 21:14:09 +08003912 // The resolver will adjust the timeout value to 1000ms since the value is too small.
3913 ScopedSystemProperties scopedSystemProperties(kDotConnectTimeoutMsFlag, "100");
Mike Yua772c202019-09-23 17:47:21 +08003914
Mike Yu40e67072019-10-09 21:14:09 +08003915 // Set up resolver to opportunistic mode with the default configuration.
Mike Yu8ac63402019-12-02 15:28:38 +08003916 const ResolverParamsParcel parcel = DnsResponderClient::GetDefaultResolverParamsParcel();
Mike Yu40e67072019-10-09 21:14:09 +08003917 ASSERT_TRUE(mDnsClient.SetResolversFromParcel(parcel));
Mike Yua772c202019-09-23 17:47:21 +08003918 EXPECT_TRUE(WaitForPrivateDnsValidation(tls.listen_address(), true));
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09003919 EXPECT_TRUE(tls.waitForQueries(1));
Mike Yua772c202019-09-23 17:47:21 +08003920 tls.clearQueries();
Bernie Innocenti0ad80e92020-01-23 22:20:44 +09003921 dns.clearQueries();
Mike Yua772c202019-09-23 17:47:21 +08003922
3923 // The server becomes unresponsive to the handshake request.
3924 tls.setHangOnHandshakeForTesting(true);
3925
3926 // Expect the things happening in getaddrinfo():
3927 // 1. Connect to the private DNS server.
3928 // 2. SSL handshake times out.
3929 // 3. Fallback to UDP transport, and then get the answer.
Mike Yu40e67072019-10-09 21:14:09 +08003930 const addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
3931 auto [result, timeTakenMs] = safe_getaddrinfo_time_taken(hostname1, nullptr, hints);
Mike Yua772c202019-09-23 17:47:21 +08003932
Mike Yu40e67072019-10-09 21:14:09 +08003933 EXPECT_NE(nullptr, result);
Mike Yua772c202019-09-23 17:47:21 +08003934 EXPECT_EQ(0, tls.queries());
Mike Yu40e67072019-10-09 21:14:09 +08003935 EXPECT_EQ(1U, GetNumQueries(dns, hostname1));
3936 EXPECT_EQ(records.at(0).addr, ToString(result));
Mike Yua772c202019-09-23 17:47:21 +08003937
Mike Yu40e67072019-10-09 21:14:09 +08003938 // A loose upper bound is set by adding 2000ms buffer time. Theoretically, getaddrinfo()
3939 // should just take a bit more than expetTimeout milliseconds.
3940 EXPECT_GE(timeTakenMs, expectedTimeout);
3941 EXPECT_LE(timeTakenMs, expectedTimeout + 2000);
3942
3943 // Set the server to be responsive. Verify that the resolver will attempt to reconnect
3944 // to the server and then get the result within the timeout.
3945 tls.setHangOnHandshakeForTesting(false);
3946 std::tie(result, timeTakenMs) = safe_getaddrinfo_time_taken(hostname2, nullptr, hints);
3947
3948 EXPECT_NE(nullptr, result);
3949 EXPECT_EQ(1, tls.queries());
3950 EXPECT_EQ(1U, GetNumQueries(dns, hostname2));
3951 EXPECT_EQ(records.at(1).addr, ToString(result));
3952
3953 EXPECT_LE(timeTakenMs, expectedTimeout);
Mike Yua772c202019-09-23 17:47:21 +08003954}
Hungming Chenbb90ab32019-10-28 18:20:31 +08003955
Ken Chen766feae2019-10-30 15:13:44 +08003956TEST_F(ResolverTest, FlushNetworkCache) {
Luke Huang0b5a76c2019-11-23 03:00:00 +08003957 SKIP_IF_REMOTE_VERSION_LESS_THAN(mDnsClient.resolvService(), 4);
Ken Chen766feae2019-10-30 15:13:44 +08003958 test::DNSResponder dns;
3959 StartDns(dns, {{kHelloExampleCom, ns_type::ns_t_a, kHelloExampleComAddrV4}});
3960 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
3961
3962 const hostent* result = gethostbyname("hello");
3963 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, kHelloExampleCom));
3964
3965 // get result from cache
3966 result = gethostbyname("hello");
3967 EXPECT_EQ(1U, GetNumQueriesForType(dns, ns_type::ns_t_a, kHelloExampleCom));
3968
3969 EXPECT_TRUE(mDnsClient.resolvService()->flushNetworkCache(TEST_NETID).isOk());
3970
3971 result = gethostbyname("hello");
3972 EXPECT_EQ(2U, GetNumQueriesForType(dns, ns_type::ns_t_a, kHelloExampleCom));
3973}
3974
3975TEST_F(ResolverTest, FlushNetworkCache_random) {
Luke Huang0b5a76c2019-11-23 03:00:00 +08003976 SKIP_IF_REMOTE_VERSION_LESS_THAN(mDnsClient.resolvService(), 4);
Ken Chen766feae2019-10-30 15:13:44 +08003977 constexpr int num_flush = 10;
3978 constexpr int num_queries = 20;
3979 test::DNSResponder dns;
3980 StartDns(dns, {{kHelloExampleCom, ns_type::ns_t_a, kHelloExampleComAddrV4}});
3981 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
3982 const addrinfo hints = {.ai_family = AF_INET};
3983
3984 std::thread t([this]() {
3985 for (int i = 0; i < num_flush; ++i) {
3986 unsigned delay = arc4random_uniform(10 * 1000); // 10ms
3987 usleep(delay);
3988 EXPECT_TRUE(mDnsClient.resolvService()->flushNetworkCache(TEST_NETID).isOk());
3989 }
3990 });
3991
3992 for (int i = 0; i < num_queries; ++i) {
3993 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
3994 EXPECT_TRUE(result != nullptr);
3995 EXPECT_EQ(kHelloExampleComAddrV4, ToString(result));
3996 }
3997 t.join();
3998}
3999
4000// flush cache while one query is wait-for-response, another is pending.
4001TEST_F(ResolverTest, FlushNetworkCache_concurrent) {
Luke Huang0b5a76c2019-11-23 03:00:00 +08004002 SKIP_IF_REMOTE_VERSION_LESS_THAN(mDnsClient.resolvService(), 4);
Ken Chen766feae2019-10-30 15:13:44 +08004003 const char* listen_addr1 = "127.0.0.9";
4004 const char* listen_addr2 = "127.0.0.10";
4005 test::DNSResponder dns1(listen_addr1);
4006 test::DNSResponder dns2(listen_addr2);
4007 StartDns(dns1, {{kHelloExampleCom, ns_type::ns_t_a, kHelloExampleComAddrV4}});
4008 StartDns(dns2, {{kHelloExampleCom, ns_type::ns_t_a, kHelloExampleComAddrV4}});
4009 addrinfo hints = {.ai_family = AF_INET};
4010
4011 // step 1: set server#1 into deferred responding mode
4012 dns1.setDeferredResp(true);
4013 std::thread t1([&listen_addr1, &hints, this]() {
4014 ASSERT_TRUE(mDnsClient.SetResolversForNetwork({listen_addr1}));
4015 // step 3: query
4016 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
4017 // step 9: check result
4018 EXPECT_TRUE(result != nullptr);
4019 EXPECT_EQ(kHelloExampleComAddrV4, ToString(result));
4020 });
4021
4022 // step 2: wait for the query to reach the server
4023 while (GetNumQueries(dns1, kHelloExampleCom) == 0) {
4024 usleep(1000); // 1ms
4025 }
4026
4027 std::thread t2([&listen_addr2, &hints, &dns2, this]() {
4028 ASSERT_TRUE(mDnsClient.SetResolversForNetwork({listen_addr2}));
4029 // step 5: query (should be blocked in resolver)
4030 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
4031 // step 7: check result
4032 EXPECT_TRUE(result != nullptr);
4033 EXPECT_EQ(kHelloExampleComAddrV4, ToString(result));
4034 EXPECT_EQ(1U, GetNumQueriesForType(dns2, ns_type::ns_t_a, kHelloExampleCom));
4035 });
4036
4037 // step 4: wait a bit for the 2nd query to enter pending state
4038 usleep(100 * 1000); // 100ms
4039 // step 6: flush cache (will unblock pending queries)
4040 EXPECT_TRUE(mDnsClient.resolvService()->flushNetworkCache(TEST_NETID).isOk());
4041 t2.join();
4042
4043 // step 8: resume server#1
4044 dns1.setDeferredResp(false);
4045 t1.join();
4046
4047 // step 10: verify if result is correctly cached
4048 dns2.clearQueries();
4049 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
4050 EXPECT_EQ(0U, GetNumQueries(dns2, kHelloExampleCom));
4051 EXPECT_EQ(kHelloExampleComAddrV4, ToString(result));
4052}
4053
waynema29253052019-08-20 11:26:08 +08004054// TODO: Perhaps to have a boundary conditions test for TCP and UDP.
4055TEST_F(ResolverTest, TcpQueryWithOversizePayload) {
4056 test::DNSResponder dns;
4057 StartDns(dns, {{kHelloExampleCom, ns_type::ns_t_a, kHelloExampleComAddrV4}});
4058 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
4059
4060 int fd = dns_open_proxy();
4061 ASSERT_TRUE(fd > 0);
4062
4063 // Sending DNS query over TCP once the packet sizes exceed 512 bytes.
4064 // The raw data is combined with Question section and Additional section
4065 // Question section : query "hello.example.com", type A, class IN
4066 // Additional section : type OPT (41), Option PADDING, Option Length 546
4067 // Padding option which allows DNS clients and servers to artificially
4068 // increase the size of a DNS message by a variable number of bytes.
4069 // See also RFC7830, section 3
4070 const std::string query =
4071 "+c0BAAABAAAAAAABBWhlbGxvB2V4YW1wbGUDY29tAAABAAEAACkgAAAAgAACJgAMAiIAAAAAAAAAAAAAAAAAA"
4072 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4073 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4074 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4075 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4076 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4077 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4078 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4079 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
4080 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=";
4081 const std::string cmd =
4082 "resnsend " + std::to_string(TEST_NETID) + " 0 " /* ResNsendFlags */ + query + '\0';
4083 ssize_t rc = TEMP_FAILURE_RETRY(write(fd, cmd.c_str(), cmd.size()));
4084 EXPECT_EQ(rc, static_cast<ssize_t>(cmd.size()));
4085 expectAnswersValid(fd, AF_INET, kHelloExampleComAddrV4);
4086 EXPECT_EQ(1U, GetNumQueriesForProtocol(dns, IPPROTO_TCP, kHelloExampleCom));
4087 EXPECT_EQ(0U, GetNumQueriesForProtocol(dns, IPPROTO_UDP, kHelloExampleCom));
4088}
4089
Ken Chen99344882020-01-01 14:59:38 +08004090TEST_F(ResolverTest, TruncatedRspMode) {
4091 constexpr char listen_addr[] = "127.0.0.4";
4092 constexpr char listen_addr2[] = "127.0.0.5";
4093 constexpr char listen_srv[] = "53";
4094
4095 test::DNSResponder dns(listen_addr, listen_srv, static_cast<ns_rcode>(-1));
4096 test::DNSResponder dns2(listen_addr2, listen_srv, static_cast<ns_rcode>(-1));
4097 // dns supports UDP only, dns2 support UDP and TCP
4098 dns.setResponseProbability(0.0, IPPROTO_TCP);
4099 StartDns(dns, kLargeCnameChainRecords);
4100 StartDns(dns2, kLargeCnameChainRecords);
4101
4102 const struct TestConfig {
4103 const std::optional<int32_t> tcMode;
4104 const bool ret;
4105 const unsigned numQueries;
4106 std::string asParameters() const {
4107 return StringPrintf("tcMode: %d, ret: %s, numQueries: %u", tcMode.value_or(-1),
4108 ret ? "true" : "false", numQueries);
4109 }
4110 } testConfigs[]{
4111 // clang-format off
4112 {std::nullopt, true, 0}, /* mode unset */
4113 {aidl::android::net::IDnsResolver::TC_MODE_DEFAULT, true, 0}, /* default mode */
4114 {aidl::android::net::IDnsResolver::TC_MODE_UDP_TCP, true, 1}, /* alternative mode */
4115 {-666, false, 1}, /* invalid input */
4116 // clang-format on
4117 };
4118
4119 for (const auto& config : testConfigs) {
4120 SCOPED_TRACE(config.asParameters());
4121
4122 ResolverParamsParcel parcel = DnsResponderClient::GetDefaultResolverParamsParcel();
4123 parcel.servers = {listen_addr, listen_addr2};
4124 if (config.tcMode) {
4125 parcel.experimentalOptions.tcMode = config.tcMode.value();
4126 }
4127 ASSERT_EQ(mDnsClient.resolvService()->setResolverConfiguration(parcel).isOk(), config.ret);
4128
4129 const addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
4130 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
4131 ASSERT_TRUE(result != nullptr);
4132 EXPECT_EQ(ToString(result), kHelloExampleComAddrV4);
4133 // TC_MODE_DEFAULT: resolver retries on TCP-only on each name server.
4134 // TC_MODE_UDP_TCP: resolver retries on TCP on the same server, falls back to UDP from next.
4135 ASSERT_EQ(GetNumQueriesForProtocol(dns, IPPROTO_UDP, kHelloExampleCom), 1U);
4136 ASSERT_EQ(GetNumQueriesForProtocol(dns, IPPROTO_TCP, kHelloExampleCom), 1U);
4137 ASSERT_EQ(GetNumQueriesForProtocol(dns2, IPPROTO_UDP, kHelloExampleCom), config.numQueries);
4138 ASSERT_EQ(GetNumQueriesForProtocol(dns2, IPPROTO_TCP, kHelloExampleCom), 1U);
4139
4140 dns.clearQueries();
4141 dns2.clearQueries();
4142 ASSERT_TRUE(mDnsClient.resolvService()->flushNetworkCache(TEST_NETID).isOk());
4143 }
4144}
4145
Hungming Chenbb90ab32019-10-28 18:20:31 +08004146// Parameterized tests.
4147// TODO: Merge the existing tests as parameterized test if possible.
4148// TODO: Perhaps move parameterized tests to an independent file.
4149enum class CallType { GETADDRINFO, GETHOSTBYNAME };
4150class ResolverParameterizedTest : public ResolverTest,
Hungming Chen63779052019-10-30 15:06:13 +08004151 public testing::WithParamInterface<CallType> {
4152 protected:
Hungming Chen22617fd2019-12-06 12:15:45 +08004153 void VerifyQueryHelloExampleComV4(const test::DNSResponder& dns, const CallType calltype,
4154 const bool verifyNumQueries = true) {
Hungming Chen63779052019-10-30 15:06:13 +08004155 if (calltype == CallType::GETADDRINFO) {
4156 const addrinfo hints = {.ai_family = AF_INET, .ai_socktype = SOCK_DGRAM};
4157 ScopedAddrinfo result = safe_getaddrinfo("hello", nullptr, &hints);
4158 ASSERT_TRUE(result != nullptr);
4159 EXPECT_EQ(kHelloExampleComAddrV4, ToString(result));
4160 } else if (calltype == CallType::GETHOSTBYNAME) {
4161 const hostent* result = gethostbyname("hello");
4162 ASSERT_TRUE(result != nullptr);
4163 ASSERT_EQ(4, result->h_length);
4164 ASSERT_FALSE(result->h_addr_list[0] == nullptr);
4165 EXPECT_EQ(kHelloExampleComAddrV4, ToString(result));
4166 EXPECT_TRUE(result->h_addr_list[1] == nullptr);
4167 } else {
4168 FAIL() << "Unsupported call type: " << static_cast<uint32_t>(calltype);
4169 }
Hungming Chen22617fd2019-12-06 12:15:45 +08004170 if (verifyNumQueries) EXPECT_EQ(1U, GetNumQueries(dns, kHelloExampleCom));
Hungming Chen63779052019-10-30 15:06:13 +08004171 }
4172};
Hungming Chenbb90ab32019-10-28 18:20:31 +08004173
Hungming Chen63779052019-10-30 15:06:13 +08004174INSTANTIATE_TEST_SUITE_P(QueryCallTest, ResolverParameterizedTest,
Hungming Chenbb90ab32019-10-28 18:20:31 +08004175 testing::Values(CallType::GETADDRINFO, CallType::GETHOSTBYNAME),
4176 [](const testing::TestParamInfo<CallType>& info) {
Hungming Chenbb90ab32019-10-28 18:20:31 +08004177 switch (info.param) {
4178 case CallType::GETADDRINFO:
Hungming Chen63779052019-10-30 15:06:13 +08004179 return "GetAddrInfo";
Hungming Chenbb90ab32019-10-28 18:20:31 +08004180 case CallType::GETHOSTBYNAME:
Hungming Chen63779052019-10-30 15:06:13 +08004181 return "GetHostByName";
Hungming Chenbb90ab32019-10-28 18:20:31 +08004182 default:
Hungming Chen63779052019-10-30 15:06:13 +08004183 return "InvalidParameter"; // Should not happen.
Hungming Chenbb90ab32019-10-28 18:20:31 +08004184 }
Hungming Chenbb90ab32019-10-28 18:20:31 +08004185 });
4186
4187TEST_P(ResolverParameterizedTest, AuthoritySectionAndAdditionalSection) {
4188 // DNS response may have more information in authority section and additional section.
4189 // Currently, getanswer() of packages/modules/DnsResolver/getaddrinfo.cpp doesn't parse the
4190 // content of authority section and additional section. Test these sections if they crash
4191 // the resolver, just in case. See also RFC 1035 section 4.1.
4192 const auto& calltype = GetParam();
4193 test::DNSHeader header(kDefaultDnsHeader);
4194
4195 // Create a DNS response which has a authoritative nameserver record in authority
4196 // section and its relevant address record in additional section.
4197 //
4198 // Question
4199 // hello.example.com. IN A
4200 // Answer
4201 // hello.example.com. IN A 1.2.3.4
4202 // Authority:
4203 // hello.example.com. IN NS ns1.example.com.
4204 // Additional:
4205 // ns1.example.com. IN A 5.6.7.8
4206 //
4207 // A response may have only question, answer, and authority section. Current testing response
4208 // should be able to cover this condition.
4209
4210 // Question section.
4211 test::DNSQuestion question{
4212 .qname = {.name = kHelloExampleCom},
4213 .qtype = ns_type::ns_t_a,
4214 .qclass = ns_c_in,
4215 };
4216 header.questions.push_back(std::move(question));
4217
4218 // Answer section.
4219 test::DNSRecord recordAnswer{
4220 .name = {.name = kHelloExampleCom},
4221 .rtype = ns_type::ns_t_a,
4222 .rclass = ns_c_in,
4223 .ttl = 0, // no cache
4224 };
Hungming Chen63779052019-10-30 15:06:13 +08004225 EXPECT_TRUE(test::DNSResponder::fillRdata(kHelloExampleComAddrV4, recordAnswer));
Hungming Chenbb90ab32019-10-28 18:20:31 +08004226 header.answers.push_back(std::move(recordAnswer));
4227
4228 // Authority section.
4229 test::DNSRecord recordAuthority{
4230 .name = {.name = kHelloExampleCom},
4231 .rtype = ns_type::ns_t_ns,
4232 .rclass = ns_c_in,
4233 .ttl = 0, // no cache
4234 };
4235 EXPECT_TRUE(test::DNSResponder::fillRdata("ns1.example.com.", recordAuthority));
4236 header.authorities.push_back(std::move(recordAuthority));
4237
4238 // Additional section.
4239 test::DNSRecord recordAdditional{
4240 .name = {.name = "ns1.example.com."},
4241 .rtype = ns_type::ns_t_a,
4242 .rclass = ns_c_in,
4243 .ttl = 0, // no cache
4244 };
4245 EXPECT_TRUE(test::DNSResponder::fillRdata("5.6.7.8", recordAdditional));
4246 header.additionals.push_back(std::move(recordAdditional));
4247
4248 // Start DNS server.
4249 test::DNSResponder dns(test::DNSResponder::MappingType::DNS_HEADER);
4250 dns.addMappingDnsHeader(kHelloExampleCom, ns_type::ns_t_a, header);
4251 ASSERT_TRUE(dns.startServer());
4252 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
4253 dns.clearQueries();
4254
4255 // Expect that get the address and the resolver doesn't crash.
Hungming Chen63779052019-10-30 15:06:13 +08004256 VerifyQueryHelloExampleComV4(dns, calltype);
4257}
4258
4259TEST_P(ResolverParameterizedTest, MessageCompression) {
4260 const auto& calltype = GetParam();
4261
4262 // The response with compressed domain name by a pointer. See RFC 1035 section 4.1.4.
4263 //
4264 // Ignoring the other fields of the message, the domain name of question section and answer
4265 // section are presented as:
4266 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4267 // 12 | 5 | h |
4268 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4269 // 14 | e | l |
4270 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4271 // 16 | l | o |
4272 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4273 // 18 | 7 | e |
4274 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4275 // 20 | x | a |
4276 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4277 // 22 | m | p |
4278 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4279 // 24 | l | e |
4280 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4281 // 26 | 3 | c |
4282 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4283 // 28 | o | m |
4284 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4285 // 30 | 0 | ... |
4286 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4287 //
4288 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4289 // 35 | 1 1| 12 |
4290 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4291 const std::vector<uint8_t> kResponseAPointer = {
4292 /* Header */
4293 0x00, 0x00, /* Transaction ID: 0x0000 */
4294 0x81, 0x80, /* Flags: qr rd ra */
4295 0x00, 0x01, /* Questions: 1 */
4296 0x00, 0x01, /* Answer RRs: 1 */
4297 0x00, 0x00, /* Authority RRs: 0 */
4298 0x00, 0x00, /* Additional RRs: 0 */
4299 /* Queries */
4300 0x05, 0x68, 0x65, 0x6c, 0x6c, 0x6f, 0x07, 0x65, 0x78, 0x61, 0x6d, 0x70, 0x6c, 0x65,
4301 0x03, 0x63, 0x6f, 0x6d, 0x00, /* Name: hello.example.com */
4302 0x00, 0x01, /* Type: A */
4303 0x00, 0x01, /* Class: IN */
4304 /* Answers */
4305 0xc0, 0x0c, /* Name: hello.example.com (a pointer) */
4306 0x00, 0x01, /* Type: A */
4307 0x00, 0x01, /* Class: IN */
4308 0x00, 0x00, 0x00, 0x00, /* Time to live: 0 */
4309 0x00, 0x04, /* Data length: 4 */
4310 0x01, 0x02, 0x03, 0x04 /* Address: 1.2.3.4 */
4311 };
4312
4313 // The response with compressed domain name by a sequence of labels ending with a pointer. See
4314 // RFC 1035 section 4.1.4.
4315 //
4316 // Ignoring the other fields of the message, the domain name of question section and answer
4317 // section are presented as:
4318 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4319 // 12 | 5 | h |
4320 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4321 // 14 | e | l |
4322 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4323 // 16 | l | o |
4324 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4325 // 18 | 7 | e |
4326 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4327 // 20 | x | a |
4328 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4329 // 22 | m | p |
4330 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4331 // 24 | l | e |
4332 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4333 // 26 | 3 | c |
4334 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4335 // 28 | o | m |
4336 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4337 // 30 | 0 | ... |
4338 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4339 //
4340 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4341 // 35 | 5 | h |
4342 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4343 // 37 | e | l |
4344 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4345 // 39 | l | o |
4346 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4347 // 41 | 1 1| 18 |
4348 // +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
4349 const std::vector<uint8_t> kResponseLabelEndingWithAPointer = {
4350 /* Header */
4351 0x00, 0x00, /* Transaction ID: 0x0000 */
4352 0x81, 0x80, /* Flags: qr rd ra */
4353 0x00, 0x01, /* Questions: 1 */
4354 0x00, 0x01, /* Answer RRs: 1 */
4355 0x00, 0x00, /* Authority RRs: 0 */
4356 0x00, 0x00, /* Additional RRs: 0 */
4357 /* Queries */
4358 0x05, 0x68, 0x65, 0x6c, 0x6c, 0x6f, 0x07, 0x65, 0x78, 0x61, 0x6d, 0x70, 0x6c, 0x65,
4359 0x03, 0x63, 0x6f, 0x6d, 0x00, /* Name: hello.example.com */
4360 0x00, 0x01, /* Type: A */
4361 0x00, 0x01, /* Class: IN */
4362 /* Answers */
4363 0x05, 0x68, 0x65, 0x6c, 0x6c, 0x6f, 0xc0,
4364 0x12, /* Name: hello.example.com (a label ending with a pointer) */
4365 0x00, 0x01, /* Type: A */
4366 0x00, 0x01, /* Class: IN */
4367 0x00, 0x00, 0x00, 0x00, /* Time to live: 0 */
4368 0x00, 0x04, /* Data length: 4 */
4369 0x01, 0x02, 0x03, 0x04 /* Address: 1.2.3.4 */
4370 };
4371
4372 for (const auto& response : {kResponseAPointer, kResponseLabelEndingWithAPointer}) {
4373 SCOPED_TRACE(StringPrintf("Hex dump: %s", toHex(makeSlice(response)).c_str()));
4374
4375 test::DNSResponder dns(test::DNSResponder::MappingType::BINARY_PACKET);
4376 dns.addMappingBinaryPacket(kHelloExampleComQueryV4, response);
4377 StartDns(dns, {});
4378 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
4379
4380 // Expect no cache because the TTL of testing responses are 0.
4381 VerifyQueryHelloExampleComV4(dns, calltype);
Hungming Chenbb90ab32019-10-28 18:20:31 +08004382 }
Mike Yu40e67072019-10-09 21:14:09 +08004383}
Hungming Chen22617fd2019-12-06 12:15:45 +08004384
4385TEST_P(ResolverParameterizedTest, TruncatedResponse) {
4386 const auto& calltype = GetParam();
4387
Hungming Chen22617fd2019-12-06 12:15:45 +08004388 test::DNSResponder dns;
Ken Chen99344882020-01-01 14:59:38 +08004389 StartDns(dns, kLargeCnameChainRecords);
Hungming Chen22617fd2019-12-06 12:15:45 +08004390 ASSERT_TRUE(mDnsClient.SetResolversForNetwork());
4391
4392 // Expect UDP response is truncated. The resolver retries over TCP. See RFC 1035 section 4.2.1.
4393 VerifyQueryHelloExampleComV4(dns, calltype, false);
4394 EXPECT_EQ(1U, GetNumQueriesForProtocol(dns, IPPROTO_UDP, kHelloExampleCom));
4395 EXPECT_EQ(1U, GetNumQueriesForProtocol(dns, IPPROTO_TCP, kHelloExampleCom));
4396}