1 // Copyright 2012 The Chromium Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifndef NET_DNS_HOST_RESOLVER_H_
6 #define NET_DNS_HOST_RESOLVER_H_
7
8 #include <stddef.h>
9 #include <stdint.h>
10
11 #include <memory>
12 #include <optional>
13 #include <set>
14 #include <string>
15 #include <string_view>
16 #include <type_traits>
17 #include <vector>
18
19 #include "base/containers/span.h"
20 #include "base/values.h"
21 #include "net/base/address_family.h"
22 #include "net/base/completion_once_callback.h"
23 #include "net/base/connection_endpoint_metadata.h"
24 #include "net/base/host_port_pair.h"
25 #include "net/base/network_anonymization_key.h"
26 #include "net/base/network_handle.h"
27 #include "net/base/request_priority.h"
28 #include "net/dns/host_cache.h"
29 #include "net/dns/host_resolver_system_task.h"
30 #include "net/dns/public/dns_config_overrides.h"
31 #include "net/dns/public/dns_query_type.h"
32 #include "net/dns/public/host_resolver_results.h"
33 #include "net/dns/public/host_resolver_source.h"
34 #include "net/dns/public/mdns_listener_update_type.h"
35 #include "net/dns/public/resolve_error_info.h"
36 #include "net/dns/public/secure_dns_policy.h"
37 #include "net/log/net_log_with_source.h"
38 #include "third_party/abseil-cpp/absl/types/variant.h"
39 #include "url/scheme_host_port.h"
40
41 namespace net {
42
43 class AddressList;
44 class ContextHostResolver;
45 class DnsClient;
46 struct DnsConfigOverrides;
47 class HostResolverManager;
48 class NetLog;
49 class URLRequestContext;
50
51 template <typename T>
requires(T t)52 concept HasConnectionEndpointMetadata = requires(T t) {
53 { t.metadata } -> std::same_as<ConnectionEndpointMetadata&>;
54 };
55
56 // This class represents the task of resolving hostnames (or IP address
57 // literal) to an AddressList object (or other DNS-style results).
58 //
59 // Typically implemented by ContextHostResolver or wrappers thereof. See
60 // HostResolver::Create[...]() methods for construction or URLRequestContext for
61 // retrieval.
62 //
63 // See mock_host_resolver.h for test implementations.
64 class NET_EXPORT HostResolver {
65 public:
66 class NET_EXPORT Host {
67 public:
68 explicit Host(absl::variant<url::SchemeHostPort, HostPortPair> host);
69 ~Host();
70
71 Host(const Host&);
72 Host& operator=(const Host&);
73 Host(Host&&);
74 Host& operator=(Host&&);
75
76 bool HasScheme() const;
77 const std::string& GetScheme() const;
78 std::string GetHostname() const; // With brackets for IPv6 literals.
79 std::string_view GetHostnameWithoutBrackets() const;
80 uint16_t GetPort() const;
81
82 std::string ToString() const;
83
84 const url::SchemeHostPort& AsSchemeHostPort() const;
85
86 bool operator==(const Host& other) const { return host_ == other.host_; }
87
88 bool operator<(const Host& other) const { return host_ < other.host_; }
89
90 private:
91 absl::variant<url::SchemeHostPort, HostPortPair> host_;
92 };
93
94 // Handler for an individual host resolution request. Created by
95 // HostResolver::CreateRequest().
96 //
97 // TODO(crbug.com/40212535): Most result retrieval here follows a pattern
98 // where it may return null or empty for requests where that result type is
99 // not available. Clean this up to always return empty for such cases and
100 // remove nullability from the return types.
101 class ResolveHostRequest {
102 public:
103 // Destruction cancels the request if running asynchronously, causing the
104 // callback to never be invoked.
105 virtual ~ResolveHostRequest() = default;
106
107 // Starts the request and returns a network error code.
108 //
109 // If the request could not be handled synchronously, returns
110 // |ERR_IO_PENDING|, and completion will be signaled later via |callback|.
111 // On any other returned value, the request was handled synchronously and
112 // |callback| will not be invoked.
113 //
114 // Results in ERR_NAME_NOT_RESOLVED if the hostname is not resolved. More
115 // detail about the underlying error can be retrieved using
116 // GetResolveErrorInfo().
117 //
118 // The parent HostResolver must still be alive when Start() is called, but
119 // if it is destroyed before an asynchronous result completes, the request
120 // will be automatically cancelled.
121 //
122 // If cancelled before |callback| is invoked, it will never be invoked.
123 virtual int Start(CompletionOnceCallback callback) = 0;
124
125 // Address record (A or AAAA) results of the request. Should only be called
126 // after Start() signals completion, either by invoking the callback or by
127 // returning a result other than |ERR_IO_PENDING|. May return nullptr or
128 // empty for non-address requests.
129 //
130 // TODO(crbug.com/40203587): Remove and replace all usage with
131 // GetEndpointResults().
132 virtual const AddressList* GetAddressResults() const = 0;
133
134 // Endpoint results for `A`, `AAAA`, `UNSPECIFIED`, or `HTTPS` requests.
135 // Should only be called after Start() signals completion, either by
136 // invoking the callback or by returning a result other than
137 // `ERR_IO_PENDING`. May return nullptr or empty for non-address/HTTPS
138 // requests.
139 virtual const std::vector<HostResolverEndpointResult>* GetEndpointResults()
140 const = 0;
141
142 // Text record (TXT) results of the request. Should only be called after
143 // Start() signals completion, either by invoking the callback or by
144 // returning a result other than |ERR_IO_PENDING|. May return nullptr or
145 // empty for non-TXT requests.
146 virtual const std::vector<std::string>* GetTextResults() const = 0;
147
148 // Hostname record (SRV or PTR) results of the request. For SRV results,
149 // hostnames are ordered according to their priorities and weights. See RFC
150 // 2782. May return nullptr or empty for non-SRV/PTR requests.
151 //
152 // Should only be called after Start() signals completion, either by
153 // invoking the callback or by returning a result other than
154 // |ERR_IO_PENDING|.
155 virtual const std::vector<HostPortPair>* GetHostnameResults() const = 0;
156
157 // Any DNS record aliases, such as CNAME aliases, found as a result of an
158 // address query. Includes all known aliases, e.g. from A, AAAA, or HTTPS,
159 // not just from the address used for the connection, in no particular
160 // order. Should only be called after Start() signals completion, either by
161 // invoking the callback or by returning a result other than
162 // `ERR_IO_PENDING`. Returns a list of aliases that has been fixed up and
163 // canonicalized (as URL hostnames), and thus may differ from the results
164 // stored directly in the AddressList. May return nullptr or empty for
165 // non-address/HTTPS requests.
166 //
167 // If `ResolveHostParameters::include_canonical_name` was true, alias
168 // results will always be the single "canonical name" received from the
169 // system resolver without URL hostname canonicalization (or an empty set or
170 // `nullptr` in the unusual case that the system resolver did not give a
171 // canonical name).
172 virtual const std::set<std::string>* GetDnsAliasResults() const = 0;
173
174 // Result of an experimental query. Meaning depends on the specific query
175 // type, but each boolean value generally refers to a valid or invalid
176 // record of the experimental type. May return nullptr or empty for requests
177 // without experimental result behavior.
178 NET_EXPORT virtual const std::vector<bool>*
179 GetExperimentalResultsForTesting() const;
180
181 // Error info for the request.
182 //
183 // Should only be called after Start() signals completion, either by
184 // invoking the callback or by returning a result other than
185 // |ERR_IO_PENDING|.
186 virtual ResolveErrorInfo GetResolveErrorInfo() const = 0;
187
188 // Information about the result's staleness in the host cache. Only
189 // available if results were received from the host cache, otherwise
190 // returns nullopt.
191 //
192 // Should only be called after Start() signals completion, either by
193 // invoking the callback or by returning a result other than
194 // |ERR_IO_PENDING|.
195 virtual const std::optional<HostCache::EntryStaleness>& GetStaleInfo()
196 const = 0;
197
198 // Changes the priority of the specified request. Can only be called while
199 // the request is running (after Start() returns |ERR_IO_PENDING| and before
200 // the callback is invoked).
ChangeRequestPriority(RequestPriority priority)201 virtual void ChangeRequestPriority(RequestPriority priority) {}
202 };
203
204 // Handler for a service endpoint resolution request. Unlike
205 // ResolveHostRequest, which waits for all responses, this could provide
206 // intermediate endpoint candidates in the middle of the resolution.
207 //
208 // A client owns an instance of this class. Destruction cancels the request.
209 class ServiceEndpointRequest {
210 public:
211 class Delegate {
212 public:
213 virtual ~Delegate() = default;
214
215 // Called when the request has updated endpoints.
216 virtual void OnServiceEndpointsUpdated() = 0;
217
218 // Called when all queries are responded or an error occurred.
219 // Note that this can be called without OnServiceEndpointsUpdated().
220 virtual void OnServiceEndpointRequestFinished(int rv) = 0;
221 };
222
223 virtual ~ServiceEndpointRequest() = default;
224
225 // Starts resolving service endpoints. `delegate` is used only when this
226 // method returns ERR_IO_PENDING. When the return value is other than
227 // ERR_IO_PENDING, resolution completed (or an error occurred)
228 // synchronously, and GetEndpointResults() will return finalized results.
229 virtual int Start(Delegate* delegate) = 0;
230
231 // The current available service endpoints. These can be changed over time
232 // while resolution is still ongoing. Changes are signaled by a call to the
233 // delegate's OnServiceEndpointsUpdated(). Results are finalized when
234 // Start() finished synchronously (returning other than ERR_IO_PENDING), or
235 // delegate's OnServiceEndpointRequestFinished() is called.
236 virtual const std::vector<ServiceEndpoint>& GetEndpointResults() = 0;
237
238 // Any DNS record aliases, such as CNAME aliases, found as a result of
239 // addresses and HTTPS queries. These can be changed over time while
240 // resolution is still ongoing. See also the comment on
241 // Request::GetDnsAliasResults() for details.
242 virtual const std::set<std::string>& GetDnsAliasResults() = 0;
243
244 // True if the client of this request can attempt cryptographic handshakes.
245 // If false, the provided service endpoints via GetEndpointResults() are not
246 // finalized to the point to allow completing transactions, and data or
247 // cryptographic handshakes must not be sent. This can be changed over time
248 // while resolution is still ongoing.
249 // TODO(crbug.com/41493696): Consider renaming this to
250 // `IsSvcbResolutionCompleted()` when Chrome supports HTTPS follow-up
251 // queries.
252 virtual bool EndpointsCryptoReady() = 0;
253
254 // Returns the error info of this request. This can be changed over time
255 // while resolution is still ongoing. In general, should be called only
256 // after resolution completed.
257 virtual ResolveErrorInfo GetResolveErrorInfo() = 0;
258
259 // Change the priority of this request.
260 virtual void ChangeRequestPriority(RequestPriority priority) = 0;
261 };
262
263 // Handler for an activation of probes controlled by a HostResolver. Created
264 // by HostResolver::CreateDohProbeRequest().
265 class ProbeRequest {
266 public:
267 // Destruction cancels the request and all probes.
268 virtual ~ProbeRequest() = default;
269
270 // Activates async running of probes. Always returns ERR_IO_PENDING or an
271 // error from activating probes. No callback as probes will never "complete"
272 // until cancellation.
273 virtual int Start() = 0;
274 };
275
276 // The options for features::kUseDnsHttpsSvcb experiment. See the comments
277 // in net/base/features.h for more details.
278 struct NET_EXPORT HttpsSvcbOptions {
279 HttpsSvcbOptions();
280 HttpsSvcbOptions(const HttpsSvcbOptions&);
281 HttpsSvcbOptions(HttpsSvcbOptions&&);
282 HttpsSvcbOptions& operator=(const HttpsSvcbOptions&) = default;
283 HttpsSvcbOptions& operator=(HttpsSvcbOptions&&) = default;
284 ~HttpsSvcbOptions();
285
286 static HttpsSvcbOptions FromDict(const base::Value::Dict& dict);
287 static HttpsSvcbOptions FromFeatures();
288
289 bool enable = false;
290 base::TimeDelta insecure_extra_time_max;
291 int insecure_extra_time_percent = 0;
292 base::TimeDelta insecure_extra_time_min;
293 base::TimeDelta secure_extra_time_max;
294 int secure_extra_time_percent = 0;
295 base::TimeDelta secure_extra_time_min;
296 };
297
298 // Parameter-grouping struct for additional optional parameters for creation
299 // of HostResolverManagers and stand-alone HostResolvers.
300 struct NET_EXPORT ManagerOptions {
301 ManagerOptions();
302 ManagerOptions(const ManagerOptions&);
303 ManagerOptions(ManagerOptions&&);
304 ManagerOptions& operator=(const ManagerOptions&) = default;
305 ManagerOptions& operator=(ManagerOptions&&) = default;
306 ~ManagerOptions();
307
308 // Set |max_concurrent_resolves| to this to select a default level
309 // of concurrency.
310 static const size_t kDefaultParallelism = 0;
311
312 // How many resolve requests will be allowed to run in parallel.
313 // |kDefaultParallelism| for the resolver to choose a default value.
314 size_t max_concurrent_resolves = kDefaultParallelism;
315
316 // The maximum number of times to retry for host resolution if using the
317 // system resolver. No effect when the system resolver is not used.
318 // |kDefaultRetryAttempts| for the resolver to choose a default value.
319 size_t max_system_retry_attempts =
320 HostResolverSystemTask::Params::kDefaultRetryAttempts;
321
322 // Initial setting for whether the insecure portion of the built-in
323 // asynchronous DnsClient is enabled or disabled. See HostResolverManager::
324 // SetInsecureDnsClientEnabled() for details.
325 bool insecure_dns_client_enabled = false;
326
327 // Initial setting for whether additional DNS types (e.g. HTTPS) may be
328 // queried when using the built-in resolver for insecure DNS.
329 bool additional_types_via_insecure_dns_enabled = true;
330
331 // Initial configuration overrides for the built-in asynchronous DnsClient.
332 // See HostResolverManager::SetDnsConfigOverrides() for details.
333 DnsConfigOverrides dns_config_overrides;
334
335 // If set to |false|, when on a WiFi connection, IPv6 will be assumed to be
336 // unreachable without actually checking. See https://crbug.com/696569 for
337 // further context.
338 bool check_ipv6_on_wifi = true;
339
340 // An experimental options for features::kUseDnsHttpsSvcb
341 // and features::kUseDnsHttpsSvcbAlpn.
342 std::optional<HostResolver::HttpsSvcbOptions> https_svcb_options;
343 };
344
345 // Factory class. Useful for classes that need to inject and override resolver
346 // creation for tests.
347 class NET_EXPORT Factory {
348 public:
349 virtual ~Factory() = default;
350
351 // See HostResolver::CreateResolver.
352 virtual std::unique_ptr<HostResolver> CreateResolver(
353 HostResolverManager* manager,
354 std::string_view host_mapping_rules,
355 bool enable_caching);
356
357 // See HostResolver::CreateStandaloneResolver.
358 virtual std::unique_ptr<HostResolver> CreateStandaloneResolver(
359 NetLog* net_log,
360 const ManagerOptions& options,
361 std::string_view host_mapping_rules,
362 bool enable_caching);
363 };
364
365 // Parameter-grouping struct for additional optional parameters for
366 // CreateRequest() calls. All fields are optional and have a reasonable
367 // default.
368 struct NET_EXPORT ResolveHostParameters {
369 ResolveHostParameters();
370
371 // Requested DNS query type. If UNSPECIFIED, the resolver will select a set
372 // of queries automatically. It will select A, AAAA, or both as the address
373 // queries, depending on IPv4/IPv6 settings and reachability. It may also
374 // replace UNSPECIFIED with additional queries, such as HTTPS.
375 DnsQueryType dns_query_type = DnsQueryType::UNSPECIFIED;
376
377 // The initial net priority for the host resolution request.
378 RequestPriority initial_priority = RequestPriority::DEFAULT_PRIORITY;
379
380 // The source to use for resolved addresses. Default allows the resolver to
381 // pick an appropriate source. Only affects use of big external sources (eg
382 // calling the system for resolution or using DNS). Even if a source is
383 // specified, results can still come from cache, resolving "localhost" or
384 // IP literals, etc.
385 HostResolverSource source = HostResolverSource::ANY;
386
387 enum class CacheUsage {
388 // Results may come from the host cache if non-stale.
389 ALLOWED,
390
391 // Results may come from the host cache even if stale (by expiration or
392 // network changes). In secure dns AUTOMATIC mode, the cache is checked
393 // for both secure and insecure results prior to any secure DNS lookups to
394 // minimize response time.
395 STALE_ALLOWED,
396
397 // Results will not come from the host cache.
398 DISALLOWED,
399 };
400 CacheUsage cache_usage = CacheUsage::ALLOWED;
401
402 // If |true|, requests special behavior that the "canonical name" be
403 // requested from the system and be returned as the only entry in
404 // `ResolveHostRequest::GetDnsAliasResults()` results. Setting this
405 // parameter is disallowed for any requests that cannot be resolved using
406 // the system resolver, e.g. non-address requests or requests specifying a
407 // non-`SYSTEM` `source`.
408 //
409 // TODO(crbug.com/40209534): Consider allowing the built-in resolver to
410 // still be used with this parameter. Would then function as a request to
411 // just keep the single final name from the alias chain instead of all
412 // aliases, and also skip the canonicalization unless that canonicalization
413 // is found to be fine for usage.
414 bool include_canonical_name = false;
415
416 // Hint to the resolver that resolution is only being requested for loopback
417 // hosts.
418 bool loopback_only = false;
419
420 // Set |true| iff the host resolve request is only being made speculatively
421 // to fill the cache and the result addresses will not be used. The request
422 // will receive special logging/observer treatment, and the result addresses
423 // will always be |std::nullopt|.
424 bool is_speculative = false;
425
426 // If `true`, resolver may (but is not guaranteed to) take steps to avoid
427 // the name being resolved via LLMNR or mDNS. Useful for requests where it
428 // is not desired to wait for longer timeouts on potential negative results,
429 // as is typically the case for LLMNR or mDNS queries without any results.
430 bool avoid_multicast_resolution = false;
431
432 // Controls the resolver's Secure DNS behavior for this request.
433 SecureDnsPolicy secure_dns_policy = SecureDnsPolicy::kAllow;
434 };
435
436 // Handler for an ongoing MDNS listening operation. Created by
437 // HostResolver::CreateMdnsListener().
438 class MdnsListener {
439 public:
440 // Delegate type for result update notifications from MdnsListener. All
441 // methods have a |result_type| field to allow a single delegate to be
442 // passed to multiple MdnsListeners and be used to listen for updates for
443 // multiple types for the same host.
444 class Delegate {
445 public:
446 virtual ~Delegate() = default;
447
448 virtual void OnAddressResult(MdnsListenerUpdateType update_type,
449 DnsQueryType result_type,
450 IPEndPoint address) = 0;
451 virtual void OnTextResult(MdnsListenerUpdateType update_type,
452 DnsQueryType result_type,
453 std::vector<std::string> text_records) = 0;
454 virtual void OnHostnameResult(MdnsListenerUpdateType update_type,
455 DnsQueryType result_type,
456 HostPortPair host) = 0;
457
458 // For results which may be valid MDNS but are not handled/parsed by
459 // HostResolver, e.g. pointers to the root domain.
460 virtual void OnUnhandledResult(MdnsListenerUpdateType update_type,
461 DnsQueryType result_type) = 0;
462 };
463
464 // Destruction cancels the listening operation.
465 virtual ~MdnsListener() = default;
466
467 // Begins the listening operation, invoking |delegate| whenever results are
468 // updated. |delegate| will no longer be called once the listening operation
469 // is cancelled (via destruction of |this|).
470 virtual int Start(Delegate* delegate) = 0;
471 };
472
473 HostResolver(const HostResolver&) = delete;
474 HostResolver& operator=(const HostResolver&) = delete;
475
476 // If any completion callbacks are pending when the resolver is destroyed,
477 // the host resolutions are cancelled, and the completion callbacks will not
478 // be called.
479 virtual ~HostResolver();
480
481 // Cancels any pending requests without calling callbacks, same as
482 // destruction, except also leaves the resolver in a mostly-noop state. Any
483 // future request Start() calls (for requests created before or after
484 // OnShutdown()) will immediately fail with ERR_CONTEXT_SHUT_DOWN.
485 virtual void OnShutdown() = 0;
486
487 // Creates a request to resolve the given hostname (or IP address literal).
488 // Profiling information for the request is saved to |net_log| if non-NULL.
489 //
490 // Additional parameters may be set using |optional_parameters|. Reasonable
491 // defaults will be used if passed |nullptr|.
492 virtual std::unique_ptr<ResolveHostRequest> CreateRequest(
493 url::SchemeHostPort host,
494 NetworkAnonymizationKey network_anonymization_key,
495 NetLogWithSource net_log,
496 std::optional<ResolveHostParameters> optional_parameters) = 0;
497
498 // Create requests when scheme is unknown or non-standard.
499 // TODO(crbug.com/40181080): Rename to discourage use when scheme is known.
500 virtual std::unique_ptr<ResolveHostRequest> CreateRequest(
501 const HostPortPair& host,
502 const NetworkAnonymizationKey& network_anonymization_key,
503 const NetLogWithSource& net_log,
504 const std::optional<ResolveHostParameters>& optional_parameters) = 0;
505
506 // Creates a service endpoint resolution request.
507 virtual std::unique_ptr<ServiceEndpointRequest> CreateServiceEndpointRequest(
508 Host host,
509 NetworkAnonymizationKey network_anonymization_key,
510 NetLogWithSource net_log,
511 ResolveHostParameters parameters) = 0;
512
513 // Creates a request to probe configured DoH servers to find which can be used
514 // successfully.
515 virtual std::unique_ptr<ProbeRequest> CreateDohProbeRequest();
516
517 // Create a listener to watch for updates to an MDNS result.
518 virtual std::unique_ptr<MdnsListener> CreateMdnsListener(
519 const HostPortPair& host,
520 DnsQueryType query_type);
521
522 // Returns the HostResolverCache |this| uses, or NULL if there isn't one.
523 // Used primarily to clear the cache and for getting debug information.
524 virtual HostCache* GetHostCache();
525
526 // Returns the current DNS configuration |this| is using, as a Value.
527 virtual base::Value::Dict GetDnsConfigAsValue() const;
528
529 // Set the associated URLRequestContext, generally expected to be called by
530 // URLRequestContextBuilder on passing ownership of |this| to a context. May
531 // only be called once.
532 virtual void SetRequestContext(URLRequestContext* request_context);
533
534 virtual HostResolverManager* GetManagerForTesting();
535 virtual const URLRequestContext* GetContextForTesting() const;
536 virtual handles::NetworkHandle GetTargetNetworkForTesting() const;
537
538 // Creates a new HostResolver. |manager| must outlive the returned resolver.
539 //
540 // If |mapping_rules| is non-empty, the mapping rules will be applied to
541 // requests. See MappedHostResolver for details.
542 static std::unique_ptr<HostResolver> CreateResolver(
543 HostResolverManager* manager,
544 std::string_view host_mapping_rules = "",
545 bool enable_caching = true);
546
547 // Creates a HostResolver independent of any global HostResolverManager. Only
548 // for tests and standalone tools not part of the browser.
549 //
550 // If |mapping_rules| is non-empty, the mapping rules will be applied to
551 // requests. See MappedHostResolver for details.
552 static std::unique_ptr<HostResolver> CreateStandaloneResolver(
553 NetLog* net_log,
554 std::optional<ManagerOptions> options = std::nullopt,
555 std::string_view host_mapping_rules = "",
556 bool enable_caching = true);
557 // Same, but explicitly returns the implementing ContextHostResolver. Only
558 // used by tests and by StaleHostResolver in Cronet. No mapping rules can be
559 // applied because doing so requires wrapping the ContextHostResolver.
560 static std::unique_ptr<ContextHostResolver> CreateStandaloneContextResolver(
561 NetLog* net_log,
562 std::optional<ManagerOptions> options = std::nullopt,
563 bool enable_caching = true);
564 // Same, but bind the resolver to `target_network`: all lookups will be
565 // performed exclusively for `target_network`, lookups will fail if
566 // `target_network` disconnects. This can only be used by network-bound
567 // URLRequestContexts.
568 // Due to the current implementation, if `options` is specified, its
569 // DnsConfigOverrides parameter must be empty.
570 // Only implemented for Android starting from Marshmallow.
571 static std::unique_ptr<HostResolver> CreateStandaloneNetworkBoundResolver(
572 NetLog* net_log,
573 handles::NetworkHandle network,
574 std::optional<ManagerOptions> options = std::nullopt,
575 std::string_view host_mapping_rules = "",
576 bool enable_caching = true);
577
578 // Helpers for interacting with HostCache and ProcResolver.
579 static AddressFamily DnsQueryTypeSetToAddressFamily(
580 DnsQueryTypeSet query_types);
581 static HostResolverFlags ParametersToHostResolverFlags(
582 const ResolveHostParameters& parameters);
583
584 // Helper for squashing error code to a small set of DNS error codes.
585 static int SquashErrorCode(int error);
586
587 // Builds an AddressList from the first non-protocol endpoint found in
588 // `endpoints`.
589 //
590 // TODO(crbug.com/40203587): Delete once `AddressList` usage is fully replaced
591 // in `HostResolver` and results.
592 static AddressList EndpointResultToAddressList(
593 base::span<const HostResolverEndpointResult> endpoints,
594 const std::set<std::string>& aliases);
595
596 // Returns whether there is at least one protocol endpoint in `endpoints`, and
597 // all such endpoints have ECH parameters. This can be used to implement the
598 // guidance in section 3 of RFC9460.
599 template <typename T>
AllProtocolEndpointsHaveEch(base::span<const T> endpoints)600 static bool AllProtocolEndpointsHaveEch(base::span<const T> endpoints)
601 requires HasConnectionEndpointMetadata<T>
602 {
603 bool has_svcb = false;
604 for (const auto& endpoint : endpoints) {
605 if (!endpoint.metadata.supported_protocol_alpns.empty()) {
606 has_svcb = true;
607 if (endpoint.metadata.ech_config_list.empty()) {
608 return false; // There is a non-ECH SVCB/HTTPS route.
609 }
610 }
611 }
612 // Either there were no SVCB/HTTPS records (should be SVCB-optional), or
613 // there were and all supported ECH (should be SVCB-reliant).
614 return has_svcb;
615 }
616
617 // Returns true if NAT64 can be used in place of an IPv4 address during host
618 // resolution.
619 static bool MayUseNAT64ForIPv4Literal(HostResolverFlags flags,
620 HostResolverSource source,
621 const IPAddress& ip_address);
622
623 protected:
624 HostResolver();
625
626 // Utility to create a request implementation that always fails with |error|
627 // immediately on start.
628 static std::unique_ptr<ResolveHostRequest> CreateFailingRequest(int error);
629 static std::unique_ptr<ProbeRequest> CreateFailingProbeRequest(int error);
630 static std::unique_ptr<ServiceEndpointRequest>
631 CreateFailingServiceEndpointRequest(int error);
632 };
633
634 } // namespace net
635
636 #endif // NET_DNS_HOST_RESOLVER_H_
637