blob: b6b71c284f18cc2f148bf2734b03867a30c9411b [file] [log] [blame]
Avi Drissman64595482022-09-14 20:52:291// Copyright 2012 The Chromium Authors
license.botbf09a502008-08-24 00:55:552// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
initial.commit586acc5fe2008-07-26 22:42:524
[email protected]f7984fc62009-06-22 23:26:445#ifndef NET_SOCKET_CLIENT_SOCKET_HANDLE_H_
6#define NET_SOCKET_CLIENT_SOCKET_HANDLE_H_
initial.commit586acc5fe2008-07-26 22:42:527
danakj655b66c2016-04-16 00:51:388#include <memory>
David Benjamin0c616162018-03-23 22:15:479#include <utility>
[email protected]7b822b2b2008-08-05 00:15:4510
Hans Wennborg0cb546b2020-06-23 18:00:0911#include "base/check.h"
Avi Drissman41c4a412023-01-11 22:45:3712#include "base/functional/bind.h"
Keishi Hattori0e45c022021-11-27 09:25:5213#include "base/memory/raw_ptr.h"
Lei Zhang58a1082452022-11-08 04:23:2014#include "base/memory/scoped_refptr.h"
[email protected]f002abb2013-06-28 02:30:2115#include "base/time/time.h"
ttuttle1f2d7e92015-04-28 16:17:4716#include "net/base/ip_endpoint.h"
[email protected]d207a5f2009-06-04 05:28:4017#include "net/base/load_states.h"
[email protected]034df0f32013-01-07 23:17:4818#include "net/base/load_timing_info.h"
[email protected]d80a4322009-08-14 07:07:4919#include "net/base/net_errors.h"
[email protected]172da1b2011-08-12 15:52:2620#include "net/base/net_export.h"
[email protected]ac790b42009-12-02 04:31:3121#include "net/base/request_priority.h"
dalykedd30d982019-12-16 15:31:1022#include "net/dns/public/resolve_error_info.h"
mikecironef22f9812016-10-04 03:40:1923#include "net/log/net_log_source.h"
24#include "net/log/net_log_with_source.h"
[email protected]d80a4322009-08-14 07:07:4925#include "net/socket/client_socket_pool.h"
ttuttle1f2d7e92015-04-28 16:17:4726#include "net/socket/connection_attempts.h"
[email protected]3268023f2011-05-05 00:08:1027#include "net/socket/stream_socket.h"
Matt Menke39b7c5a2019-04-10 19:47:5128#include "net/ssl/ssl_cert_request_info.h"
Anton Bikineev068d2912021-05-15 20:43:5229#include "third_party/abseil-cpp/absl/types/optional.h"
initial.commit586acc5fe2008-07-26 22:42:5230
31namespace net {
32
Matt Menkec1ae1d52019-04-10 19:28:2733class ConnectJob;
Matt Menkef09e64c2019-04-23 22:16:2834struct NetworkTrafficAnnotationTag;
Paul Jensen8d6f87ec2018-01-13 00:46:5435class SocketTag;
36
[email protected]3268023f2011-05-05 00:08:1037// A container for a StreamSocket.
initial.commit586acc5fe2008-07-26 22:42:5238//
Matt Menkef6edce752019-03-19 17:21:5639// The handle's |group_id| uniquely identifies the origin and type of the
[email protected]e1e06262008-08-06 23:57:0740// connection. It is used by the ClientSocketPool to group similar connected
41// client socket objects.
initial.commit586acc5fe2008-07-26 22:42:5242//
[email protected]172da1b2011-08-12 15:52:2643class NET_EXPORT ClientSocketHandle {
initial.commit586acc5fe2008-07-26 22:42:5244 public:
[email protected]be1a48b2011-01-20 00:12:1345 enum SocketReuseType {
[email protected]a19f1c602009-08-24 21:35:2846 UNUSED = 0, // unused socket that just finished connecting
[email protected]cd273122009-08-22 21:20:1147 UNUSED_IDLE, // unused socket that has been idle for awhile
48 REUSED_IDLE, // previously used socket
[email protected]f9d285c2009-08-17 19:54:2949 NUM_TYPES,
[email protected]be1a48b2011-01-20 00:12:1350 };
[email protected]f9d285c2009-08-17 19:54:2951
[email protected]a512f5982009-08-18 16:01:0652 ClientSocketHandle();
Peter Boström293b1342021-09-22 17:31:4353
54 ClientSocketHandle(const ClientSocketHandle&) = delete;
55 ClientSocketHandle& operator=(const ClientSocketHandle&) = delete;
56
[email protected]e1e06262008-08-06 23:57:0757 ~ClientSocketHandle();
initial.commit586acc5fe2008-07-26 22:42:5258
[email protected]e1e06262008-08-06 23:57:0759 // Initializes a ClientSocketHandle object, which involves talking to the
[email protected]d207a5f2009-06-04 05:28:4060 // ClientSocketPool to obtain a connected socket, possibly reusing one. This
61 // method returns either OK or ERR_IO_PENDING. On ERR_IO_PENDING, |priority|
62 // is used to determine the placement in ClientSocketPool's wait list.
mmenked3641e12016-01-28 16:06:1563 // If |respect_limits| is DISABLED, will bypass the wait list, but |priority|
64 // must also be HIGHEST, if set.
initial.commit586acc5fe2008-07-26 22:42:5265 //
66 // If this method succeeds, then the socket member will be set to an existing
[email protected]d207a5f2009-06-04 05:28:4067 // connected socket if an existing connected socket was available to reuse,
68 // otherwise it will be set to a new connected socket. Consumers can then
69 // call is_reused() to see if the socket was reused. If not reusing an
[email protected]2884a462009-06-15 05:08:4270 // existing socket, ClientSocketPool may need to establish a new
[email protected]d80a4322009-08-14 07:07:4971 // connection using |socket_params|.
initial.commit586acc5fe2008-07-26 22:42:5272 //
73 // This method returns ERR_IO_PENDING if it cannot complete synchronously, in
[email protected]d207a5f2009-06-04 05:28:4074 // which case the consumer will be notified of completion via |callback|.
initial.commit586acc5fe2008-07-26 22:42:5275 //
[email protected]e772db3f2010-07-12 18:11:1376 // If the pool was not able to reuse an existing socket, the new socket
77 // may report a recoverable error. In this case, the return value will
78 // indicate an error and the socket member will be set. If it is determined
79 // that the error is not recoverable, the Disconnect method should be used
80 // on the socket, so that it does not get reused.
81 //
[email protected]e60e47a2010-07-14 03:37:1882 // A non-recoverable error may set additional state in the ClientSocketHandle
83 // to allow the caller to determine what went wrong.
84 //
initial.commit586acc5fe2008-07-26 22:42:5285 // Init may be called multiple times.
86 //
[email protected]9e743cd2010-03-16 07:03:5387 // Profiling information for the request is saved to |net_log| if non-NULL.
Matt Menkef09e64c2019-04-23 22:16:2888 int Init(
89 const ClientSocketPool::GroupId& group_id,
90 scoped_refptr<ClientSocketPool::SocketParams> socket_params,
Anton Bikineev068d2912021-05-15 20:43:5291 const absl::optional<NetworkTrafficAnnotationTag>& proxy_annotation_tag,
Matt Menkef09e64c2019-04-23 22:16:2892 RequestPriority priority,
93 const SocketTag& socket_tag,
94 ClientSocketPool::RespectLimits respect_limits,
95 CompletionOnceCallback callback,
96 const ClientSocketPool::ProxyAuthCallback& proxy_auth_callback,
97 ClientSocketPool* pool,
98 const NetLogWithSource& net_log);
initial.commit586acc5fe2008-07-26 22:42:5299
rdsmith29dbad12017-02-17 02:22:18100 // Changes the priority of the ClientSocketHandle to the passed value.
101 // This function is a no-op if |priority| is the same as the current
102 // priority, of if Init() has not been called since the last time
103 // the ClientSocketHandle was reset.
104 void SetPriority(RequestPriority priority);
105
[email protected]e1e06262008-08-06 23:57:07106 // An initialized handle can be reset, which causes it to return to the
initial.commit586acc5fe2008-07-26 22:42:52107 // un-initialized state. This releases the underlying socket, which in the
[email protected]e1e06262008-08-06 23:57:07108 // case of a socket that still has an established connection, indicates that
109 // the socket may be kept alive for use by a subsequent ClientSocketHandle.
110 //
111 // NOTE: To prevent the socket from being kept alive, be sure to call its
[email protected]d207a5f2009-06-04 05:28:40112 // Disconnect method. This will result in the ClientSocketPool deleting the
[email protected]3268023f2011-05-05 00:08:10113 // StreamSocket.
initial.commit586acc5fe2008-07-26 22:42:52114 void Reset();
115
Matt Menke7eb405e2019-04-25 20:48:21116 // Like Reset(), but also closes the socket (if there is one) and cancels any
117 // pending attempt to establish a connection, if the connection attempt is
118 // still ongoing.
119 void ResetAndCloseSocket();
120
[email protected]d207a5f2009-06-04 05:28:40121 // Used after Init() is called, but before the ClientSocketPool has
122 // initialized the ClientSocketHandle.
123 LoadState GetLoadState() const;
124
[email protected]51fdc7c2012-04-10 19:19:48125 bool IsPoolStalled() const;
126
[email protected]043b68c82013-08-22 23:41:52127 // Adds a higher layered pool on top of the socket pool that |socket_| belongs
128 // to. At most one higher layered pool can be added to a
129 // ClientSocketHandle at a time. On destruction or reset, automatically
130 // removes the higher pool if RemoveHigherLayeredPool has not been called.
131 void AddHigherLayeredPool(HigherLayeredPool* higher_pool);
[email protected]51fdc7c2012-04-10 19:19:48132
[email protected]043b68c82013-08-22 23:41:52133 // Removes a higher layered pool from the socket pool that |socket_| belongs
134 // to. |higher_pool| must have been added by the above function.
135 void RemoveHigherLayeredPool(HigherLayeredPool* higher_pool);
[email protected]51fdc7c2012-04-10 19:19:48136
xunjieli92feb332017-03-03 17:19:23137 // Closes idle sockets that are in the same group with |this|.
Matt Menke433de6d2020-03-04 00:24:11138 void CloseIdleSocketsInGroup(const char* net_log_reason_utf8);
xunjieli92feb332017-03-03 17:19:23139
[email protected]d207a5f2009-06-04 05:28:40140 // Returns true when Init() has completed successfully.
[email protected]05ea9ff2010-07-15 19:08:21141 bool is_initialized() const { return is_initialized_; }
initial.commit586acc5fe2008-07-26 22:42:52142
[email protected]034df0f32013-01-07 23:17:48143 // Sets the portion of LoadTimingInfo related to connection establishment, and
144 // the socket id. |is_reused| is needed because the handle may not have full
145 // reuse information. |load_timing_info| must have all default values when
146 // called. Returns false and makes no changes to |load_timing_info| when
147 // |socket_| is NULL.
148 bool GetLoadTimingInfo(bool is_reused,
149 LoadTimingInfo* load_timing_info) const;
150
[email protected]d207a5f2009-06-04 05:28:40151 // Used by ClientSocketPool to initialize the ClientSocketHandle.
[email protected]ebc1600632013-08-28 08:10:05152 //
153 // SetSocket() may also be used if this handle is used as simply for
154 // socket storage (e.g., http://crbug.com/37810).
danakj655b66c2016-04-16 00:51:38155 void SetSocket(std::unique_ptr<StreamSocket> s);
Matt Menkec1ae1d52019-04-10 19:28:27156
157 // Populates several fields of |this| with error-related information from the
158 // provided completed ConnectJob. Should only be called on ConnectJob failure.
159 void SetAdditionalErrorState(ConnectJob* connect_job);
160
[email protected]a34f61ee2014-03-18 20:59:49161 void set_reuse_type(SocketReuseType reuse_type) { reuse_type_ = reuse_type; }
[email protected]f9d285c2009-08-17 19:54:29162 void set_idle_time(base::TimeDelta idle_time) { idle_time_ = idle_time; }
Matt Menkebf3c767d2019-04-15 23:28:24163 void set_group_generation(int64_t group_generation) {
164 group_generation_ = group_generation;
165 }
[email protected]e60e47a2010-07-14 03:37:18166 void set_is_ssl_error(bool is_ssl_error) { is_ssl_error_ = is_ssl_error; }
Matt Menke39b7c5a2019-04-10 19:47:51167 void set_ssl_cert_request_info(
168 scoped_refptr<SSLCertRequestInfo> ssl_cert_request_info) {
169 ssl_cert_request_info_ = std::move(ssl_cert_request_info);
[email protected]8b498692010-07-16 17:11:43170 }
ttuttle1f2d7e92015-04-28 16:17:47171 void set_connection_attempts(const ConnectionAttempts& attempts) {
172 connection_attempts_ = attempts;
173 }
dalykedd30d982019-12-16 15:31:10174 ResolveErrorInfo resolve_error_info() const { return resolve_error_info_; }
[email protected]8b498692010-07-16 17:11:43175
176 // Only valid if there is no |socket_|.
177 bool is_ssl_error() const {
melandory1346cde2016-06-11 00:42:12178 DCHECK(!socket_);
[email protected]8b498692010-07-16 17:11:43179 return is_ssl_error_;
180 }
Matt Menkefaae31a2019-04-10 19:45:20181
182 // On an ERR_SSL_CLIENT_AUTH_CERT_NEEDED error, the |cert_request_info| field
183 // is set.
Matt Menke39b7c5a2019-04-10 19:47:51184 scoped_refptr<SSLCertRequestInfo> ssl_cert_request_info() const {
185 return ssl_cert_request_info_;
[email protected]8b498692010-07-16 17:11:43186 }
Matt Menke39b7c5a2019-04-10 19:47:51187
David Benjamin95ea68322022-04-25 19:55:19188 // If the connection failed, returns the connection attempts made.
ttuttle1f2d7e92015-04-28 16:17:47189 const ConnectionAttempts& connection_attempts() {
190 return connection_attempts_;
191 }
[email protected]d207a5f2009-06-04 05:28:40192
[email protected]18ccfdb2013-08-15 00:13:44193 StreamSocket* socket() { return socket_.get(); }
[email protected]ebc1600632013-08-28 08:10:05194
195 // SetSocket() must be called with a new socket before this handle
196 // is destroyed if is_initialized() is true.
danakj655b66c2016-04-16 00:51:38197 std::unique_ptr<StreamSocket> PassSocket();
[email protected]ebc1600632013-08-28 08:10:05198
199 // These may only be used if is_initialized() is true.
Matt Menkef6edce752019-03-19 17:21:56200 const ClientSocketPool::GroupId& group_id() const { return group_id_; }
Matt Menkebf3c767d2019-04-15 23:28:24201 int64_t group_generation() const { return group_generation_; }
[email protected]a34f61ee2014-03-18 20:59:49202 bool is_reused() const { return reuse_type_ == REUSED_IDLE; }
[email protected]f9d285c2009-08-17 19:54:29203 base::TimeDelta idle_time() const { return idle_time_; }
[email protected]a34f61ee2014-03-18 20:59:49204 SocketReuseType reuse_type() const { return reuse_type_; }
[email protected]034df0f32013-01-07 23:17:48205 const LoadTimingInfo::ConnectTiming& connect_timing() const {
206 return connect_timing_;
207 }
208 void set_connect_timing(const LoadTimingInfo::ConnectTiming& connect_timing) {
209 connect_timing_ = connect_timing;
210 }
initial.commit586acc5fe2008-07-26 22:42:52211
212 private:
[email protected]3ae82302009-06-26 06:01:21213 // Called on asynchronous completion of an Init() request.
[email protected]d207a5f2009-06-04 05:28:40214 void OnIOComplete(int result);
215
[email protected]3ae82302009-06-26 06:01:21216 // Called on completion (both asynchronous & synchronous) of an Init()
217 // request.
218 void HandleInitCompletion(int result);
219
[email protected]d207a5f2009-06-04 05:28:40220 // Resets the state of the ClientSocketHandle. |cancel| indicates whether or
[email protected]e60e47a2010-07-14 03:37:18221 // not to try to cancel the request with the ClientSocketPool. Does not
Matt Menke7eb405e2019-04-25 20:48:21222 // reset the supplemental error state. |cancel_connect_job| indicates whether
223 // a pending ConnectJob, if there is one in the SocketPool, should be
224 // cancelled in addition to cancelling the request. It may only be true if
225 // |cancel| is also true.
226 void ResetInternal(bool cancel, bool cancel_connect_job);
[email protected]e1e06262008-08-06 23:57:07227
[email protected]e60e47a2010-07-14 03:37:18228 // Resets the supplemental error state.
229 void ResetErrorState();
230
Tsuyoshi Horo2ec06e002022-06-09 01:38:59231 bool is_initialized_ = false;
Tsuyoshi Horo432981d52022-06-09 09:50:13232 raw_ptr<ClientSocketPool> pool_ = nullptr;
233 raw_ptr<HigherLayeredPool> higher_pool_ = nullptr;
danakj655b66c2016-04-16 00:51:38234 std::unique_ptr<StreamSocket> socket_;
Matt Menkef6edce752019-03-19 17:21:56235 ClientSocketPool::GroupId group_id_;
Tsuyoshi Horo2ec06e002022-06-09 01:38:59236 SocketReuseType reuse_type_ = ClientSocketHandle::UNUSED;
Bence Békya4a50932018-08-10 13:39:41237 CompletionOnceCallback callback_;
[email protected]f9d285c2009-08-17 19:54:29238 base::TimeDelta idle_time_;
Matt Menkebf3c767d2019-04-15 23:28:24239 // See ClientSocketPool::ReleaseSocket() for an explanation.
Tsuyoshi Horo2ec06e002022-06-09 01:38:59240 int64_t group_generation_ = -1;
dalykedd30d982019-12-16 15:31:10241 ResolveErrorInfo resolve_error_info_;
Tsuyoshi Horo2ec06e002022-06-09 01:38:59242 bool is_ssl_error_ = false;
Matt Menke39b7c5a2019-04-10 19:47:51243 scoped_refptr<SSLCertRequestInfo> ssl_cert_request_info_;
ttuttle1f2d7e92015-04-28 16:17:47244 std::vector<ConnectionAttempt> connection_attempts_;
initial.commit586acc5fe2008-07-26 22:42:52245
mikecironef22f9812016-10-04 03:40:19246 NetLogSource requesting_source_;
[email protected]06650c52010-06-03 00:49:17247
[email protected]034df0f32013-01-07 23:17:48248 // Timing information is set when a connection is successfully established.
249 LoadTimingInfo::ConnectTiming connect_timing_;
initial.commit586acc5fe2008-07-26 22:42:52250};
251
252} // namespace net
253
[email protected]f7984fc62009-06-22 23:26:44254#endif // NET_SOCKET_CLIENT_SOCKET_HANDLE_H_