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.
5 #ifndef NET_QUIC_QUIC_STREAM_FACTORY_H_
6 #define NET_QUIC_QUIC_STREAM_FACTORY_H_
13 #include "base/logging.h"
14 #include "base/memory/weak_ptr.h"
15 #include "net/base/address_list.h"
16 #include "net/base/completion_callback.h"
17 #include "net/base/host_port_pair.h"
18 #include "net/base/network_change_notifier.h"
19 #include "net/cert/cert_database.h"
20 #include "net/log/net_log.h"
21 #include "net/proxy/proxy_server.h"
22 #include "net/quic/network_connection.h"
23 #include "net/quic/quic_config.h"
24 #include "net/quic/quic_crypto_stream.h"
25 #include "net/quic/quic_http_stream.h"
26 #include "net/quic/quic_protocol.h"
31 class ChannelIDService
;
32 class ClientSocketFactory
;
34 class HttpServerProperties
;
36 class QuicClientSession
;
37 class QuicConnectionHelper
;
38 class QuicCryptoClientStreamFactory
;
40 class QuicServerInfoFactory
;
42 class QuicStreamFactory
;
43 class TransportSecurityState
;
46 class QuicStreamFactoryPeer
;
49 // Encapsulates a pending request for a QuicHttpStream.
50 // If the request is still pending when it is destroyed, it will
51 // cancel the request with the factory.
52 class NET_EXPORT_PRIVATE QuicStreamRequest
{
54 explicit QuicStreamRequest(QuicStreamFactory
* factory
);
57 // For http, |is_https| is false.
58 int Request(const HostPortPair
& host_port_pair
,
60 PrivacyMode privacy_mode
,
61 base::StringPiece method
,
62 const BoundNetLog
& net_log
,
63 const CompletionCallback
& callback
);
65 void OnRequestComplete(int rv
);
67 scoped_ptr
<QuicHttpStream
> ReleaseStream();
69 void set_stream(scoped_ptr
<QuicHttpStream
> stream
);
71 const BoundNetLog
& net_log() const{
76 QuicStreamFactory
* factory_
;
77 HostPortPair host_port_pair_
;
79 CompletionCallback callback_
;
80 scoped_ptr
<QuicHttpStream
> stream_
;
82 DISALLOW_COPY_AND_ASSIGN(QuicStreamRequest
);
85 // A factory for creating new QuicHttpStreams on top of a pool of
86 // QuicClientSessions.
87 class NET_EXPORT_PRIVATE QuicStreamFactory
88 : public NetworkChangeNotifier::IPAddressObserver
,
89 public CertDatabase::Observer
{
92 HostResolver
* host_resolver
,
93 ClientSocketFactory
* client_socket_factory
,
94 base::WeakPtr
<HttpServerProperties
> http_server_properties
,
95 CertVerifier
* cert_verifier
,
96 ChannelIDService
* channel_id_service
,
97 TransportSecurityState
* transport_security_state
,
98 QuicCryptoClientStreamFactory
* quic_crypto_client_stream_factory
,
99 QuicRandom
* random_generator
,
101 size_t max_packet_length
,
102 const std::string
& user_agent_id
,
103 const QuicVersionVector
& supported_versions
,
104 bool enable_port_selection
,
105 bool always_require_handshake_confirmation
,
106 bool disable_connection_pooling
,
107 float load_server_info_timeout_srtt_multiplier
,
108 bool enable_connection_racing
,
109 bool enable_non_blocking_io
,
110 bool disable_disk_cache
,
111 int max_number_of_lossy_connections
,
112 float packet_loss_threshold
,
113 int socket_receive_buffer_size
,
114 const QuicTagVector
& connection_options
);
115 ~QuicStreamFactory() override
;
117 // Creates a new QuicHttpStream to |host_port_pair| which will be
118 // owned by |request|. |is_https| specifies if the protocol is https or not.
119 // If a matching session already exists, this method will return OK. If no
120 // matching session exists, this will return ERR_IO_PENDING and will invoke
121 // OnRequestComplete asynchronously.
122 int Create(const HostPortPair
& host_port_pair
,
124 PrivacyMode privacy_mode
,
125 base::StringPiece method
,
126 const BoundNetLog
& net_log
,
127 QuicStreamRequest
* request
);
129 // Returns false if |packet_loss_rate| is less than |packet_loss_threshold_|
130 // otherwise it returns true and closes the session and marks QUIC as recently
131 // broken for the port of the session. Increments
132 // |number_of_lossy_connections_| by port.
133 bool OnHandshakeConfirmed(QuicClientSession
* session
, float packet_loss_rate
);
135 // Returns true if QUIC is disabled for this port.
136 bool IsQuicDisabled(uint16 port
);
138 // Called by a session when it becomes idle.
139 void OnIdleSession(QuicClientSession
* session
);
141 // Called by a session when it is going away and no more streams should be
143 void OnSessionGoingAway(QuicClientSession
* session
);
145 // Called by a session after it shuts down.
146 void OnSessionClosed(QuicClientSession
* session
);
148 // Called by a session whose connection has timed out.
149 void OnSessionConnectTimeout(QuicClientSession
* session
);
151 // Cancels a pending request.
152 void CancelRequest(QuicStreamRequest
* request
);
154 // Closes all current sessions.
155 void CloseAllSessions(int error
);
157 base::Value
* QuicStreamFactoryInfoToValue() const;
159 // Delete all cached state objects in |crypto_config_|.
160 void ClearCachedStatesInCryptoConfig();
162 // NetworkChangeNotifier::IPAddressObserver methods:
164 // Until the servers support roaming, close all connections when the local
165 // IP address changes.
166 void OnIPAddressChanged() override
;
168 // CertDatabase::Observer methods:
170 // We close all sessions when certificate database is changed.
171 void OnCertAdded(const X509Certificate
* cert
) override
;
172 void OnCACertChanged(const X509Certificate
* cert
) override
;
174 bool require_confirmation() const {
175 return require_confirmation_
;
178 void set_require_confirmation(bool require_confirmation
);
180 QuicConnectionHelper
* helper() { return helper_
.get(); }
182 bool enable_port_selection() const { return enable_port_selection_
; }
184 bool has_quic_server_info_factory() {
185 return quic_server_info_factory_
!= NULL
;
188 void set_quic_server_info_factory(
189 QuicServerInfoFactory
* quic_server_info_factory
) {
190 DCHECK(!quic_server_info_factory_
);
191 quic_server_info_factory_
= quic_server_info_factory
;
194 bool enable_connection_racing() const { return enable_connection_racing_
; }
195 void set_enable_connection_racing(bool enable_connection_racing
) {
196 enable_connection_racing_
= enable_connection_racing
;
201 friend class test::QuicStreamFactoryPeer
;
203 // The key used to find session by ip. Includes
204 // the ip address, port, and scheme.
205 struct NET_EXPORT_PRIVATE IpAliasKey
{
207 IpAliasKey(IPEndPoint ip_endpoint
, bool is_https
);
210 IPEndPoint ip_endpoint
;
213 // Needed to be an element of std::set.
214 bool operator<(const IpAliasKey
&other
) const;
215 bool operator==(const IpAliasKey
&other
) const;
218 typedef std::map
<QuicServerId
, QuicClientSession
*> SessionMap
;
219 typedef std::map
<QuicClientSession
*, QuicServerId
> SessionIdMap
;
220 typedef std::set
<QuicServerId
> AliasSet
;
221 typedef std::map
<QuicClientSession
*, AliasSet
> SessionAliasMap
;
222 typedef std::set
<QuicClientSession
*> SessionSet
;
223 typedef std::map
<IpAliasKey
, SessionSet
> IPAliasMap
;
224 typedef std::map
<QuicServerId
, QuicCryptoClientConfig
*> CryptoConfigMap
;
225 typedef std::set
<Job
*> JobSet
;
226 typedef std::map
<QuicServerId
, JobSet
> JobMap
;
227 typedef std::map
<QuicStreamRequest
*, QuicServerId
> RequestMap
;
228 typedef std::set
<QuicStreamRequest
*> RequestSet
;
229 typedef std::map
<QuicServerId
, RequestSet
> ServerIDRequestsMap
;
231 // Creates a job which doesn't wait for server config to be loaded from the
232 // disk cache. This job is started via a PostTask.
233 void CreateAuxilaryJob(const QuicServerId server_id
,
235 const BoundNetLog
& net_log
);
237 // Returns a newly created QuicHttpStream owned by the caller, if a
238 // matching session already exists. Returns NULL otherwise.
239 scoped_ptr
<QuicHttpStream
> CreateIfSessionExists(const QuicServerId
& key
,
240 const BoundNetLog
& net_log
);
242 bool OnResolution(const QuicServerId
& server_id
,
243 const AddressList
& address_list
);
244 void OnJobComplete(Job
* job
, int rv
);
245 bool HasActiveSession(const QuicServerId
& server_id
) const;
246 bool HasActiveJob(const QuicServerId
& server_id
) const;
247 int CreateSession(const QuicServerId
& server_id
,
248 scoped_ptr
<QuicServerInfo
> quic_server_info
,
249 const AddressList
& address_list
,
250 base::TimeTicks dns_resolution_end_time
,
251 const BoundNetLog
& net_log
,
252 QuicClientSession
** session
);
253 void ActivateSession(const QuicServerId
& key
,
254 QuicClientSession
* session
);
256 // Returns |srtt| in micro seconds from ServerNetworkStats. Returns 0 if there
257 // is no |http_server_properties_| or if |http_server_properties_| doesn't
258 // have ServerNetworkStats for the given |server_id|.
259 int64
GetServerNetworkStatsSmoothedRttInMicroseconds(
260 const QuicServerId
& server_id
) const;
263 bool WasQuicRecentlyBroken(const QuicServerId
& server_id
) const;
264 bool CryptoConfigCacheIsEmpty(const QuicServerId
& server_id
);
266 // Initializes the cached state associated with |server_id| in
267 // |crypto_config_| with the information in |server_info|.
268 void InitializeCachedStateInCryptoConfig(
269 const QuicServerId
& server_id
,
270 const scoped_ptr
<QuicServerInfo
>& server_info
);
272 void ProcessGoingAwaySession(QuicClientSession
* session
,
273 const QuicServerId
& server_id
,
274 bool was_session_active
);
276 bool require_confirmation_
;
277 HostResolver
* host_resolver_
;
278 ClientSocketFactory
* client_socket_factory_
;
279 base::WeakPtr
<HttpServerProperties
> http_server_properties_
;
280 TransportSecurityState
* transport_security_state_
;
281 QuicServerInfoFactory
* quic_server_info_factory_
;
282 QuicCryptoClientStreamFactory
* quic_crypto_client_stream_factory_
;
283 QuicRandom
* random_generator_
;
284 scoped_ptr
<QuicClock
> clock_
;
285 const size_t max_packet_length_
;
287 // The helper used for all connections.
288 scoped_ptr
<QuicConnectionHelper
> helper_
;
290 // Contains owning pointers to all sessions that currently exist.
291 SessionIdMap all_sessions_
;
292 // Contains non-owning pointers to currently active session
293 // (not going away session, once they're implemented).
294 SessionMap active_sessions_
;
295 // Map from session to set of aliases that this session is known by.
296 SessionAliasMap session_aliases_
;
297 // Map from IP address to sessions which are connected to this address.
298 IPAliasMap ip_aliases_
;
300 // Origins which have gone away recently.
301 AliasSet gone_away_aliases_
;
303 const QuicConfig config_
;
304 QuicCryptoClientConfig crypto_config_
;
307 ServerIDRequestsMap job_requests_map_
;
308 RequestMap active_requests_
;
310 QuicVersionVector supported_versions_
;
312 // Determine if we should consistently select a client UDP port. If false,
313 // then we will just let the OS select a random client port for each new
315 bool enable_port_selection_
;
317 // Set if we always require handshake confirmation. If true, this will
318 // introduce at least one RTT for the handshake before the client sends data.
319 bool always_require_handshake_confirmation_
;
321 // Set if we do not want connection pooling.
322 bool disable_connection_pooling_
;
324 // Specifies the ratio between time to load QUIC server information from disk
325 // cache to 'smoothed RTT'. This ratio is used to calculate the timeout in
326 // milliseconds to wait for loading of QUIC server information. If we don't
327 // want to timeout, set |load_server_info_timeout_srtt_multiplier_| to 0.
328 float load_server_info_timeout_srtt_multiplier_
;
330 // Set if we want to race connections - one connection that sends
331 // INCHOATE_HELLO and another connection that sends CHLO after loading server
332 // config from the disk cache.
333 bool enable_connection_racing_
;
335 // Set if experimental non-blocking IO should be used on windows sockets.
336 bool enable_non_blocking_io_
;
338 // Set if we do not want to load server config from the disk cache.
339 bool disable_disk_cache_
;
341 // Set if we want to disable QUIC when there is high packet loss rate.
342 // Specifies the maximum number of connections with high packet loss in a row
343 // after which QUIC will be disabled.
344 int max_number_of_lossy_connections_
;
345 // Specifies packet loss rate in fraction after which a connection is closed
346 // and is considered as a lossy connection.
347 float packet_loss_threshold_
;
348 // Count number of lossy connections by port.
349 std::map
<uint16
, int> number_of_lossy_connections_
;
351 // Size of the UDP receive buffer.
352 int socket_receive_buffer_size_
;
354 // Each profile will (probably) have a unique port_seed_ value. This value
355 // is used to help seed a pseudo-random number generator (PortSuggester) so
356 // that we consistently (within this profile) suggest the same ephemeral
357 // port when we re-connect to any given server/port. The differences between
358 // profiles (probablistically) prevent two profiles from colliding in their
359 // ephemeral port requests.
362 // Local address of socket that was created in CreateSession.
363 IPEndPoint local_address_
;
364 bool check_persisted_supports_quic_
;
365 std::set
<HostPortPair
> quic_supported_servers_at_startup_
;
367 NetworkConnection network_connection_
;
369 base::TaskRunner
* task_runner_
;
371 base::WeakPtrFactory
<QuicStreamFactory
> weak_factory_
;
373 DISALLOW_COPY_AND_ASSIGN(QuicStreamFactory
);
378 #endif // NET_QUIC_QUIC_STREAM_FACTORY_H_