1// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. 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_BASE_HOST_RESOLVER_H_ 6#define NET_BASE_HOST_RESOLVER_H_ 7 8#include <string> 9 10#include "base/ref_counted.h" 11#include "googleurl/src/gurl.h" 12#include "net/base/address_family.h" 13#include "net/base/completion_callback.h" 14#include "net/base/request_priority.h" 15 16class MessageLoop; 17 18namespace net { 19 20class AddressList; 21class HostCache; 22class LoadLog; 23class NetworkChangeNotifier; 24 25// This class represents the task of resolving hostnames (or IP address 26// literal) to an AddressList object. 27// 28// HostResolver can handle multiple requests at a time, so when cancelling a 29// request the RequestHandle that was returned by Resolve() needs to be 30// given. A simpler alternative for consumers that only have 1 outstanding 31// request at a time is to create a SingleRequestHostResolver wrapper around 32// HostResolver (which will automatically cancel the single request when it 33// goes out of scope). 34class HostResolver : public base::RefCountedThreadSafe<HostResolver> { 35 public: 36 // The parameters for doing a Resolve(). |hostname| and |port| are required, 37 // the rest are optional (and have reasonable defaults). 38 class RequestInfo { 39 public: 40 RequestInfo(const std::string& hostname, int port) 41 : hostname_(hostname), 42 address_family_(ADDRESS_FAMILY_UNSPECIFIED), 43 port_(port), 44 allow_cached_response_(true), 45 is_speculative_(false), 46 priority_(MEDIUM) {} 47 48 const int port() const { return port_; } 49 const std::string& hostname() const { return hostname_; } 50 51 AddressFamily address_family() const { return address_family_; } 52 void set_address_family(AddressFamily address_family) { 53 address_family_ = address_family; 54 } 55 56 bool allow_cached_response() const { return allow_cached_response_; } 57 void set_allow_cached_response(bool b) { allow_cached_response_ = b; } 58 59 bool is_speculative() const { return is_speculative_; } 60 void set_is_speculative(bool b) { is_speculative_ = b; } 61 62 RequestPriority priority() const { return priority_; } 63 void set_priority(RequestPriority priority) { priority_ = priority; } 64 65 const GURL& referrer() const { return referrer_; } 66 void set_referrer(const GURL& referrer) { referrer_ = referrer; } 67 68 private: 69 // The hostname to resolve. 70 std::string hostname_; 71 72 // The address family to restrict results to. 73 AddressFamily address_family_; 74 75 // The port number to set in the result's sockaddrs. 76 int port_; 77 78 // Whether it is ok to return a result from the host cache. 79 bool allow_cached_response_; 80 81 // Whether this request was started by the DNS prefetcher. 82 bool is_speculative_; 83 84 // The priority for the request. 85 RequestPriority priority_; 86 87 // Optional data for consumption by observers. This is the URL of the 88 // page that lead us to the navigation, for DNS prefetcher's benefit. 89 GURL referrer_; 90 }; 91 92 // Interface for observing the requests that flow through a HostResolver. 93 class Observer { 94 public: 95 virtual ~Observer() {} 96 97 // Called at the start of HostResolver::Resolve(). |id| is a unique number 98 // given to the request, so it can be matched up with a corresponding call 99 // to OnFinishResolutionWithStatus() or OnCancelResolution(). 100 virtual void OnStartResolution(int id, const RequestInfo& info) = 0; 101 102 // Called on completion of request |id|. Note that if the request was 103 // cancelled, OnCancelResolution() will be called instead. 104 virtual void OnFinishResolutionWithStatus(int id, bool was_resolved, 105 const RequestInfo& info) = 0; 106 107 // Called when request |id| has been cancelled. A request is "cancelled" 108 // if either the HostResolver is destroyed while a resolution is in 109 // progress, or HostResolver::CancelRequest() is called. 110 virtual void OnCancelResolution(int id, const RequestInfo& info) = 0; 111 }; 112 113 // Opaque type used to cancel a request. 114 typedef void* RequestHandle; 115 116 // Resolves the given hostname (or IP address literal), filling out the 117 // |addresses| object upon success. The |info.port| parameter will be set as 118 // the sin(6)_port field of the sockaddr_in{6} struct. Returns OK if 119 // successful or an error code upon failure. 120 // 121 // When callback is null, the operation completes synchronously. 122 // 123 // When callback is non-null, the operation may be performed asynchronously. 124 // If the operation cannnot be completed synchronously, ERR_IO_PENDING will 125 // be returned and the real result code will be passed to the completion 126 // callback. Otherwise the result code is returned immediately from this 127 // call. 128 // If |out_req| is non-NULL, then |*out_req| will be filled with a handle to 129 // the async request. This handle is not valid after the request has 130 // completed. 131 // 132 // Profiling information for the request is saved to |load_log| if non-NULL. 133 virtual int Resolve(const RequestInfo& info, 134 AddressList* addresses, 135 CompletionCallback* callback, 136 RequestHandle* out_req, 137 LoadLog* load_log) = 0; 138 139 // Cancels the specified request. |req| is the handle returned by Resolve(). 140 // After a request is cancelled, its completion callback will not be called. 141 virtual void CancelRequest(RequestHandle req) = 0; 142 143 // Adds an observer to this resolver. The observer will be notified of the 144 // start and completion of all requests (excluding cancellation). |observer| 145 // must remain valid for the duration of this HostResolver's lifetime. 146 virtual void AddObserver(Observer* observer) = 0; 147 148 // Unregisters an observer previously added by AddObserver(). 149 virtual void RemoveObserver(Observer* observer) = 0; 150 151 // TODO(eroman): temp hack for http://crbug.com/18373 152 virtual void Shutdown() = 0; 153 154 // Sets the default AddressFamily to use when requests have left it 155 // unspecified. For example, this could be used to restrict resolution 156 // results to AF_INET by passing in ADDRESS_FAMILY_IPV4, or to 157 // AF_INET6 by passing in ADDRESS_FAMILY_IPV6. 158 virtual void SetDefaultAddressFamily(AddressFamily address_family) {} 159 160 // Returns true if this HostResolver is an instance of HostResolverImpl. 161 // Used primarily to expose additional functionality on the 162 // about:net-internals page. 163 virtual bool IsHostResolverImpl() { return false; } 164 165 protected: 166 friend class base::RefCountedThreadSafe<HostResolver>; 167 168 HostResolver() { } 169 170 // If any completion callbacks are pending when the resolver is destroyed, 171 // the host resolutions are cancelled, and the completion callbacks will not 172 // be called. 173 virtual ~HostResolver() {} 174 175 private: 176 DISALLOW_COPY_AND_ASSIGN(HostResolver); 177}; 178 179// This class represents the task of resolving a hostname (or IP address 180// literal) to an AddressList object. It wraps HostResolver to resolve only a 181// single hostname at a time and cancels this request when going out of scope. 182class SingleRequestHostResolver { 183 public: 184 explicit SingleRequestHostResolver(HostResolver* resolver); 185 186 // If a completion callback is pending when the resolver is destroyed, the 187 // host resolution is cancelled, and the completion callback will not be 188 // called. 189 ~SingleRequestHostResolver(); 190 191 // Resolves the given hostname (or IP address literal), filling out the 192 // |addresses| object upon success. See HostResolver::Resolve() for details. 193 int Resolve(const HostResolver::RequestInfo& info, 194 AddressList* addresses, 195 CompletionCallback* callback, 196 LoadLog* load_log); 197 198 // Cancels the in-progress request, if any. This prevents the callback 199 // from being invoked. Resolve() can be called again after cancelling. 200 void Cancel(); 201 202 private: 203 // Callback for when the request to |resolver_| completes, so we dispatch 204 // to the user's callback. 205 void OnResolveCompletion(int result); 206 207 // The actual host resolver that will handle the request. 208 scoped_refptr<HostResolver> resolver_; 209 210 // The current request (if any). 211 HostResolver::RequestHandle cur_request_; 212 CompletionCallback* cur_request_callback_; 213 214 // Completion callback for when request to |resolver_| completes. 215 net::CompletionCallbackImpl<SingleRequestHostResolver> callback_; 216 217 DISALLOW_COPY_AND_ASSIGN(SingleRequestHostResolver); 218}; 219 220// Creates a HostResolver implementation that queries the underlying system. 221// (Except if a unit-test has changed the global HostResolverProc using 222// ScopedHostResolverProc to intercept requests to the system). 223// |network_change_notifier| must outlive HostResolver. It can optionally be 224// NULL, in which case HostResolver will not respond to network changes. 225HostResolver* CreateSystemHostResolver( 226 NetworkChangeNotifier* network_change_notifier); 227 228} // namespace net 229 230#endif // NET_BASE_HOST_RESOLVER_H_ 231