Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(615)

Side by Side Diff: chrome/browser/extensions/api/cast_channel/cast_socket.cc

Issue 393023003: Added connection timeout functionality to CastSocket. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 6 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 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 #include "chrome/browser/extensions/api/cast_channel/cast_socket.h" 5 #include "chrome/browser/extensions/api/cast_channel/cast_socket.h"
6 6
7 #include <stdlib.h> 7 #include <stdlib.h>
8 #include <string.h> 8 #include <string.h>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
60 return g_factory.Pointer(); 60 return g_factory.Pointer();
61 } 61 }
62 62
63 namespace api { 63 namespace api {
64 namespace cast_channel { 64 namespace cast_channel {
65 65
66 CastSocket::CastSocket(const std::string& owner_extension_id, 66 CastSocket::CastSocket(const std::string& owner_extension_id,
67 const net::IPEndPoint& ip_endpoint, 67 const net::IPEndPoint& ip_endpoint,
68 ChannelAuthType channel_auth, 68 ChannelAuthType channel_auth,
69 CastSocket::Delegate* delegate, 69 CastSocket::Delegate* delegate,
70 net::NetLog* net_log) : 70 net::NetLog* net_log,
71 int64 timeout_ms) :
71 ApiResource(owner_extension_id), 72 ApiResource(owner_extension_id),
72 channel_id_(0), 73 channel_id_(0),
73 ip_endpoint_(ip_endpoint), 74 ip_endpoint_(ip_endpoint),
74 channel_auth_(channel_auth), 75 channel_auth_(channel_auth),
75 delegate_(delegate), 76 delegate_(delegate),
76 current_message_size_(0), 77 current_message_size_(0),
77 current_message_(new CastMessage()), 78 current_message_(new CastMessage()),
78 net_log_(net_log), 79 net_log_(net_log),
79 connect_state_(CONN_STATE_NONE), 80 connect_state_(CONN_STATE_NONE),
80 write_state_(WRITE_STATE_NONE), 81 write_state_(WRITE_STATE_NONE),
81 read_state_(READ_STATE_NONE), 82 read_state_(READ_STATE_NONE),
82 error_state_(CHANNEL_ERROR_NONE), 83 error_state_(CHANNEL_ERROR_NONE),
83 ready_state_(READY_STATE_NONE) { 84 ready_state_(READY_STATE_NONE),
85 timeout_interval_ms_(timeout_ms),
86 timed_out_(false) {
84 DCHECK(net_log_); 87 DCHECK(net_log_);
85 DCHECK(channel_auth_ == CHANNEL_AUTH_TYPE_SSL || 88 DCHECK(channel_auth_ == CHANNEL_AUTH_TYPE_SSL ||
86 channel_auth_ == CHANNEL_AUTH_TYPE_SSL_VERIFIED); 89 channel_auth_ == CHANNEL_AUTH_TYPE_SSL_VERIFIED);
87 net_log_source_.type = net::NetLog::SOURCE_SOCKET; 90 net_log_source_.type = net::NetLog::SOURCE_SOCKET;
88 net_log_source_.id = net_log_->NextID(); 91 net_log_source_.id = net_log_->NextID();
89 92
90 // Reuse these buffers for each message. 93 // Reuse these buffers for each message.
91 header_read_buffer_ = new net::GrowableIOBuffer(); 94 header_read_buffer_ = new net::GrowableIOBuffer();
92 header_read_buffer_->SetCapacity(MessageHeader::header_size()); 95 header_read_buffer_->SetCapacity(MessageHeader::header_size());
93 body_read_buffer_ = new net::GrowableIOBuffer(); 96 body_read_buffer_ = new net::GrowableIOBuffer();
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
164 void CastSocket::Connect(const net::CompletionCallback& callback) { 167 void CastSocket::Connect(const net::CompletionCallback& callback) {
165 DCHECK(CalledOnValidThread()); 168 DCHECK(CalledOnValidThread());
166 VLOG_WITH_CONNECTION(1) << "Connect readyState = " << ready_state_; 169 VLOG_WITH_CONNECTION(1) << "Connect readyState = " << ready_state_;
167 if (ready_state_ != READY_STATE_NONE) { 170 if (ready_state_ != READY_STATE_NONE) {
168 callback.Run(net::ERR_CONNECTION_FAILED); 171 callback.Run(net::ERR_CONNECTION_FAILED);
169 return; 172 return;
170 } 173 }
171 ready_state_ = READY_STATE_CONNECTING; 174 ready_state_ = READY_STATE_CONNECTING;
172 connect_callback_ = callback; 175 connect_callback_ = callback;
173 connect_state_ = CONN_STATE_TCP_CONNECT; 176 connect_state_ = CONN_STATE_TCP_CONNECT;
177
178 timeout_callback_.Reset(base::Bind(&CastSocket::Timeout, AsWeakPtr()));
179 base::MessageLoop::current()->PostDelayedTask(
180 FROM_HERE,
181 timeout_callback_.callback(),
182 base::TimeDelta::FromMilliseconds(timeout_interval_ms_));
183
174 DoConnectLoop(net::OK); 184 DoConnectLoop(net::OK);
175 } 185 }
176 186
177 void CastSocket::PostTaskToStartConnectLoop(int result) { 187 void CastSocket::PostTaskToStartConnectLoop(int result) {
178 DCHECK(CalledOnValidThread()); 188 DCHECK(CalledOnValidThread());
179 base::MessageLoop::current()->PostTask( 189 base::MessageLoop::current()->PostTask(
180 FROM_HERE, 190 FROM_HERE,
181 base::Bind(&CastSocket::DoConnectLoop, AsWeakPtr(), result)); 191 base::Bind(&CastSocket::DoConnectLoop, AsWeakPtr(), result));
182 } 192 }
183 193
194 void CastSocket::Timeout() {
195 VLOG(1) << "Timeout while establishing connection.";
196 CloseWithError(CHANNEL_ERROR_CONNECT_ERROR);
mark a. foltz 2014/07/15 22:18:15 I would be in favor of adding an error enum CHANNE
Kevin M 2014/07/16 22:59:41 Done.
197 timed_out_ = true;
mark a. foltz 2014/07/15 22:18:15 Is timed_out_ used anywhere?
Kevin M 2014/07/16 22:59:41 No, I ended up using the error state instead. Remo
198 DoConnectCallback(net::ERR_TIMED_OUT);
199 }
200
184 // This method performs the state machine transitions for connection flow. 201 // This method performs the state machine transitions for connection flow.
185 // There are two entry points to this method: 202 // There are two entry points to this method:
186 // 1. Connect method: this starts the flow 203 // 1. Connect method: this starts the flow
187 // 2. Callback from network operations that finish asynchronously 204 // 2. Callback from network operations that finish asynchronously
188 void CastSocket::DoConnectLoop(int result) { 205 void CastSocket::DoConnectLoop(int result) {
206 if (error_state_ != CHANNEL_ERROR_NONE) {
207 VLOG(1) << "Connection timeout; DoConnectLoop aborted.";
mark a. foltz 2014/07/15 22:18:15 Is this the only possible way error_state_ can be
Kevin M 2014/07/16 22:59:41 Good idea, done.
208 return;
209 }
210
189 // Network operations can either finish synchronously or asynchronously. 211 // Network operations can either finish synchronously or asynchronously.
190 // This method executes the state machine transitions in a loop so that 212 // This method executes the state machine transitions in a loop so that
191 // correct state transitions happen even when network operations finish 213 // correct state transitions happen even when network operations finish
192 // synchronously. 214 // synchronously.
193 int rv = result; 215 int rv = result;
194 do { 216 do {
195 ConnectionState state = connect_state_; 217 ConnectionState state = connect_state_;
196 // Default to CONN_STATE_NONE, which breaks the processing loop if any 218 // Default to CONN_STATE_NONE, which breaks the processing loop if any
197 // handler fails to transition to another state to continue processing. 219 // handler fails to transition to another state to continue processing.
198 connect_state_ = CONN_STATE_NONE; 220 connect_state_ = CONN_STATE_NONE;
(...skipping 23 matching lines...) Expand all
222 default: 244 default:
223 NOTREACHED() << "BUG in connect flow. Unknown state: " << state; 245 NOTREACHED() << "BUG in connect flow. Unknown state: " << state;
224 break; 246 break;
225 } 247 }
226 } while (rv != net::ERR_IO_PENDING && connect_state_ != CONN_STATE_NONE); 248 } while (rv != net::ERR_IO_PENDING && connect_state_ != CONN_STATE_NONE);
227 // Get out of the loop either when: 249 // Get out of the loop either when:
228 // a. A network operation is pending, OR 250 // a. A network operation is pending, OR
229 // b. The Do* method called did not change state 251 // b. The Do* method called did not change state
230 252
231 // Connect loop is finished: if there is no pending IO invoke the callback. 253 // Connect loop is finished: if there is no pending IO invoke the callback.
232 if (rv != net::ERR_IO_PENDING) 254 if (rv != net::ERR_IO_PENDING) {
255 timeout_callback_.Cancel();
233 DoConnectCallback(rv); 256 DoConnectCallback(rv);
257 }
234 } 258 }
235 259
236 int CastSocket::DoTcpConnect() { 260 int CastSocket::DoTcpConnect() {
237 VLOG_WITH_CONNECTION(1) << "DoTcpConnect"; 261 VLOG_WITH_CONNECTION(1) << "DoTcpConnect";
238 connect_state_ = CONN_STATE_TCP_CONNECT_COMPLETE; 262 connect_state_ = CONN_STATE_TCP_CONNECT_COMPLETE;
239 tcp_socket_ = CreateTcpSocket(); 263 tcp_socket_ = CreateTcpSocket();
240 return tcp_socket_->Connect( 264 return tcp_socket_->Connect(
241 base::Bind(&CastSocket::DoConnectLoop, AsWeakPtr())); 265 base::Bind(&CastSocket::DoConnectLoop, AsWeakPtr()));
242 } 266 }
243 267
(...skipping 431 matching lines...) Expand 10 before | Expand all | Expand 10 after
675 message_proto.SerializeToString(message_data); 699 message_proto.SerializeToString(message_data);
676 size_t message_size = message_data->size(); 700 size_t message_size = message_data->size();
677 if (message_size > MessageHeader::max_message_size()) { 701 if (message_size > MessageHeader::max_message_size()) {
678 message_data->clear(); 702 message_data->clear();
679 return false; 703 return false;
680 } 704 }
681 CastSocket::MessageHeader header; 705 CastSocket::MessageHeader header;
682 header.SetMessageSize(message_size); 706 header.SetMessageSize(message_size);
683 header.PrependToString(message_data); 707 header.PrependToString(message_data);
684 return true; 708 return true;
685 }; 709 }
686 710
687 void CastSocket::CloseWithError(ChannelError error) { 711 void CastSocket::CloseWithError(ChannelError error) {
688 DCHECK(CalledOnValidThread()); 712 DCHECK(CalledOnValidThread());
689 socket_.reset(NULL); 713 socket_.reset(NULL);
690 ready_state_ = READY_STATE_CLOSED; 714 ready_state_ = READY_STATE_CLOSED;
691 error_state_ = error; 715 error_state_ = error;
692 if (delegate_) 716 if (delegate_)
693 delegate_->OnError(this, error); 717 delegate_->OnError(this, error);
694 } 718 }
695 719
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
751 return true; 775 return true;
752 } 776 }
753 777
754 CastSocket::WriteRequest::~WriteRequest() { } 778 CastSocket::WriteRequest::~WriteRequest() { }
755 779
756 } // namespace cast_channel 780 } // namespace cast_channel
757 } // namespace api 781 } // namespace api
758 } // namespace extensions 782 } // namespace extensions
759 783
760 #undef VLOG_WITH_CONNECTION 784 #undef VLOG_WITH_CONNECTION
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698