dns: Refactor HostResolverManager::ServiceEndpointRequestImpl
This is a preparation for adding a feature to allow using stale DNS
results by using ServiceEndpointRequest:
* Add a state for resolving locally
* Add a helper method to convert HostCache::Entry to ServiceEndpoints
No behavior changes.
Bug: 383174960
Change-Id: I0e4fd71c34676f3e99ff1cce03e773f9c21c654a
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6088517
Commit-Queue: Kenichi Ishibashi <bashi@chromium.org>
Reviewed-by: Eric Orth <ericorth@chromium.org>
Cr-Commit-Position: refs/heads/main@{#1398190}
diff --git a/net/dns/host_cache.cc b/net/dns/host_cache.cc
index 59bdd507..75b433f 100644
--- a/net/dns/host_cache.cc
+++ b/net/dns/host_cache.cc
@@ -507,6 +507,50 @@
return copy;
}
+std::vector<ServiceEndpoint> HostCache::Entry::ConvertToServiceEndpoints(
+ uint16_t port) const {
+ std::vector<ServiceEndpoint> endpoints;
+
+ std::vector<IPEndPoint> ipv4_endpoints;
+ std::vector<IPEndPoint> ipv6_endpoints;
+ for (const auto& ip_endpoint : ip_endpoints()) {
+ std::vector<IPEndPoint>& ip_endpoints =
+ ip_endpoint.address().IsIPv6() ? ipv6_endpoints : ipv4_endpoints;
+ if (ip_endpoint.port() == 0) {
+ ip_endpoints.emplace_back(ip_endpoint.address(), port);
+ } else {
+ ip_endpoints.emplace_back(ip_endpoint);
+ }
+ }
+
+ // See HostCache::Entry::GetEndpoints.
+ if (!ipv4_endpoints.empty() || !ipv6_endpoints.empty()) {
+ for (const auto& metadata : GetMetadatas()) {
+ if (!base::Contains(canonical_names(), metadata.target_name)) {
+ continue;
+ }
+
+ ServiceEndpoint endpoint;
+ endpoint.ipv4_endpoints = ipv4_endpoints;
+ endpoint.ipv6_endpoints = ipv6_endpoints;
+ endpoint.metadata = metadata;
+ endpoints.emplace_back(std::move(endpoint));
+ }
+
+ // Append Non-SVCB endpoints at the end for fallback.
+ // TODO(crbug.com/41493696): Revisit how to handle non-SVCB endpoints once
+ // the connection layer starts using this API. Adding non-SVCB endpoints
+ // here might be inconsistent with intermediate results generated by
+ // DnsTaskResultsManager, which doesn't append non-SVCB endpoints.
+ ServiceEndpoint non_alternative_endpoint;
+ non_alternative_endpoint.ipv4_endpoints = ipv4_endpoints;
+ non_alternative_endpoint.ipv6_endpoints = ipv6_endpoints;
+ endpoints.emplace_back(std::move(non_alternative_endpoint));
+ }
+
+ return endpoints;
+}
+
HostCache::Entry& HostCache::Entry::operator=(const Entry& entry) = default;
HostCache::Entry& HostCache::Entry::operator=(Entry&& entry) = default;
diff --git a/net/dns/host_cache.h b/net/dns/host_cache.h
index b1a65f4..73be90e 100644
--- a/net/dns/host_cache.h
+++ b/net/dns/host_cache.h
@@ -264,6 +264,11 @@
// set to |port| if the current port is 0. Preserves any non-zero ports.
HostCache::Entry CopyWithDefaultPort(uint16_t port) const;
+ // Converts `this` to a vector of ServiceEndpoints. Converted IP endpoint's
+ // ports set to `port` if the current port is 0. Preserves any non-zero
+ // ports.
+ std::vector<ServiceEndpoint> ConvertToServiceEndpoints(uint16_t port) const;
+
static std::optional<base::TimeDelta> TtlFromInternalResults(
const std::set<std::unique_ptr<HostResolverInternalResult>>& results,
base::Time now,
diff --git a/net/dns/host_resolver_manager_service_endpoint_request_impl.cc b/net/dns/host_resolver_manager_service_endpoint_request_impl.cc
index 32ad45f..78cc965 100644
--- a/net/dns/host_resolver_manager_service_endpoint_request_impl.cc
+++ b/net/dns/host_resolver_manager_service_endpoint_request_impl.cc
@@ -224,6 +224,9 @@
case State::kCheckIPv6ReachabilityComplete:
rv = DoCheckIPv6ReachabilityComplete(rv);
break;
+ case State::kDoResolveLocally:
+ rv = DoResolveLocally();
+ break;
case State::kStartJob:
rv = DoStartJob();
break;
@@ -261,32 +264,36 @@
int HostResolverManager::ServiceEndpointRequestImpl::
DoCheckIPv6ReachabilityComplete(int rv) {
- next_state_ = rv == OK ? State::kStartJob : State::kNone;
+ next_state_ = rv == OK ? State::kDoResolveLocally : State::kNone;
return rv;
}
-int HostResolverManager::ServiceEndpointRequestImpl::DoStartJob() {
- JobKey job_key(host_, resolve_context_.get());
+int HostResolverManager::ServiceEndpointRequestImpl::DoResolveLocally() {
+ job_key_ = JobKey(host_, resolve_context_.get());
IPAddress ip_address;
manager_->InitializeJobKeyAndIPAddress(
- network_anonymization_key_, parameters_, net_log_, job_key, ip_address);
+ network_anonymization_key_, parameters_, net_log_, *job_key_, ip_address);
// Try to resolve locally first.
std::optional<HostCache::EntryStaleness> stale_info;
- std::deque<TaskType> tasks;
HostCache::Entry results = manager_->ResolveLocally(
- /*only_ipv6_reachable=*/false, job_key, ip_address,
+ /*only_ipv6_reachable=*/false, *job_key_, ip_address,
parameters_.cache_usage, parameters_.secure_dns_policy,
- parameters_.source, net_log_, host_cache(), &tasks, &stale_info);
+ parameters_.source, net_log_, host_cache(), &tasks_, &stale_info);
if (results.error() != ERR_DNS_CACHE_MISS ||
- parameters_.source == HostResolverSource::LOCAL_ONLY || tasks.empty()) {
+ parameters_.source == HostResolverSource::LOCAL_ONLY || tasks_.empty()) {
SetFinalizedResultFromLegacyResults(results);
error_info_ = ResolveErrorInfo(results.error());
return results.error();
}
- manager_->CreateAndStartJobForServiceEndpointRequest(std::move(job_key),
- std::move(tasks), this);
+ next_state_ = State::kStartJob;
+ return OK;
+}
+
+int HostResolverManager::ServiceEndpointRequestImpl::DoStartJob() {
+ manager_->CreateAndStartJobForServiceEndpointRequest(std::move(*job_key_),
+ std::move(tasks_), this);
return ERR_IO_PENDING;
}
@@ -298,44 +305,8 @@
SetFinalizedResultFromLegacyResults(const HostCache::Entry& results) {
CHECK(!finalized_result_);
if (results.error() == OK && !parameters_.is_speculative) {
- std::vector<IPEndPoint> ipv4_endpoints;
- std::vector<IPEndPoint> ipv6_endpoints;
- for (const auto& ip_endpoint : results.ip_endpoints()) {
- std::vector<IPEndPoint>& ip_endpoints =
- ip_endpoint.address().IsIPv6() ? ipv6_endpoints : ipv4_endpoints;
- if (ip_endpoint.port() == 0) {
- ip_endpoints.emplace_back(ip_endpoint.address(), host_.GetPort());
- } else {
- ip_endpoints.emplace_back(ip_endpoint);
- }
- }
-
- // See HostCache::Entry::GetEndpoints.
- std::vector<ServiceEndpoint> endpoints;
- if (!ipv4_endpoints.empty() || !ipv6_endpoints.empty()) {
- for (const auto& metadata : results.GetMetadatas()) {
- if (!base::Contains(results.canonical_names(), metadata.target_name)) {
- continue;
- }
-
- ServiceEndpoint endpoint;
- endpoint.ipv4_endpoints = ipv4_endpoints;
- endpoint.ipv6_endpoints = ipv6_endpoints;
- endpoint.metadata = metadata;
- endpoints.emplace_back(std::move(endpoint));
- }
-
- // Append Non-SVCB endpoints at the end for fallback.
- // TODO(crbug.com/41493696): Revisit how to handle non-SVCB endpoints once
- // the connection layer starts using this API. Adding non-SVCB endpoints
- // here might be inconsistent with intermediate results generated by
- // DnsTaskResultsManager, which doesn't append non-SVCB endpoints.
- ServiceEndpoint non_alternative_endpoint;
- non_alternative_endpoint.ipv4_endpoints = ipv4_endpoints;
- non_alternative_endpoint.ipv6_endpoints = ipv6_endpoints;
- endpoints.emplace_back(std::move(non_alternative_endpoint));
- }
-
+ std::vector<ServiceEndpoint> endpoints =
+ results.ConvertToServiceEndpoints(host_.GetPort());
finalized_result_ =
FinalizedResult(std::move(endpoints),
dns_alias_utility::FixUpDnsAliases(results.aliases()));
diff --git a/net/dns/host_resolver_manager_service_endpoint_request_impl.h b/net/dns/host_resolver_manager_service_endpoint_request_impl.h
index 9ead26a2..dcb427ac 100644
--- a/net/dns/host_resolver_manager_service_endpoint_request_impl.h
+++ b/net/dns/host_resolver_manager_service_endpoint_request_impl.h
@@ -5,6 +5,7 @@
#ifndef NET_DNS_HOST_RESOLVER_MANAGER_SERVICE_ENDPOINT_REQUEST_IMPL_H_
#define NET_DNS_HOST_RESOLVER_MANAGER_SERVICE_ENDPOINT_REQUEST_IMPL_H_
+#include <deque>
#include <optional>
#include <set>
#include <string>
@@ -79,12 +80,14 @@
kNone,
kCheckIPv6Reachability,
kCheckIPv6ReachabilityComplete,
+ kDoResolveLocally,
kStartJob,
};
int DoLoop(int rv);
int DoCheckIPv6Reachability();
int DoCheckIPv6ReachabilityComplete(int rv);
+ int DoResolveLocally();
int DoStartJob();
void OnIOComplete(int rv);
@@ -125,6 +128,11 @@
// Set when the endpoint results are finalized.
std::optional<FinalizedResult> finalized_result_;
+ // These fields are calculated by DoResolveLocally() and consumed by
+ // DoStartJob().
+ std::optional<JobKey> job_key_;
+ std::deque<TaskType> tasks_;
+
// Set when a job is associated with `this`. Must be valid unless
// `resolve_context_` becomes invalid. Cleared when the endpoints are
// finalized to ensure that `job_` doesn't become a dangling pointer.