1 // Copyright 2014 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 #include "chrome/browser/devtools/device/usb/android_usb_socket.h"
7 #include "base/callback_helpers.h"
8 #include "base/message_loop/message_loop.h"
9 #include "net/base/net_errors.h"
13 const int kMaxPayload
= 4096;
17 AndroidUsbSocket::AndroidUsbSocket(scoped_refptr
<AndroidUsbDevice
> device
,
19 const std::string
& command
,
20 base::Closure delete_callback
)
26 delete_callback_(delete_callback
),
30 AndroidUsbSocket::~AndroidUsbSocket() {
31 DCHECK(CalledOnValidThread());
34 if (!delete_callback_
.is_null())
35 delete_callback_
.Run();
38 void AndroidUsbSocket::HandleIncoming(scoped_ptr
<AdbMessage
> message
) {
42 CHECK_EQ(message
->arg1
, local_id_
);
43 switch (message
->command
) {
44 case AdbMessage::kCommandOKAY
:
46 remote_id_
= message
->arg0
;
48 if (!connect_callback_
.is_null())
49 base::ResetAndReturn(&connect_callback_
).Run(net::OK
);
50 // "this" can be deleted.
52 RespondToWriter(write_length_
);
53 // "this" can be deleted.
56 case AdbMessage::kCommandWRTE
:
57 device_
->Send(AdbMessage::kCommandOKAY
, local_id_
, message
->arg0
, "");
58 read_buffer_
+= message
->body
;
59 // Allow WRTE over new connection even though OKAY ack was not received.
61 remote_id_
= message
->arg0
;
63 if (!connect_callback_
.is_null())
64 base::ResetAndReturn(&connect_callback_
).Run(net::OK
);
65 // "this" can be deleted.
67 RespondToReader(false);
68 // "this" can be deleted.
71 case AdbMessage::kCommandCLSE
:
73 device_
->Send(AdbMessage::kCommandCLSE
, local_id_
, 0, "");
75 // "this" can be deleted.
82 void AndroidUsbSocket::Terminated(bool closed_by_device
) {
83 is_connected_
= false;
85 // Break the socket -> device connection, release the device.
87 base::ResetAndReturn(&delete_callback_
).Run();
89 if (!closed_by_device
)
92 // Respond to pending callbacks.
93 if (!connect_callback_
.is_null()) {
94 base::ResetAndReturn(&connect_callback_
).Run(net::ERR_FAILED
);
95 // "this" can be deleted.
98 base::WeakPtr
<AndroidUsbSocket
> weak_this
= weak_factory_
.GetWeakPtr();
99 RespondToReader(true);
100 // "this" can be deleted.
102 RespondToWriter(net::ERR_FAILED
);
103 // "this" can be deleted.
107 int AndroidUsbSocket::Read(net::IOBuffer
* buffer
,
109 const net::CompletionCallback
& callback
) {
110 DCHECK(!callback
.is_null());
112 return device_
.get() ? net::ERR_SOCKET_NOT_CONNECTED
: 0;
114 DCHECK(read_callback_
.is_null());
115 if (read_buffer_
.empty()) {
116 read_callback_
= callback
;
117 read_io_buffer_
= buffer
;
118 read_length_
= length
;
119 return net::ERR_IO_PENDING
;
122 size_t bytes_to_copy
= static_cast<size_t>(length
) > read_buffer_
.length() ?
123 read_buffer_
.length() : static_cast<size_t>(length
);
124 memcpy(buffer
->data(), read_buffer_
.data(), bytes_to_copy
);
125 if (read_buffer_
.length() > bytes_to_copy
)
126 read_buffer_
= read_buffer_
.substr(bytes_to_copy
);
128 read_buffer_
= std::string();
129 return bytes_to_copy
;
132 int AndroidUsbSocket::Write(net::IOBuffer
* buffer
,
134 const net::CompletionCallback
& callback
) {
135 DCHECK(!callback
.is_null());
137 return net::ERR_SOCKET_NOT_CONNECTED
;
139 if (length
> kMaxPayload
)
140 length
= kMaxPayload
;
142 DCHECK(write_callback_
.is_null());
143 write_callback_
= callback
;
144 write_length_
= length
;
145 device_
->Send(AdbMessage::kCommandWRTE
, local_id_
, remote_id_
,
146 std::string(buffer
->data(), length
));
147 return net::ERR_IO_PENDING
;
150 int AndroidUsbSocket::SetReceiveBufferSize(int32 size
) {
152 return net::ERR_NOT_IMPLEMENTED
;
155 int AndroidUsbSocket::SetSendBufferSize(int32 size
) {
157 return net::ERR_NOT_IMPLEMENTED
;
160 int AndroidUsbSocket::Connect(const net::CompletionCallback
& callback
) {
161 DCHECK(CalledOnValidThread());
162 DCHECK(!callback
.is_null());
164 return net::ERR_FAILED
;
166 DCHECK(!is_connected_
);
167 DCHECK(connect_callback_
.is_null());
168 connect_callback_
= callback
;
169 device_
->Send(AdbMessage::kCommandOPEN
, local_id_
, 0, command_
);
170 return net::ERR_IO_PENDING
;
173 void AndroidUsbSocket::Disconnect() {
176 device_
->Send(AdbMessage::kCommandCLSE
, local_id_
, remote_id_
, "");
180 bool AndroidUsbSocket::IsConnected() const {
181 DCHECK(CalledOnValidThread());
182 return is_connected_
;
185 bool AndroidUsbSocket::IsConnectedAndIdle() const {
190 int AndroidUsbSocket::GetPeerAddress(net::IPEndPoint
* address
) const {
191 net::IPAddressNumber
ip(net::kIPv4AddressSize
);
192 *address
= net::IPEndPoint(ip
, 0);
196 int AndroidUsbSocket::GetLocalAddress(net::IPEndPoint
* address
) const {
198 return net::ERR_NOT_IMPLEMENTED
;
201 const net::BoundNetLog
& AndroidUsbSocket::NetLog() const {
205 void AndroidUsbSocket::SetSubresourceSpeculation() {
209 void AndroidUsbSocket::SetOmniboxSpeculation() {
213 bool AndroidUsbSocket::WasEverUsed() const {
218 bool AndroidUsbSocket::UsingTCPFastOpen() const {
223 bool AndroidUsbSocket::WasNpnNegotiated() const {
228 net::NextProto
AndroidUsbSocket::GetNegotiatedProtocol() const {
230 return net::kProtoUnknown
;
233 bool AndroidUsbSocket::GetSSLInfo(net::SSLInfo
* ssl_info
) {
237 void AndroidUsbSocket::GetConnectionAttempts(
238 net::ConnectionAttempts
* out
) const {
242 void AndroidUsbSocket::RespondToReader(bool disconnect
) {
243 if (read_callback_
.is_null() || (read_buffer_
.empty() && !disconnect
))
245 size_t bytes_to_copy
=
246 static_cast<size_t>(read_length_
) > read_buffer_
.length() ?
247 read_buffer_
.length() : static_cast<size_t>(read_length_
);
248 memcpy(read_io_buffer_
->data(), read_buffer_
.data(), bytes_to_copy
);
249 if (read_buffer_
.length() > bytes_to_copy
)
250 read_buffer_
= read_buffer_
.substr(bytes_to_copy
);
252 read_buffer_
= std::string();
253 base::ResetAndReturn(&read_callback_
).Run(bytes_to_copy
);
256 void AndroidUsbSocket::RespondToWriter(int result
) {
257 if (!write_callback_
.is_null())
258 base::ResetAndReturn(&write_callback_
).Run(result
);