| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 // | 4 // |
| 5 // A ClientSocketPoolBase is used to restrict the number of sockets open at | 5 // A ClientSocketPoolBase is used to restrict the number of sockets open at |
| 6 // a time. It also maintains a list of idle persistent sockets for reuse. | 6 // a time. It also maintains a list of idle persistent sockets for reuse. |
| 7 // Subclasses of ClientSocketPool should compose ClientSocketPoolBase to handle | 7 // Subclasses of ClientSocketPool should compose ClientSocketPoolBase to handle |
| 8 // the core logic of (1) restricting the number of active (connected or | 8 // the core logic of (1) restricting the number of active (connected or |
| 9 // connecting) sockets per "group" (generally speaking, the hostname), (2) | 9 // connecting) sockets per "group" (generally speaking, the hostname), (2) |
| 10 // maintaining a per-group list of idle, persistent sockets for reuse, and (3) | 10 // maintaining a per-group list of idle, persistent sockets for reuse, and (3) |
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 74 ConnectJob* job) = 0; | 74 ConnectJob* job) = 0; |
| 75 | 75 |
| 76 private: | 76 private: |
| 77 DISALLOW_COPY_AND_ASSIGN(Delegate); | 77 DISALLOW_COPY_AND_ASSIGN(Delegate); |
| 78 }; | 78 }; |
| 79 | 79 |
| 80 // A |timeout_duration| of 0 corresponds to no timeout. | 80 // A |timeout_duration| of 0 corresponds to no timeout. |
| 81 ConnectJob(const std::string& group_name, | 81 ConnectJob(const std::string& group_name, |
| 82 base::TimeDelta timeout_duration, | 82 base::TimeDelta timeout_duration, |
| 83 RequestPriority priority, | 83 RequestPriority priority, |
| 84 ClientSocketPool::IgnoreLimits ignore_limits, |
| 84 Delegate* delegate, | 85 Delegate* delegate, |
| 85 const BoundNetLog& net_log); | 86 const BoundNetLog& net_log); |
| 86 virtual ~ConnectJob(); | 87 virtual ~ConnectJob(); |
| 87 | 88 |
| 88 // Accessors | 89 // Accessors |
| 89 const std::string& group_name() const { return group_name_; } | 90 const std::string& group_name() const { return group_name_; } |
| 90 const BoundNetLog& net_log() { return net_log_; } | 91 const BoundNetLog& net_log() { return net_log_; } |
| 91 | 92 |
| 92 // Releases ownership of the underlying socket to the caller. | 93 // Releases ownership of the underlying socket to the caller. |
| 93 // Returns the released socket, or NULL if there was a connection | 94 // Returns the released socket, or NULL if there was a connection |
| (...skipping 16 matching lines...) Expand all Loading... |
| 110 virtual void GetAdditionalErrorState(ClientSocketHandle* handle) {} | 111 virtual void GetAdditionalErrorState(ClientSocketHandle* handle) {} |
| 111 | 112 |
| 112 const LoadTimingInfo::ConnectTiming& connect_timing() const { | 113 const LoadTimingInfo::ConnectTiming& connect_timing() const { |
| 113 return connect_timing_; | 114 return connect_timing_; |
| 114 } | 115 } |
| 115 | 116 |
| 116 const BoundNetLog& net_log() const { return net_log_; } | 117 const BoundNetLog& net_log() const { return net_log_; } |
| 117 | 118 |
| 118 protected: | 119 protected: |
| 119 RequestPriority priority() const { return priority_; } | 120 RequestPriority priority() const { return priority_; } |
| 121 ClientSocketPool::IgnoreLimits ignore_limits() const { |
| 122 return ignore_limits_; |
| 123 } |
| 120 void SetSocket(scoped_ptr<StreamSocket> socket); | 124 void SetSocket(scoped_ptr<StreamSocket> socket); |
| 121 StreamSocket* socket() { return socket_.get(); } | 125 StreamSocket* socket() { return socket_.get(); } |
| 122 void NotifyDelegateOfCompletion(int rv); | 126 void NotifyDelegateOfCompletion(int rv); |
| 123 void ResetTimer(base::TimeDelta remainingTime); | 127 void ResetTimer(base::TimeDelta remainingTime); |
| 124 | 128 |
| 125 // Connection establishment timing information. | 129 // Connection establishment timing information. |
| 126 LoadTimingInfo::ConnectTiming connect_timing_; | 130 LoadTimingInfo::ConnectTiming connect_timing_; |
| 127 | 131 |
| 128 private: | 132 private: |
| 129 virtual int ConnectInternal() = 0; | 133 virtual int ConnectInternal() = 0; |
| 130 | 134 |
| 131 void LogConnectStart(); | 135 void LogConnectStart(); |
| 132 void LogConnectCompletion(int net_error); | 136 void LogConnectCompletion(int net_error); |
| 133 | 137 |
| 134 // Alerts the delegate that the ConnectJob has timed out. | 138 // Alerts the delegate that the ConnectJob has timed out. |
| 135 void OnTimeout(); | 139 void OnTimeout(); |
| 136 | 140 |
| 137 const std::string group_name_; | 141 const std::string group_name_; |
| 138 const base::TimeDelta timeout_duration_; | 142 const base::TimeDelta timeout_duration_; |
| 139 // TODO(akalin): Support reprioritization. | 143 // TODO(akalin): Support reprioritization. |
| 140 const RequestPriority priority_; | 144 const RequestPriority priority_; |
| 145 const ClientSocketPool::IgnoreLimits ignore_limits_; |
| 141 // Timer to abort jobs that take too long. | 146 // Timer to abort jobs that take too long. |
| 142 base::OneShotTimer timer_; | 147 base::OneShotTimer timer_; |
| 143 Delegate* delegate_; | 148 Delegate* delegate_; |
| 144 scoped_ptr<StreamSocket> socket_; | 149 scoped_ptr<StreamSocket> socket_; |
| 145 BoundNetLog net_log_; | 150 BoundNetLog net_log_; |
| 146 // A ConnectJob is idle until Connect() has been called. | 151 // A ConnectJob is idle until Connect() has been called. |
| 147 bool idle_; | 152 bool idle_; |
| 148 | 153 |
| 149 DISALLOW_COPY_AND_ASSIGN(ConnectJob); | 154 DISALLOW_COPY_AND_ASSIGN(ConnectJob); |
| 150 }; | 155 }; |
| (...skipping 15 matching lines...) Expand all Loading... |
| 166 enum Flag { | 171 enum Flag { |
| 167 NORMAL = 0, // Normal behavior. | 172 NORMAL = 0, // Normal behavior. |
| 168 NO_IDLE_SOCKETS = 0x1, // Do not return an idle socket. Create a new one. | 173 NO_IDLE_SOCKETS = 0x1, // Do not return an idle socket. Create a new one. |
| 169 }; | 174 }; |
| 170 | 175 |
| 171 class NET_EXPORT_PRIVATE Request { | 176 class NET_EXPORT_PRIVATE Request { |
| 172 public: | 177 public: |
| 173 Request(ClientSocketHandle* handle, | 178 Request(ClientSocketHandle* handle, |
| 174 const CompletionCallback& callback, | 179 const CompletionCallback& callback, |
| 175 RequestPriority priority, | 180 RequestPriority priority, |
| 176 bool ignore_limits, | 181 ClientSocketPool::IgnoreLimits ignore_limits, |
| 177 Flags flags, | 182 Flags flags, |
| 178 const BoundNetLog& net_log); | 183 const BoundNetLog& net_log); |
| 179 | 184 |
| 180 virtual ~Request(); | 185 virtual ~Request(); |
| 181 | 186 |
| 182 ClientSocketHandle* handle() const { return handle_; } | 187 ClientSocketHandle* handle() const { return handle_; } |
| 183 const CompletionCallback& callback() const { return callback_; } | 188 const CompletionCallback& callback() const { return callback_; } |
| 184 RequestPriority priority() const { return priority_; } | 189 RequestPriority priority() const { return priority_; } |
| 185 bool ignore_limits() const { return ignore_limits_; } | 190 ClientSocketPool::IgnoreLimits ignore_limits() const { |
| 191 return ignore_limits_; |
| 192 } |
| 186 Flags flags() const { return flags_; } | 193 Flags flags() const { return flags_; } |
| 187 const BoundNetLog& net_log() const { return net_log_; } | 194 const BoundNetLog& net_log() const { return net_log_; } |
| 188 | 195 |
| 189 // TODO(eroman): Temporary until crbug.com/467797 is solved. | 196 // TODO(eroman): Temporary until crbug.com/467797 is solved. |
| 190 void CrashIfInvalid() const; | 197 void CrashIfInvalid() const; |
| 191 | 198 |
| 192 private: | 199 private: |
| 193 // TODO(eroman): Temporary until crbug.com/467797 is solved. | 200 // TODO(eroman): Temporary until crbug.com/467797 is solved. |
| 194 enum Liveness { | 201 enum Liveness { |
| 195 ALIVE = 0xCA11AB13, | 202 ALIVE = 0xCA11AB13, |
| 196 DEAD = 0xDEADBEEF, | 203 DEAD = 0xDEADBEEF, |
| 197 }; | 204 }; |
| 198 | 205 |
| 199 ClientSocketHandle* const handle_; | 206 ClientSocketHandle* const handle_; |
| 200 const CompletionCallback callback_; | 207 const CompletionCallback callback_; |
| 201 // TODO(akalin): Support reprioritization. | 208 // TODO(akalin): Support reprioritization. |
| 202 const RequestPriority priority_; | 209 const RequestPriority priority_; |
| 203 const bool ignore_limits_; | 210 const ClientSocketPool::IgnoreLimits ignore_limits_; |
| 204 const Flags flags_; | 211 const Flags flags_; |
| 205 const BoundNetLog net_log_; | 212 const BoundNetLog net_log_; |
| 206 | 213 |
| 207 // TODO(eroman): Temporary until crbug.com/467797 is solved. | 214 // TODO(eroman): Temporary until crbug.com/467797 is solved. |
| 208 Liveness liveness_ = ALIVE; | 215 Liveness liveness_ = ALIVE; |
| 209 | 216 |
| 210 DISALLOW_COPY_AND_ASSIGN(Request); | 217 DISALLOW_COPY_AND_ASSIGN(Request); |
| 211 }; | 218 }; |
| 212 | 219 |
| 213 class ConnectJobFactory { | 220 class ConnectJobFactory { |
| (...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 400 // Returns true if the group could make use of an additional socket slot, if | 407 // Returns true if the group could make use of an additional socket slot, if |
| 401 // it were given one. | 408 // it were given one. |
| 402 bool CanUseAdditionalSocketSlot(int max_sockets_per_group) const { | 409 bool CanUseAdditionalSocketSlot(int max_sockets_per_group) const { |
| 403 return HasAvailableSocketSlot(max_sockets_per_group) && | 410 return HasAvailableSocketSlot(max_sockets_per_group) && |
| 404 pending_requests_.size() > jobs_.size(); | 411 pending_requests_.size() > jobs_.size(); |
| 405 } | 412 } |
| 406 | 413 |
| 407 // Returns the priority of the top of the pending request queue | 414 // Returns the priority of the top of the pending request queue |
| 408 // (which may be less than the maximum priority over the entire | 415 // (which may be less than the maximum priority over the entire |
| 409 // queue, due to how we prioritize requests with |ignore_limits| | 416 // queue, due to how we prioritize requests with |ignore_limits| |
| 410 // set over others). | 417 // ENABLED over others). |
| 411 RequestPriority TopPendingPriority() const { | 418 RequestPriority TopPendingPriority() const { |
| 412 // NOTE: FirstMax().value()->priority() is not the same as | 419 // NOTE: FirstMax().value()->priority() is not the same as |
| 413 // FirstMax().priority()! | 420 // FirstMax().priority()! |
| 414 return pending_requests_.FirstMax().value()->priority(); | 421 return pending_requests_.FirstMax().value()->priority(); |
| 415 } | 422 } |
| 416 | 423 |
| 417 // Set a timer to create a backup job if it takes too long to | 424 // Set a timer to create a backup job if it takes too long to |
| 418 // create one and if a timer isn't already running. | 425 // create one and if a timer isn't already running. |
| 419 void StartBackupJobTimer(const std::string& group_name, | 426 void StartBackupJobTimer(const std::string& group_name, |
| 420 ClientSocketPoolBaseHelper* pool); | 427 ClientSocketPoolBaseHelper* pool); |
| (...skipping 252 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 673 } // namespace internal | 680 } // namespace internal |
| 674 | 681 |
| 675 template <typename SocketParams> | 682 template <typename SocketParams> |
| 676 class ClientSocketPoolBase { | 683 class ClientSocketPoolBase { |
| 677 public: | 684 public: |
| 678 class Request : public internal::ClientSocketPoolBaseHelper::Request { | 685 class Request : public internal::ClientSocketPoolBaseHelper::Request { |
| 679 public: | 686 public: |
| 680 Request(ClientSocketHandle* handle, | 687 Request(ClientSocketHandle* handle, |
| 681 const CompletionCallback& callback, | 688 const CompletionCallback& callback, |
| 682 RequestPriority priority, | 689 RequestPriority priority, |
| 690 ClientSocketPool::IgnoreLimits ignore_limits, |
| 683 internal::ClientSocketPoolBaseHelper::Flags flags, | 691 internal::ClientSocketPoolBaseHelper::Flags flags, |
| 684 bool ignore_limits, | |
| 685 const scoped_refptr<SocketParams>& params, | 692 const scoped_refptr<SocketParams>& params, |
| 686 const BoundNetLog& net_log) | 693 const BoundNetLog& net_log) |
| 687 : internal::ClientSocketPoolBaseHelper::Request( | 694 : internal::ClientSocketPoolBaseHelper::Request(handle, |
| 688 handle, callback, priority, ignore_limits, flags, net_log), | 695 callback, |
| 696 priority, |
| 697 ignore_limits, |
| 698 flags, |
| 699 net_log), |
| 689 params_(params) {} | 700 params_(params) {} |
| 690 | 701 |
| 691 const scoped_refptr<SocketParams>& params() const { return params_; } | 702 const scoped_refptr<SocketParams>& params() const { return params_; } |
| 692 | 703 |
| 693 private: | 704 private: |
| 694 const scoped_refptr<SocketParams> params_; | 705 const scoped_refptr<SocketParams> params_; |
| 695 }; | 706 }; |
| 696 | 707 |
| 697 class ConnectJobFactory { | 708 class ConnectJobFactory { |
| 698 public: | 709 public: |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 742 | 753 |
| 743 void RemoveHigherLayeredPool(HigherLayeredPool* higher_pool) { | 754 void RemoveHigherLayeredPool(HigherLayeredPool* higher_pool) { |
| 744 helper_.RemoveHigherLayeredPool(higher_pool); | 755 helper_.RemoveHigherLayeredPool(higher_pool); |
| 745 } | 756 } |
| 746 | 757 |
| 747 // RequestSocket bundles up the parameters into a Request and then forwards to | 758 // RequestSocket bundles up the parameters into a Request and then forwards to |
| 748 // ClientSocketPoolBaseHelper::RequestSocket(). | 759 // ClientSocketPoolBaseHelper::RequestSocket(). |
| 749 int RequestSocket(const std::string& group_name, | 760 int RequestSocket(const std::string& group_name, |
| 750 const scoped_refptr<SocketParams>& params, | 761 const scoped_refptr<SocketParams>& params, |
| 751 RequestPriority priority, | 762 RequestPriority priority, |
| 763 ClientSocketPool::IgnoreLimits ignore_limits, |
| 752 ClientSocketHandle* handle, | 764 ClientSocketHandle* handle, |
| 753 const CompletionCallback& callback, | 765 const CompletionCallback& callback, |
| 754 const BoundNetLog& net_log) { | 766 const BoundNetLog& net_log) { |
| 755 scoped_ptr<const Request> request( | 767 scoped_ptr<const Request> request(new Request( |
| 756 new Request(handle, callback, priority, | 768 handle, callback, priority, ignore_limits, |
| 757 internal::ClientSocketPoolBaseHelper::NORMAL, | 769 internal::ClientSocketPoolBaseHelper::NORMAL, params, net_log)); |
| 758 params->ignore_limits(), | |
| 759 params, net_log)); | |
| 760 return helper_.RequestSocket(group_name, std::move(request)); | 770 return helper_.RequestSocket(group_name, std::move(request)); |
| 761 } | 771 } |
| 762 | 772 |
| 763 // RequestSockets bundles up the parameters into a Request and then forwards | 773 // RequestSockets bundles up the parameters into a Request and then forwards |
| 764 // to ClientSocketPoolBaseHelper::RequestSockets(). Note that it assigns the | 774 // to ClientSocketPoolBaseHelper::RequestSockets(). Note that it assigns the |
| 765 // priority to IDLE and specifies the NO_IDLE_SOCKETS flag. | 775 // priority to IDLE and specifies the NO_IDLE_SOCKETS flag. |
| 766 void RequestSockets(const std::string& group_name, | 776 void RequestSockets(const std::string& group_name, |
| 767 const scoped_refptr<SocketParams>& params, | 777 const scoped_refptr<SocketParams>& params, |
| 768 int num_sockets, | 778 int num_sockets, |
| 769 const BoundNetLog& net_log) { | 779 const BoundNetLog& net_log) { |
| 770 const Request request(NULL /* no handle */, CompletionCallback(), IDLE, | 780 const Request request(nullptr /* no handle */, CompletionCallback(), IDLE, |
| 781 ClientSocketPool::IgnoreLimits::DISABLED, |
| 771 internal::ClientSocketPoolBaseHelper::NO_IDLE_SOCKETS, | 782 internal::ClientSocketPoolBaseHelper::NO_IDLE_SOCKETS, |
| 772 params->ignore_limits(), params, net_log); | 783 params, net_log); |
| 773 helper_.RequestSockets(group_name, request, num_sockets); | 784 helper_.RequestSockets(group_name, request, num_sockets); |
| 774 } | 785 } |
| 775 | 786 |
| 776 void CancelRequest(const std::string& group_name, | 787 void CancelRequest(const std::string& group_name, |
| 777 ClientSocketHandle* handle) { | 788 ClientSocketHandle* handle) { |
| 778 return helper_.CancelRequest(group_name, handle); | 789 return helper_.CancelRequest(group_name, handle); |
| 779 } | 790 } |
| 780 | 791 |
| 781 void ReleaseSocket(const std::string& group_name, | 792 void ReleaseSocket(const std::string& group_name, |
| 782 scoped_ptr<StreamSocket> socket, | 793 scoped_ptr<StreamSocket> socket, |
| (...skipping 92 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 875 }; | 886 }; |
| 876 | 887 |
| 877 internal::ClientSocketPoolBaseHelper helper_; | 888 internal::ClientSocketPoolBaseHelper helper_; |
| 878 | 889 |
| 879 DISALLOW_COPY_AND_ASSIGN(ClientSocketPoolBase); | 890 DISALLOW_COPY_AND_ASSIGN(ClientSocketPoolBase); |
| 880 }; | 891 }; |
| 881 | 892 |
| 882 } // namespace net | 893 } // namespace net |
| 883 | 894 |
| 884 #endif // NET_SOCKET_CLIENT_SOCKET_POOL_BASE_H_ | 895 #endif // NET_SOCKET_CLIENT_SOCKET_POOL_BASE_H_ |
| OLD | NEW |