1 // Copyright (c) 2012 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_HTTP_HTTP_SERVER_PROPERTIES_H_
6 #define NET_HTTP_HTTP_SERVER_PROPERTIES_H_
7 
8 #include <stddef.h>
9 #include <stdint.h>
10 
11 #include <map>
12 #include <memory>
13 #include <set>
14 #include <string>
15 #include <tuple>
16 #include <vector>
17 
18 #include "base/callback.h"
19 #include "base/containers/mru_cache.h"
20 #include "base/macros.h"
21 #include "base/memory/weak_ptr.h"
22 #include "base/optional.h"
23 #include "base/threading/thread_checker.h"
24 #include "base/time/time.h"
25 #include "base/timer/timer.h"
26 #include "base/values.h"
27 #include "net/base/host_port_pair.h"
28 #include "net/base/ip_address.h"
29 #include "net/base/net_export.h"
30 #include "net/base/network_isolation_key.h"
31 #include "net/http/alternative_service.h"
32 #include "net/http/broken_alternative_services.h"
33 #include "net/third_party/quiche/src/quic/core/quic_bandwidth.h"
34 #include "net/third_party/quiche/src/quic/core/quic_server_id.h"
35 #include "net/third_party/quiche/src/quic/core/quic_versions.h"
36 #include "net/third_party/quiche/src/spdy/core/spdy_framer.h"  // TODO(willchan): Reconsider this.
37 #include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
38 #include "url/scheme_host_port.h"
39 
40 namespace base {
41 class Clock;
42 class TickClock;
43 class Value;
44 }
45 
46 namespace net {
47 
48 class HttpServerPropertiesManager;
49 class IPAddress;
50 class NetLog;
51 struct SSLConfig;
52 
53 struct NET_EXPORT SupportsQuic {
SupportsQuicSupportsQuic54   SupportsQuic() : used_quic(false) {}
SupportsQuicSupportsQuic55   SupportsQuic(bool used_quic, const std::string& address)
56       : used_quic(used_quic), address(address) {}
57 
EqualsSupportsQuic58   bool Equals(const SupportsQuic& other) const {
59     return used_quic == other.used_quic && address == other.address;
60   }
61 
62   bool used_quic;
63   std::string address;
64 };
65 
66 struct NET_EXPORT ServerNetworkStats {
ServerNetworkStatsServerNetworkStats67   ServerNetworkStats() : bandwidth_estimate(quic::QuicBandwidth::Zero()) {}
68 
69   bool operator==(const ServerNetworkStats& other) const {
70     return srtt == other.srtt && bandwidth_estimate == other.bandwidth_estimate;
71   }
72 
73   bool operator!=(const ServerNetworkStats& other) const {
74     return !this->operator==(other);
75   }
76 
77   base::TimeDelta srtt;
78   quic::QuicBandwidth bandwidth_estimate;
79 };
80 
81 typedef std::vector<AlternativeService> AlternativeServiceVector;
82 
83 // Store at most 200 MRU RecentlyBrokenAlternativeServices in memory and disk.
84 // This ideally would be with the other constants in HttpServerProperties, but
85 // has to go here instead of prevent a circular dependency.
86 const int kMaxRecentlyBrokenAlternativeServiceEntries = 200;
87 
88 // Store at most 5 MRU QUIC servers by default. This is mainly used by cronet.
89 const int kDefaultMaxQuicServerEntries = 5;
90 
91 // The interface for setting/retrieving the HTTP server properties.
92 // Currently, this class manages servers':
93 // * HTTP/2 support;
94 // * Alternative Service support;
95 // * QUIC data (like ServerNetworkStats and QuicServerInfo).
96 //
97 // Optionally retrieves and saves properties from/to disk. This class is not
98 // threadsafe.
99 class NET_EXPORT HttpServerProperties
100     : public BrokenAlternativeServices::Delegate {
101  public:
102   // Store at most 500 MRU ServerInfos in memory and disk.
103   static const int kMaxServerInfoEntries = 500;
104 
105   // Provides an interface to interact with persistent preferences storage
106   // implemented by the embedder. The prefs are assumed not to have been loaded
107   // before HttpServerPropertiesManager construction.
108   class NET_EXPORT PrefDelegate {
109    public:
110     virtual ~PrefDelegate();
111 
112     // Returns the branch of the preferences system for the server properties.
113     // Returns nullptr if the pref system has no data for the server properties.
114     virtual const base::DictionaryValue* GetServerProperties() const = 0;
115 
116     // Sets the server properties to the given value. If |callback| is
117     // non-empty, flushes data to persistent storage and invokes |callback|
118     // asynchronously when complete.
119     virtual void SetServerProperties(const base::DictionaryValue& value,
120                                      base::OnceClosure callback) = 0;
121 
122     // Starts listening for prefs to be loaded. If prefs are already loaded,
123     // |pref_loaded_callback| will be invoked asynchronously. Callback will be
124     // invoked even if prefs fail to load. Will only be called once by the
125     // HttpServerPropertiesManager.
126     virtual void WaitForPrefLoad(base::OnceClosure pref_loaded_callback) = 0;
127   };
128 
129   // Contains metadata about a particular server. Note that all methods that
130   // take a "SchemeHostPort" expect schemes of ws and wss to be mapped to http
131   // and https, respectively. See GetNormalizedSchemeHostPort().
132   struct NET_EXPORT ServerInfo {
133     ServerInfo();
134     ServerInfo(const ServerInfo& server_info);
135     ServerInfo(ServerInfo&& server_info);
136     ~ServerInfo();
137 
138     // Returns true if no fields are populated.
139     bool empty() const;
140 
141     // Used in tests.
142     bool operator==(const ServerInfo& other) const;
143 
144     // IMPORTANT:  When adding a field here, be sure to update
145     // HttpServerProperties::OnServerInfoLoaded() as well as
146     // HttpServerPropertiesManager to correctly load/save the from/to the pref
147     // store.
148 
149     // Whether or not a server is known to support H2/SPDY. False indicates
150     // known lack of support, true indicates known support, and not set
151     // indicates unknown. The difference between false and not set only matters
152     // when loading from disk, when an initialized false value will take
153     // priority over a not set value.
154     base::Optional<bool> supports_spdy;
155 
156     // True if the server has previously indicated it required HTTP/1.1. Unlike
157     // other fields, not persisted to disk.
158     base::Optional<bool> requires_http11;
159 
160     base::Optional<AlternativeServiceInfoVector> alternative_services;
161     base::Optional<ServerNetworkStats> server_network_stats;
162   };
163 
164   struct NET_EXPORT ServerInfoMapKey {
165     // If |use_network_isolation_key| is false, an empty NetworkIsolationKey is
166     // used instead of |network_isolation_key|. Note that |server| can be passed
167     // in via std::move(), since most callsites can pass a recently created
168     // SchemeHostPort.
169     ServerInfoMapKey(url::SchemeHostPort server,
170                      const NetworkIsolationKey& network_isolation_key,
171                      bool use_network_isolation_key);
172     ~ServerInfoMapKey();
173 
174     bool operator<(const ServerInfoMapKey& other) const;
175 
176     // IMPORTANT: The constructor normalizes the scheme so that "ws" is replaced
177     // by "http" and "wss" by "https", so this should never be compared directly
178     // with values passed into to HttpServerProperties methods.
179     url::SchemeHostPort server;
180 
181     NetworkIsolationKey network_isolation_key;
182   };
183 
184   class NET_EXPORT ServerInfoMap
185       : public base::MRUCache<ServerInfoMapKey, ServerInfo> {
186    public:
187     ServerInfoMap();
188 
189     // If there's an entry corresponding to |key|, brings that entry to the
190     // front and returns an iterator to it. Otherwise, inserts an empty
191     // ServerInfo using |key|, and returns an iterator to it.
192     iterator GetOrPut(const ServerInfoMapKey& key);
193 
194     // Erases the ServerInfo identified by |server_info_it| if no fields have
195     // data. The iterator must point to an entry in the map. Regardless of
196     // whether the entry is removed or not, returns iterator for the next entry.
197     iterator EraseIfEmpty(iterator server_info_it);
198 
199    private:
200     DISALLOW_COPY_AND_ASSIGN(ServerInfoMap);
201   };
202 
203   struct NET_EXPORT QuicServerInfoMapKey {
204     // If |use_network_isolation_key| is false, an empty NetworkIsolationKey is
205     // used instead of |network_isolation_key|.
206     QuicServerInfoMapKey(const quic::QuicServerId& server_id,
207                          const NetworkIsolationKey& network_isolation_key,
208                          bool use_network_isolation_key);
209     ~QuicServerInfoMapKey();
210 
211     bool operator<(const QuicServerInfoMapKey& other) const;
212 
213     // Used in tests.
214     bool operator==(const QuicServerInfoMapKey& other) const;
215 
216     quic::QuicServerId server_id;
217     NetworkIsolationKey network_isolation_key;
218   };
219 
220   // Max number of quic servers to store is not hardcoded and can be set.
221   // Because of this, QuicServerInfoMap will not be a subclass of MRUCache.
222   // Separate from ServerInfoMap because the key includes privacy mode (Since
223   // this is analogous to the SSL session cache, which has separate caches for
224   // privacy mode), and each entry can be quite large, so it has its own size
225   // limit, which is much smaller than the ServerInfoMap's limit.
226   typedef base::MRUCache<QuicServerInfoMapKey, std::string> QuicServerInfoMap;
227 
228   // If a |pref_delegate| is specified, it will be used to read/write the
229   // properties to a pref file. Writes are rate limited to improve performance.
230   //
231   // |tick_clock| is used for setting expiration times and scheduling the
232   // expiration of broken alternative services. If null, default clock will be
233   // used.
234   //
235   // |clock| is used for converting base::TimeTicks to base::Time for
236   // wherever base::Time is preferable.
237   HttpServerProperties(std::unique_ptr<PrefDelegate> pref_delegate = nullptr,
238                        NetLog* net_log = nullptr,
239                        const base::TickClock* tick_clock = nullptr,
240                        base::Clock* clock = nullptr);
241 
242   ~HttpServerProperties() override;
243 
244   // Deletes all data. If |callback| is non-null, flushes data to disk
245   // and invokes the callback asynchronously once changes have been written to
246   // disk.
247   void Clear(base::OnceClosure callback);
248 
249   // Returns true if |server|, in the context of |network_isolation_key|, has
250   // previously supported a network protocol which honors request
251   // prioritization.
252   //
253   // Note that this also implies that the server supports request
254   // multiplexing, since priorities imply a relationship between
255   // multiple requests.
256   bool SupportsRequestPriority(
257       const url::SchemeHostPort& server,
258       const net::NetworkIsolationKey& network_isolation_key);
259 
260   // Returns the value set by SetSupportsSpdy(). If not set, returns false.
261   bool GetSupportsSpdy(const url::SchemeHostPort& server,
262                        const net::NetworkIsolationKey& network_isolation_key);
263 
264   // Records whether |server| supports H2 or not. Information is restricted to
265   // the context of |network_isolation_key|, to prevent cross-site information
266   // leakage.
267   void SetSupportsSpdy(const url::SchemeHostPort& server,
268                        const net::NetworkIsolationKey& network_isolation_key,
269                        bool supports_spdy);
270 
271   // Returns true if |server| has required HTTP/1.1 via HTTP/2 error code, in
272   // the context of |network_isolation_key|.
273   bool RequiresHTTP11(const url::SchemeHostPort& server,
274                       const net::NetworkIsolationKey& network_isolation_key);
275 
276   // Require HTTP/1.1 on subsequent connections, in the context of
277   // |network_isolation_key|.  Not persisted.
278   void SetHTTP11Required(const url::SchemeHostPort& server,
279                          const net::NetworkIsolationKey& network_isolation_key);
280 
281   // Modify SSLConfig to force HTTP/1.1 if necessary.
282   void MaybeForceHTTP11(const url::SchemeHostPort& server,
283                         const net::NetworkIsolationKey& network_isolation_key,
284                         SSLConfig* ssl_config);
285 
286   // Return all alternative services for |origin|, learned in the context of
287   // |network_isolation_key|, including broken ones. Returned alternative
288   // services never have empty hostnames.
289   AlternativeServiceInfoVector GetAlternativeServiceInfos(
290       const url::SchemeHostPort& origin,
291       const net::NetworkIsolationKey& network_isolation_key);
292 
293   // Set a single HTTP/2 alternative service for |origin|.  Previous
294   // alternative services for |origin| are discarded.
295   // |alternative_service.host| may be empty.
296   void SetHttp2AlternativeService(
297       const url::SchemeHostPort& origin,
298       const NetworkIsolationKey& network_isolation_key,
299       const AlternativeService& alternative_service,
300       base::Time expiration);
301 
302   // Set a single QUIC alternative service for |origin|.  Previous alternative
303   // services for |origin| are discarded.
304   // |alternative_service.host| may be empty.
305   void SetQuicAlternativeService(
306       const url::SchemeHostPort& origin,
307       const NetworkIsolationKey& network_isolation_key,
308       const AlternativeService& alternative_service,
309       base::Time expiration,
310       const quic::ParsedQuicVersionVector& advertised_versions);
311 
312   // Set alternative services for |origin|, learned in the context of
313   // |network_isolation_key|.  Previous alternative services for |origin| are
314   // discarded. Hostnames in |alternative_service_info_vector| may be empty.
315   // |alternative_service_info_vector| may be empty.
316   void SetAlternativeServices(
317       const url::SchemeHostPort& origin,
318       const net::NetworkIsolationKey& network_isolation_key,
319       const AlternativeServiceInfoVector& alternative_service_info_vector);
320 
321   // Marks |alternative_service| as broken in the context of
322   // |network_isolation_key|. |alternative_service.host| must not be empty.
323   void MarkAlternativeServiceBroken(
324       const AlternativeService& alternative_service,
325       const net::NetworkIsolationKey& network_isolation_key);
326 
327   // Marks |alternative_service| as broken in the context of
328   // |network_isolation_key| until the default network changes.
329   // |alternative_service.host| must not be empty.
330   void MarkAlternativeServiceBrokenUntilDefaultNetworkChanges(
331       const AlternativeService& alternative_service,
332       const net::NetworkIsolationKey& network_isolation_key);
333 
334   // Marks |alternative_service| as recently broken in the context of
335   // |network_isolation_key|. |alternative_service.host| must not be empty.
336   void MarkAlternativeServiceRecentlyBroken(
337       const AlternativeService& alternative_service,
338       const net::NetworkIsolationKey& network_isolation_key);
339 
340   // Returns true iff |alternative_service| is currently broken in the context
341   // of |network_isolation_key|. |alternative_service.host| must not be empty.
342   bool IsAlternativeServiceBroken(
343       const AlternativeService& alternative_service,
344       const net::NetworkIsolationKey& network_isolation_key) const;
345 
346   // Returns true iff |alternative_service| was recently broken in the context
347   // of |network_isolation_key|. |alternative_service.host| must not be empty.
348   bool WasAlternativeServiceRecentlyBroken(
349       const AlternativeService& alternative_service,
350       const net::NetworkIsolationKey& network_isolation_key);
351 
352   // Confirms that |alternative_service| is working in the context of
353   // |network_isolation_key|. |alternative_service.host| must not be empty.
354   void ConfirmAlternativeService(
355       const AlternativeService& alternative_service,
356       const net::NetworkIsolationKey& network_isolation_key);
357 
358   // Called when the default network changes.
359   // Clears all the alternative services that were marked broken until the
360   // default network changed.
361   void OnDefaultNetworkChanged();
362 
363   // Returns all alternative service mappings as human readable strings.
364   // Empty alternative service hostnames will be printed as such.
365   std::unique_ptr<base::Value> GetAlternativeServiceInfoAsValue() const;
366 
367   // Tracks the last local address when QUIC was known to work. The address
368   // cannot be set to an empty address - use
369   // ClearLastLocalAddressWhenQuicWorked() if it needs to be cleared.
370   bool WasLastLocalAddressWhenQuicWorked(const IPAddress& local_address) const;
371   bool HasLastLocalAddressWhenQuicWorked() const;
372   void SetLastLocalAddressWhenQuicWorked(
373       IPAddress last_local_address_when_quic_worked);
374   void ClearLastLocalAddressWhenQuicWorked();
375 
376   // Sets |stats| for |server|.
377   void SetServerNetworkStats(const url::SchemeHostPort& server,
378                              const NetworkIsolationKey& network_isolation_key,
379                              ServerNetworkStats stats);
380 
381   // Clears any stats for |server|.
382   void ClearServerNetworkStats(
383       const url::SchemeHostPort& server,
384       const NetworkIsolationKey& network_isolation_key);
385 
386   // Returns any stats for |server| or nullptr if there are none.
387   const ServerNetworkStats* GetServerNetworkStats(
388       const url::SchemeHostPort& server,
389       const NetworkIsolationKey& network_isolation_key);
390 
391   // Save QuicServerInfo (in std::string form) for the given |server_id|, in the
392   // context of |network_isolation_key|.
393   void SetQuicServerInfo(const quic::QuicServerId& server_id,
394                          const NetworkIsolationKey& network_isolation_key,
395                          const std::string& server_info);
396 
397   // Get QuicServerInfo (in std::string form) for the given |server_id|, in the
398   // context of |network_isolation_key|.
399   const std::string* GetQuicServerInfo(
400       const quic::QuicServerId& server_id,
401       const NetworkIsolationKey& network_isolation_key);
402 
403   // Returns all persistent QuicServerInfo objects.
404   const QuicServerInfoMap& quic_server_info_map() const;
405 
406   // Returns the number of server configs (QuicServerInfo objects) persisted.
407   size_t max_server_configs_stored_in_properties() const;
408 
409   // Sets the number of server configs (QuicServerInfo objects) to be persisted.
410   void SetMaxServerConfigsStoredInProperties(
411       size_t max_server_configs_stored_in_properties);
412 
413   // Returns whether HttpServerProperties is initialized.
414   bool IsInitialized() const;
415 
416   // BrokenAlternativeServices::Delegate method.
417   void OnExpireBrokenAlternativeService(
418       const AlternativeService& expired_alternative_service,
419       const NetworkIsolationKey& network_isolation_key) override;
420 
421   static base::TimeDelta GetUpdatePrefsDelayForTesting();
422 
423   // Test-only routines that call the methods used to load the specified
424   // field(s) from a prefs file. Unlike OnPrefsLoaded(), these may be invoked
425   // multiple times.
OnServerInfoLoadedForTesting(std::unique_ptr<ServerInfoMap> server_info_map)426   void OnServerInfoLoadedForTesting(
427       std::unique_ptr<ServerInfoMap> server_info_map) {
428     OnServerInfoLoaded(std::move(server_info_map));
429   }
OnLastLocalAddressWhenQuicWorkedForTesting(const IPAddress & last_local_address_when_quic_worked)430   void OnLastLocalAddressWhenQuicWorkedForTesting(
431       const IPAddress& last_local_address_when_quic_worked) {
432     OnLastLocalAddressWhenQuicWorkedLoaded(last_local_address_when_quic_worked);
433   }
OnQuicServerInfoMapLoadedForTesting(std::unique_ptr<QuicServerInfoMap> quic_server_info_map)434   void OnQuicServerInfoMapLoadedForTesting(
435       std::unique_ptr<QuicServerInfoMap> quic_server_info_map) {
436     OnQuicServerInfoMapLoaded(std::move(quic_server_info_map));
437   }
OnBrokenAndRecentlyBrokenAlternativeServicesLoadedForTesting(std::unique_ptr<BrokenAlternativeServiceList> broken_alternative_service_list,std::unique_ptr<RecentlyBrokenAlternativeServices> recently_broken_alternative_services)438   void OnBrokenAndRecentlyBrokenAlternativeServicesLoadedForTesting(
439       std::unique_ptr<BrokenAlternativeServiceList>
440           broken_alternative_service_list,
441       std::unique_ptr<RecentlyBrokenAlternativeServices>
442           recently_broken_alternative_services) {
443     OnBrokenAndRecentlyBrokenAlternativeServicesLoaded(
444         std::move(broken_alternative_service_list),
445         std::move(recently_broken_alternative_services));
446   }
447 
GetCanonicalSuffixForTesting(const std::string & host)448   const std::string* GetCanonicalSuffixForTesting(
449       const std::string& host) const {
450     return GetCanonicalSuffix(host);
451   }
452 
server_info_map_for_testing()453   const ServerInfoMap& server_info_map_for_testing() const {
454     return server_info_map_;
455   }
456 
457   // TODO(mmenke): Look into removing this.
properties_manager_for_testing()458   HttpServerPropertiesManager* properties_manager_for_testing() {
459     return properties_manager_.get();
460   }
461 
462  private:
463   // TODO (wangyix): modify HttpServerProperties unit tests so this
464   // friendness is no longer required.
465   friend class HttpServerPropertiesPeer;
466 
467   typedef base::flat_map<ServerInfoMapKey, url::SchemeHostPort> CanonicalMap;
468   typedef base::flat_map<QuicServerInfoMapKey, quic::QuicServerId>
469       QuicCanonicalMap;
470   typedef std::vector<std::string> CanonicalSuffixList;
471 
472   // Internal implementations of public methods. SchemeHostPort argument must be
473   // normalized before calling (ws/wss replaced with http/https). Use wrapped
474   // functions instead of putting the normalization in the public functions to
475   // reduce chance of regression - normalization in ServerInfoMapKey's
476   // constructor would leave |server.scheme| as wrong if not access through the
477   // key, and explicit normalization to create |normalized_server| means the one
478   // with the incorrect scheme would still be available.
479   bool GetSupportsSpdyInternal(
480       url::SchemeHostPort server,
481       const net::NetworkIsolationKey& network_isolation_key);
482   void SetSupportsSpdyInternal(
483       url::SchemeHostPort server,
484       const net::NetworkIsolationKey& network_isolation_key,
485       bool supports_spdy);
486   bool RequiresHTTP11Internal(
487       url::SchemeHostPort server,
488       const net::NetworkIsolationKey& network_isolation_key);
489   void SetHTTP11RequiredInternal(
490       url::SchemeHostPort server,
491       const net::NetworkIsolationKey& network_isolation_key);
492   void MaybeForceHTTP11Internal(
493       url::SchemeHostPort server,
494       const net::NetworkIsolationKey& network_isolation_key,
495       SSLConfig* ssl_config);
496   AlternativeServiceInfoVector GetAlternativeServiceInfosInternal(
497       const url::SchemeHostPort& origin,
498       const net::NetworkIsolationKey& network_isolation_key);
499   void SetAlternativeServicesInternal(
500       const url::SchemeHostPort& origin,
501       const net::NetworkIsolationKey& network_isolation_key,
502       const AlternativeServiceInfoVector& alternative_service_info_vector);
503   void SetServerNetworkStatsInternal(
504       url::SchemeHostPort server,
505       const NetworkIsolationKey& network_isolation_key,
506       ServerNetworkStats stats);
507   void ClearServerNetworkStatsInternal(
508       url::SchemeHostPort server,
509       const NetworkIsolationKey& network_isolation_key);
510   const ServerNetworkStats* GetServerNetworkStatsInternal(
511       url::SchemeHostPort server,
512       const NetworkIsolationKey& network_isolation_key);
513 
514   // Helper functions to use the passed in parameters and
515   // |use_network_isolation_key_| to create a [Quic]ServerInfoMapKey.
516   ServerInfoMapKey CreateServerInfoKey(
517       const url::SchemeHostPort& server,
518       const NetworkIsolationKey& network_isolation_key) const;
519   QuicServerInfoMapKey CreateQuicServerInfoKey(
520       const quic::QuicServerId& server_id,
521       const NetworkIsolationKey& network_isolation_key) const;
522 
523   // Return the iterator for |server| in the context of |network_isolation_key|,
524   // or for its canonical host, or end. Skips over ServerInfos without
525   // |alternative_service_info| populated.
526   ServerInfoMap::const_iterator GetIteratorWithAlternativeServiceInfo(
527       const url::SchemeHostPort& server,
528       const net::NetworkIsolationKey& network_isolation_key);
529 
530   // Return the canonical host for |server|  in the context of
531   // |network_isolation_key|, or end if none exists.
532   CanonicalMap::const_iterator GetCanonicalAltSvcHost(
533       const url::SchemeHostPort& server,
534       const net::NetworkIsolationKey& network_isolation_key) const;
535 
536   // Return the canonical host with the same canonical suffix as |server|.
537   // The returned canonical host can be used to search for server info in
538   // |quic_server_info_map_|. Return 'end' the host doesn't exist.
539   QuicCanonicalMap::const_iterator GetCanonicalServerInfoHost(
540       const QuicServerInfoMapKey& key) const;
541 
542   // Remove the canonical alt-svc host for |server| with
543   // |network_isolation_key|.
544   void RemoveAltSvcCanonicalHost(
545       const url::SchemeHostPort& server,
546       const NetworkIsolationKey& network_isolation_key);
547 
548   // Update |canonical_server_info_map_| with the new canonical host.
549   // The |key| should have the corresponding server info associated with it
550   // in |quic_server_info_map_|. If |canonical_server_info_map_| doesn't
551   // have an entry associated with |key|, the method will add one.
552   void UpdateCanonicalServerInfoMap(const QuicServerInfoMapKey& key);
553 
554   // Returns the canonical host suffix for |host|, or nullptr if none
555   // exists.
556   const std::string* GetCanonicalSuffix(const std::string& host) const;
557 
558   void OnPrefsLoaded(std::unique_ptr<ServerInfoMap> server_info_map,
559                      const IPAddress& last_local_address_when_quic_worked,
560                      std::unique_ptr<QuicServerInfoMap> quic_server_info_map,
561                      std::unique_ptr<BrokenAlternativeServiceList>
562                          broken_alternative_service_list,
563                      std::unique_ptr<RecentlyBrokenAlternativeServices>
564                          recently_broken_alternative_services);
565 
566   // These methods are called by OnPrefsLoaded to handle merging properties
567   // loaded from prefs with what has been learned while waiting for prefs to
568   // load.
569   void OnServerInfoLoaded(std::unique_ptr<ServerInfoMap> server_info_map);
570   void OnLastLocalAddressWhenQuicWorkedLoaded(
571       const IPAddress& last_local_address_when_quic_worked);
572   void OnQuicServerInfoMapLoaded(
573       std::unique_ptr<QuicServerInfoMap> quic_server_info_map);
574   void OnBrokenAndRecentlyBrokenAlternativeServicesLoaded(
575       std::unique_ptr<BrokenAlternativeServiceList>
576           broken_alternative_service_list,
577       std::unique_ptr<RecentlyBrokenAlternativeServices>
578           recently_broken_alternative_services);
579 
580   // Queue a delayed call to WriteProperties(). If |is_initialized_| is false,
581   // or |properties_manager_| is nullptr, or there's already a queued call to
582   // WriteProperties(), does nothing.
583   void MaybeQueueWriteProperties();
584 
585   // Writes cached state to |properties_manager_|, which must not be null.
586   // Invokes |callback| on completion, if non-null.
587   void WriteProperties(base::OnceClosure callback) const;
588 
589   const base::TickClock* tick_clock_;  // Unowned
590   base::Clock* clock_;                 // Unowned
591 
592   // Cached value of kPartitionHttpServerPropertiesByNetworkIsolationKey
593   // feature. Cached to improve performance.
594   const bool use_network_isolation_key_;
595 
596   // Set to true once initial properties have been retrieved from disk by
597   // |properties_manager_|. Always true if |properties_manager_| is nullptr.
598   bool is_initialized_;
599 
600   // Queue a write when resources finish loading. Set to true when
601   // MaybeQueueWriteProperties() is invoked while still waiting on
602   // initialization to complete.
603   bool queue_write_on_load_;
604 
605   // Used to load/save properties from/to preferences. May be nullptr.
606   std::unique_ptr<HttpServerPropertiesManager> properties_manager_;
607 
608   ServerInfoMap server_info_map_;
609 
610   BrokenAlternativeServices broken_alternative_services_;
611 
612   IPAddress last_local_address_when_quic_worked_;
613   // Contains a map of servers which could share the same alternate protocol.
614   // Map from a Canonical scheme/host/port/NIK (host is some postfix of host
615   // names) to an actual origin, which has a plausible alternate protocol
616   // mapping.
617   CanonicalMap canonical_alt_svc_map_;
618 
619   // Contains list of suffixes (for example ".c.youtube.com",
620   // ".googlevideo.com", ".googleusercontent.com") of canonical hostnames.
621   const CanonicalSuffixList canonical_suffixes_;
622 
623   QuicServerInfoMap quic_server_info_map_;
624 
625   // Maps canonical suffixes to host names that have the same canonical suffix
626   // and have a corresponding entry in |quic_server_info_map_|. The map can be
627   // used to quickly look for server info for hosts that share the same
628   // canonical suffix but don't have exact match in |quic_server_info_map_|. The
629   // map exists solely to improve the search performance. It only contains
630   // derived data that can be recalculated by traversing
631   // |quic_server_info_map_|.
632   QuicCanonicalMap canonical_server_info_map_;
633 
634   size_t max_server_configs_stored_in_properties_;
635 
636   // Used to post calls to WriteProperties().
637   base::OneShotTimer prefs_update_timer_;
638 
639   THREAD_CHECKER(thread_checker_);
640 
641   DISALLOW_COPY_AND_ASSIGN(HttpServerProperties);
642 };
643 
644 }  // namespace net
645 
646 #endif  // NET_HTTP_HTTP_SERVER_PROPERTIES_H_
647