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

Side by Side Diff: components/proximity_auth/ble/bluetooth_low_energy_weave_client_connection.cc

Issue 2075313002: Substituting legacy protocol with uWeave protocol (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: readible reason for close and removed dlog in test Created 4 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 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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 "components/proximity_auth/ble/bluetooth_low_energy_connection.h" 5 #include "components/proximity_auth/ble/bluetooth_low_energy_weave_client_connec tion.h"
6 6
7 #include <utility> 7 #include <utility>
8 8
9 #include "base/bind.h" 9 #include "base/bind.h"
10 #include "base/location.h" 10 #include "base/location.h"
11 #include "base/memory/ref_counted.h"
12 #include "base/memory/weak_ptr.h"
13 #include "base/task_runner.h" 11 #include "base/task_runner.h"
14 #include "base/threading/thread_task_runner_handle.h" 12 #include "base/threading/thread_task_runner_handle.h"
15 #include "base/time/time.h"
16 #include "components/proximity_auth/ble/bluetooth_low_energy_characteristics_fin der.h"
17 #include "components/proximity_auth/ble/fake_wire_message.h"
18 #include "components/proximity_auth/bluetooth_throttler.h" 13 #include "components/proximity_auth/bluetooth_throttler.h"
19 #include "components/proximity_auth/connection_finder.h" 14 #include "components/proximity_auth/connection_finder.h"
20 #include "components/proximity_auth/logging/logging.h" 15 #include "components/proximity_auth/logging/logging.h"
21 #include "components/proximity_auth/wire_message.h" 16 #include "components/proximity_auth/wire_message.h"
22 #include "device/bluetooth/bluetooth_adapter.h"
23 #include "device/bluetooth/bluetooth_device.h"
24 #include "device/bluetooth/bluetooth_gatt_connection.h" 17 #include "device/bluetooth/bluetooth_gatt_connection.h"
25 #include "device/bluetooth/bluetooth_gatt_notify_session.h"
26 #include "device/bluetooth/bluetooth_remote_gatt_characteristic.h"
27 #include "device/bluetooth/bluetooth_uuid.h"
28 18
29 using device::BluetoothAdapter; 19 using device::BluetoothAdapter;
30 using device::BluetoothDevice; 20 using device::BluetoothDevice;
31 using device::BluetoothGattConnection; 21 using device::BluetoothGattConnection;
32 using device::BluetoothRemoteGattService; 22 using device::BluetoothRemoteGattService;
33 using device::BluetoothRemoteGattCharacteristic; 23 using device::BluetoothRemoteGattCharacteristic;
34 using device::BluetoothGattNotifySession; 24 using device::BluetoothGattNotifySession;
35 using device::BluetoothUUID; 25 using device::BluetoothUUID;
36 26
37 namespace proximity_auth { 27 namespace proximity_auth {
28 namespace weave {
38 namespace { 29 namespace {
39 30
40 // The UUID of the characteristic used to send data to the peripheral. 31 typedef BluetoothLowEnergyWeavePacketReceiver::State ReceiverState;
41 const char kToPeripheralCharUUID[] = "977c6674-1239-4e72-993b-502369b8bb5a";
42 32
43 // The UUID of the characteristic used to receive data from the peripheral. 33 // The UUID of the TX characteristic used to transmit data to the server.
44 const char kFromPeripheralCharUUID[] = "f4b904a2-a030-43b3-98a8-221c536c03cb"; 34 const char kTXCharacteristicUUID[] = "00000100-0004-1000-8000-001A11000101";
45 35
46 // Deprecated signal send as the first byte in send byte operations. 36 // The UUID of the RX characteristic used to receive data from the server.
47 const int kFirstByteZero = 0; 37 const char kRXCharacteristicUUID[] = "00000100-0004-1000-8000-001A11000102";
48 38
49 // The maximum number of bytes written in a remote characteristic with a single
50 // write request. This is not the connection MTU, we are assuming that the
51 // remote device allows for writes larger than MTU.
52 const int kMaxChunkSize = 500;
53 } // namespace 39 } // namespace
54 40
55 BluetoothLowEnergyConnection::BluetoothLowEnergyConnection( 41 BluetoothLowEnergyWeaveClientConnection::
56 const RemoteDevice& device, 42 BluetoothLowEnergyWeaveClientConnection(
57 scoped_refptr<device::BluetoothAdapter> adapter, 43 const RemoteDevice& device,
58 const BluetoothUUID remote_service_uuid, 44 scoped_refptr<device::BluetoothAdapter> adapter,
59 BluetoothThrottler* bluetooth_throttler, 45 const BluetoothUUID remote_service_uuid,
60 int max_number_of_write_attempts) 46 BluetoothThrottler* bluetooth_throttler,
47 int max_number_of_write_attempts)
61 : Connection(device), 48 : Connection(device),
62 adapter_(adapter), 49 adapter_(adapter),
63 remote_service_({remote_service_uuid, ""}), 50 remote_service_({remote_service_uuid, ""}),
64 to_peripheral_char_({BluetoothUUID(kToPeripheralCharUUID), ""}), 51 packet_generator_(
65 from_peripheral_char_({BluetoothUUID(kFromPeripheralCharUUID), ""}), 52 BluetoothLowEnergyWeavePacketGenerator::Factory::NewInstance()),
53 packet_receiver_(
54 BluetoothLowEnergyWeavePacketReceiver::Factory::NewInstance(
55 BluetoothLowEnergyWeavePacketReceiver::ReceiverType::CLIENT)),
56 tx_characteristic_({BluetoothUUID(kTXCharacteristicUUID), ""}),
57 rx_characteristic_({BluetoothUUID(kRXCharacteristicUUID), ""}),
66 bluetooth_throttler_(bluetooth_throttler), 58 bluetooth_throttler_(bluetooth_throttler),
67 task_runner_(base::ThreadTaskRunnerHandle::Get()), 59 task_runner_(base::ThreadTaskRunnerHandle::Get()),
68 sub_status_(SubStatus::DISCONNECTED), 60 sub_status_(SubStatus::DISCONNECTED),
69 receiving_bytes_(false),
70 write_remote_characteristic_pending_(false), 61 write_remote_characteristic_pending_(false),
71 max_number_of_write_attempts_(max_number_of_write_attempts), 62 max_number_of_write_attempts_(max_number_of_write_attempts),
72 max_chunk_size_(kMaxChunkSize),
73 weak_ptr_factory_(this) { 63 weak_ptr_factory_(this) {
74 DCHECK(adapter_); 64 DCHECK(adapter_);
75 DCHECK(adapter_->IsInitialized()); 65 DCHECK(adapter_->IsInitialized());
76 66
77 adapter_->AddObserver(this); 67 adapter_->AddObserver(this);
78 } 68 }
79 69
80 BluetoothLowEnergyConnection::~BluetoothLowEnergyConnection() { 70 BluetoothLowEnergyWeaveClientConnection::
71 ~BluetoothLowEnergyWeaveClientConnection() {
81 Disconnect(); 72 Disconnect();
82 if (adapter_) { 73 if (adapter_) {
83 adapter_->RemoveObserver(this); 74 adapter_->RemoveObserver(this);
84 adapter_ = NULL; 75 adapter_ = NULL;
85 } 76 }
86 } 77 }
87 78
88 void BluetoothLowEnergyConnection::Connect() { 79 void BluetoothLowEnergyWeaveClientConnection::Connect() {
89 DCHECK(sub_status() == SubStatus::DISCONNECTED); 80 DCHECK(sub_status() == SubStatus::DISCONNECTED);
90 81
91 SetSubStatus(SubStatus::WAITING_GATT_CONNECTION); 82 SetSubStatus(SubStatus::WAITING_GATT_CONNECTION);
92 base::TimeDelta throttler_delay = bluetooth_throttler_->GetDelay(); 83 base::TimeDelta throttler_delay = bluetooth_throttler_->GetDelay();
93 PA_LOG(INFO) << "Connecting in " << throttler_delay; 84 PA_LOG(INFO) << "Connecting in " << throttler_delay;
94 85
95 start_time_ = base::TimeTicks::Now(); 86 start_time_ = base::TimeTicks::Now();
96 87
97 // If necessary, wait to create a new GATT connection. 88 // If necessary, wait to create a new GATT connection.
98 // 89 //
99 // Avoid creating a new GATT connection immediately after a given device was 90 // Avoid creating a new GATT connection immediately after a given device was
100 // disconnected. This is a workaround for crbug.com/508919. 91 // disconnected. This is a workaround for crbug.com/508919.
101 if (!throttler_delay.is_zero()) { 92 if (!throttler_delay.is_zero()) {
102 task_runner_->PostDelayedTask( 93 task_runner_->PostDelayedTask(
103 FROM_HERE, 94 FROM_HERE,
104 base::Bind(&BluetoothLowEnergyConnection::CreateGattConnection, 95 base::Bind(
105 weak_ptr_factory_.GetWeakPtr()), 96 &BluetoothLowEnergyWeaveClientConnection::CreateGattConnection,
97 weak_ptr_factory_.GetWeakPtr()),
106 throttler_delay); 98 throttler_delay);
107 return; 99 return;
108 } 100 }
109 101
110 CreateGattConnection(); 102 CreateGattConnection();
111 } 103 }
112 104
113 void BluetoothLowEnergyConnection::CreateGattConnection() { 105 void BluetoothLowEnergyWeaveClientConnection::CreateGattConnection() {
114 DCHECK(sub_status() == SubStatus::WAITING_GATT_CONNECTION); 106 DCHECK(sub_status() == SubStatus::WAITING_GATT_CONNECTION);
115 107
116 BluetoothDevice* remote_device = GetRemoteDevice(); 108 BluetoothDevice* remote_device = GetRemoteDevice();
117 if (remote_device) { 109 if (remote_device) {
118 PA_LOG(INFO) << "Creating GATT connection with " 110 PA_LOG(INFO) << "Creating GATT connection with "
119 << remote_device->GetAddress(); 111 << remote_device->GetAddress();
120 112
121 remote_device->CreateGattConnection( 113 remote_device->CreateGattConnection(
122 base::Bind(&BluetoothLowEnergyConnection::OnGattConnectionCreated, 114 base::Bind(
123 weak_ptr_factory_.GetWeakPtr()), 115 &BluetoothLowEnergyWeaveClientConnection::OnGattConnectionCreated,
124 base::Bind(&BluetoothLowEnergyConnection::OnCreateGattConnectionError, 116 weak_ptr_factory_.GetWeakPtr()),
117 base::Bind(&BluetoothLowEnergyWeaveClientConnection::
118 OnCreateGattConnectionError,
125 weak_ptr_factory_.GetWeakPtr())); 119 weak_ptr_factory_.GetWeakPtr()));
126 } 120 }
127 } 121 }
128 122
129 void BluetoothLowEnergyConnection::Disconnect() { 123 void BluetoothLowEnergyWeaveClientConnection::Disconnect() {
130 if (sub_status() != SubStatus::DISCONNECTED) { 124 if (sub_status() != SubStatus::DISCONNECTED) {
131 weak_ptr_factory_.InvalidateWeakPtrs(); 125 weak_ptr_factory_.InvalidateWeakPtrs();
132 StopNotifySession(); 126 StopNotifySession();
133 characteristic_finder_.reset(); 127 characteristic_finder_.reset();
134 if (gatt_connection_) { 128 if (gatt_connection_) {
135 PA_LOG(INFO) << "Disconnect from device " 129 PA_LOG(INFO) << "Disconnect from device "
136 << gatt_connection_->GetDeviceAddress(); 130 << gatt_connection_->GetDeviceAddress();
137 131
138 // Destroying BluetoothGattConnection also disconnects it. 132 // Destroying BluetoothGattConnection also disconnects it.
139 gatt_connection_.reset(); 133 gatt_connection_.reset();
140 } 134 }
141 135
142 // Only transition to the DISCONNECTED state after perfoming all necessary 136 // Only transition to the DISCONNECTED state after perfoming all necessary
143 // operations. Otherwise, it'll trigger observers that can pontentially 137 // operations. Otherwise, it'll trigger observers that can pontentially
144 // destroy the current instance (causing a crash). 138 // destroy the current instance (causing a crash).
145 SetSubStatus(SubStatus::DISCONNECTED); 139 SetSubStatus(SubStatus::DISCONNECTED);
146 } 140 }
147 } 141 }
148 142
149 void BluetoothLowEnergyConnection::SetSubStatus(SubStatus new_sub_status) { 143 void BluetoothLowEnergyWeaveClientConnection::SetSubStatus(
144 SubStatus new_sub_status) {
150 sub_status_ = new_sub_status; 145 sub_status_ = new_sub_status;
151 146
152 // Sets the status of parent class proximity_auth::Connection accordingly. 147 // Sets the status of parent class proximity_auth::Connection accordingly.
153 if (new_sub_status == SubStatus::CONNECTED) { 148 if (new_sub_status == SubStatus::CONNECTED) {
154 SetStatus(CONNECTED); 149 SetStatus(Status::CONNECTED);
155 } else if (new_sub_status == SubStatus::DISCONNECTED) { 150 } else if (new_sub_status == SubStatus::DISCONNECTED) {
156 SetStatus(DISCONNECTED); 151 SetStatus(Status::DISCONNECTED);
157 } else { 152 } else {
158 SetStatus(IN_PROGRESS); 153 SetStatus(Status::IN_PROGRESS);
159 } 154 }
160 } 155 }
161 156
162 void BluetoothLowEnergyConnection::SetTaskRunnerForTesting( 157 void BluetoothLowEnergyWeaveClientConnection::SetTaskRunnerForTesting(
163 scoped_refptr<base::TaskRunner> task_runner) { 158 scoped_refptr<base::TaskRunner> task_runner) {
164 task_runner_ = task_runner; 159 task_runner_ = task_runner;
165 } 160 }
166 161
167 void BluetoothLowEnergyConnection::SendMessageImpl( 162 void BluetoothLowEnergyWeaveClientConnection::SendMessageImpl(
168 std::unique_ptr<WireMessage> message) { 163 std::unique_ptr<WireMessage> message) {
169 PA_LOG(INFO) << "Sending message " << message->Serialize(); 164 PA_LOG(INFO) << "Sending message " << message->Serialize();
170 std::string serialized_msg = message->Serialize(); 165 std::string serialized_msg = message->Serialize();
171 166
172 // [First write]: Build a header with the [send signal] + [size of the 167 std::vector<Packet> packets =
173 // message]. 168 packet_generator_->EncodeDataMessage(serialized_msg);
174 WriteRequest write_request = BuildWriteRequest(
175 ToByteVector(static_cast<uint32_t>(ControlSignal::kSendSignal)),
176 ToByteVector(static_cast<uint32_t>(serialized_msg.size())), false);
177 169
178 // [First write]: Fill the it with a prefix of |serialized_msg| up to 170 for (uint32_t i = 0; i < packets.size(); ++i) {
179 // |max_chunk_size_|. 171 WriteRequest request = WriteRequest(packets[i], i == packets.size() - 1);
180 size_t first_chunk_size = std::min( 172 WriteRemoteCharacteristic(request);
181 max_chunk_size_ - write_request.value.size(), serialized_msg.size());
182 std::vector<uint8_t> bytes(serialized_msg.begin(),
183 serialized_msg.begin() + first_chunk_size);
184 write_request.value.insert(write_request.value.end(), bytes.begin(),
185 bytes.end());
186
187 bool is_last_write_request = first_chunk_size == serialized_msg.size();
188 write_request.is_last_write_for_wire_message = is_last_write_request;
189 WriteRemoteCharacteristic(write_request);
190 if (is_last_write_request)
191 return;
192
193 // [Other write requests]: Each chunk has to include a deprecated signal:
194 // |kFirstByteZero| as the first byte.
195 int chunk_size = max_chunk_size_ - 1;
196 std::vector<uint8_t> kFirstByteZeroVector;
197 kFirstByteZeroVector.push_back(static_cast<uint8_t>(kFirstByteZero));
198
199 int message_size = static_cast<int>(serialized_msg.size());
200 int start_index = first_chunk_size;
201 while (start_index < message_size) {
202 int end_index = (start_index + chunk_size) <= message_size
203 ? (start_index + chunk_size)
204 : message_size;
205 bool is_last_write_request = (end_index == message_size);
206 write_request = BuildWriteRequest(
207 kFirstByteZeroVector,
208 std::vector<uint8_t>(serialized_msg.begin() + start_index,
209 serialized_msg.begin() + end_index),
210 is_last_write_request);
211 WriteRemoteCharacteristic(write_request);
212 start_index = end_index;
213 } 173 }
214 } 174 }
215 175
216 // Changes in the GATT connection with the remote device should be observed 176 // Changes in the GATT connection with the remote device should be observed
217 // here. If the GATT connection is dropped, we should call Disconnect() anyway, 177 // here. If the GATT connection is dropped, we should call Disconnect() anyway,
218 // so the object can notify its observers. 178 // so the object can notify its observers.
219 void BluetoothLowEnergyConnection::DeviceChanged(BluetoothAdapter* adapter, 179 void BluetoothLowEnergyWeaveClientConnection::DeviceChanged(
220 BluetoothDevice* device) { 180 BluetoothAdapter* adapter,
181 BluetoothDevice* device) {
221 DCHECK(device); 182 DCHECK(device);
222 if (sub_status() == SubStatus::DISCONNECTED || 183 if (sub_status() == SubStatus::DISCONNECTED ||
223 device->GetAddress() != GetDeviceAddress()) 184 device->GetAddress() != GetDeviceAddress())
224 return; 185 return;
225 186
226 if (sub_status() != SubStatus::WAITING_GATT_CONNECTION && 187 if (sub_status() != SubStatus::WAITING_GATT_CONNECTION &&
227 !device->IsConnected()) { 188 !device->IsConnected()) {
228 PA_LOG(INFO) << "GATT connection dropped " << GetDeviceAddress() 189 PA_LOG(INFO) << "GATT connection dropped " << GetDeviceAddress()
229 << "\ndevice connected: " << device->IsConnected() 190 << "\ndevice connected: " << device->IsConnected()
230 << "\ngatt connection: " 191 << "\ngatt connection: "
231 << (gatt_connection_ ? gatt_connection_->IsConnected() 192 << (gatt_connection_ ? gatt_connection_->IsConnected()
232 : false); 193 : false);
233 Disconnect(); 194 Disconnect();
234 } 195 }
235 } 196 }
236 197
237 void BluetoothLowEnergyConnection::DeviceRemoved(BluetoothAdapter* adapter, 198 void BluetoothLowEnergyWeaveClientConnection::DeviceRemoved(
238 BluetoothDevice* device) { 199 BluetoothAdapter* adapter,
200 BluetoothDevice* device) {
239 DCHECK(device); 201 DCHECK(device);
240 if (sub_status_ == SubStatus::DISCONNECTED || 202 if (sub_status_ == SubStatus::DISCONNECTED ||
241 device->GetAddress() != GetDeviceAddress()) 203 device->GetAddress() != GetDeviceAddress())
242 return; 204 return;
243 205
244 PA_LOG(INFO) << "Device removed " << GetDeviceAddress(); 206 PA_LOG(INFO) << "Device removed " << GetDeviceAddress();
245 Disconnect(); 207 Disconnect();
246 } 208 }
247 209
248 void BluetoothLowEnergyConnection::GattCharacteristicValueChanged( 210 void BluetoothLowEnergyWeaveClientConnection::GattCharacteristicValueChanged(
249 BluetoothAdapter* adapter, 211 BluetoothAdapter* adapter,
250 BluetoothRemoteGattCharacteristic* characteristic, 212 BluetoothRemoteGattCharacteristic* characteristic,
251 const std::vector<uint8_t>& value) { 213 const Packet& value) {
252 DCHECK_EQ(adapter, adapter_.get()); 214 DCHECK_EQ(adapter, adapter_.get());
253 if (sub_status() != SubStatus::WAITING_RESPONSE_SIGNAL && 215 if (sub_status() != SubStatus::WAITING_CONNECTION_RESPONSE &&
254 sub_status() != SubStatus::CONNECTED) 216 sub_status() != SubStatus::CONNECTED)
255 return; 217 return;
256 218
257 PA_LOG(INFO) << "Characteristic value changed: " 219 PA_LOG(INFO) << "Characteristic value changed: "
258 << characteristic->GetUUID().canonical_value(); 220 << characteristic->GetUUID().canonical_value();
259 221
260 if (characteristic->GetIdentifier() == from_peripheral_char_.id) { 222 if (characteristic->GetIdentifier() == rx_characteristic_.id) {
Kyle Horimoto 2016/06/30 18:00:23 It looks like none of this new logic you added is
jingxuy 2016/06/30 21:59:26 Since certain functions are only called in certain
261 if (receiving_bytes_) { 223 ReceiverState state = packet_receiver_->ReceivePacket(value);
262 // Ignoring the first byte, as it contains a deprecated signal. 224 PA_LOG(INFO) << "\nReceiver State: " << state;
263 const std::string bytes(value.begin() + 1, value.end()); 225 switch (state) {
264 incoming_bytes_buffer_.append(bytes); 226 case ReceiverState::DATA_READY:
265 if (incoming_bytes_buffer_.size() >= expected_number_of_incoming_bytes_) { 227 OnBytesReceived(packet_receiver_->GetDataMessage());
266 OnBytesReceived(incoming_bytes_buffer_); 228 break;
267 receiving_bytes_ = false; 229 case ReceiverState::CONNECTION_CLOSED:
268 } 230 PA_LOG(ERROR) << "Connection closed due to: " << GetReasonForClose();
269 return; 231 Disconnect();
270 } 232 break;
271 233 case ReceiverState::ERROR_DETECTED:
272 if (value.size() < 4) { 234 // TODO(jingxuy): test this once the design has been confirmed
273 PA_LOG(WARNING) << "Incoming data corrupted, no signal found."; 235 WriteConnectionClose(packet_generator_->CreateConnectionClose(
274 return; 236 packet_receiver_->GetReasonToClose()));
275 } 237 Disconnect();
276 238 break;
277 const ControlSignal signal = static_cast<ControlSignal>(ToUint32(value)); 239 case ReceiverState::WAITING:
278 switch (signal) { 240 // Receiver state should have changed from CONNECTING to WAITING if
279 case ControlSignal::kInvitationResponseSignal: 241 // a proper connection response had been received.
280 if (sub_status() == SubStatus::WAITING_RESPONSE_SIGNAL) 242 // The max packet size selected from the connection response will be
243 // used to generate future data packets.
244 packet_generator_->SetMaxPacketSize(
245 packet_receiver_->GetMaxPacketSize());
246 if (sub_status() == SubStatus::WAITING_CONNECTION_RESPONSE)
281 CompleteConnection(); 247 CompleteConnection();
282 break; 248 break;
283 case ControlSignal::kInviteToConnectSignal: 249 case ReceiverState::RECEIVING_DATA:
250 // Normal in between states, so do nothing.
284 break; 251 break;
285 case ControlSignal::kSendSignal: { 252 default:
286 if (value.size() < 8) { 253 NOTREACHED();
287 PA_LOG(WARNING)
288 << "Incoming data corrupted, expected message size not found.";
289 return;
290 }
291 std::vector<uint8_t> size(value.begin() + 4, value.begin() + 8);
292 expected_number_of_incoming_bytes_ =
293 static_cast<size_t>(ToUint32(size));
294 receiving_bytes_ = true;
295 incoming_bytes_buffer_.clear();
296
297 const std::string bytes(value.begin() + 8, value.end());
298 incoming_bytes_buffer_.append(bytes);
299 if (incoming_bytes_buffer_.size() >=
300 expected_number_of_incoming_bytes_) {
301 OnBytesReceived(incoming_bytes_buffer_);
302 receiving_bytes_ = false;
303 }
304 break;
305 }
306 case ControlSignal::kDisconnectSignal:
307 PA_LOG(INFO) << "Disconnect signal received.";
308 Disconnect();
309 break;
310 } 254 }
311 } 255 }
312 } 256 }
313 257
314 BluetoothLowEnergyConnection::WriteRequest::WriteRequest( 258 BluetoothLowEnergyWeaveClientConnection::WriteRequest::WriteRequest(
315 const std::vector<uint8_t>& val, 259 const Packet& val,
316 bool flag) 260 bool flag)
317 : value(val), 261 : value(val),
318 is_last_write_for_wire_message(flag), 262 is_last_write_for_wire_message(flag),
319 number_of_failed_attempts(0) {} 263 number_of_failed_attempts(0) {}
320 264
321 BluetoothLowEnergyConnection::WriteRequest::WriteRequest( 265 BluetoothLowEnergyWeaveClientConnection::WriteRequest::WriteRequest(
322 const WriteRequest& other) = default; 266 const WriteRequest& other) = default;
323 267
324 BluetoothLowEnergyConnection::WriteRequest::~WriteRequest() {} 268 BluetoothLowEnergyWeaveClientConnection::WriteRequest::~WriteRequest() {}
325 269
326 void BluetoothLowEnergyConnection::CompleteConnection() { 270 void BluetoothLowEnergyWeaveClientConnection::CompleteConnection() {
327 PA_LOG(INFO) << "Connection completed. Time elapsed: " 271 PA_LOG(INFO) << "Connection completed. Time elapsed: "
328 << base::TimeTicks::Now() - start_time_; 272 << base::TimeTicks::Now() - start_time_;
329 SetSubStatus(SubStatus::CONNECTED); 273 SetSubStatus(SubStatus::CONNECTED);
330 } 274 }
331 275
332 void BluetoothLowEnergyConnection::OnCreateGattConnectionError( 276 void BluetoothLowEnergyWeaveClientConnection::OnCreateGattConnectionError(
333 device::BluetoothDevice::ConnectErrorCode error_code) { 277 device::BluetoothDevice::ConnectErrorCode error_code) {
334 DCHECK(sub_status_ == SubStatus::WAITING_GATT_CONNECTION); 278 DCHECK(sub_status_ == SubStatus::WAITING_GATT_CONNECTION);
335 PA_LOG(WARNING) << "Error creating GATT connection to " 279 PA_LOG(WARNING) << "Error creating GATT connection to "
336 << remote_device().bluetooth_address 280 << remote_device().bluetooth_address
337 << "error code: " << error_code; 281 << "error code: " << error_code;
338 Disconnect(); 282 Disconnect();
339 } 283 }
340 284
341 void BluetoothLowEnergyConnection::OnGattConnectionCreated( 285 void BluetoothLowEnergyWeaveClientConnection::OnGattConnectionCreated(
342 std::unique_ptr<device::BluetoothGattConnection> gatt_connection) { 286 std::unique_ptr<device::BluetoothGattConnection> gatt_connection) {
343 DCHECK(sub_status() == SubStatus::WAITING_GATT_CONNECTION); 287 DCHECK(sub_status() == SubStatus::WAITING_GATT_CONNECTION);
344 PA_LOG(INFO) << "GATT connection with " << gatt_connection->GetDeviceAddress() 288 PA_LOG(INFO) << "GATT connection with " << gatt_connection->GetDeviceAddress()
345 << " created."; 289 << " created.";
346 PrintTimeElapsed(); 290 PrintTimeElapsed();
347 291
348 // Informing |bluetooth_trottler_| a new connection was established. 292 // Informing |bluetooth_trottler_| a new connection was established.
349 bluetooth_throttler_->OnConnection(this); 293 bluetooth_throttler_->OnConnection(this);
350 294
351 gatt_connection_ = std::move(gatt_connection); 295 gatt_connection_ = std::move(gatt_connection);
352 SetSubStatus(SubStatus::WAITING_CHARACTERISTICS); 296 SetSubStatus(SubStatus::WAITING_CHARACTERISTICS);
353 characteristic_finder_.reset(CreateCharacteristicsFinder( 297 characteristic_finder_.reset(CreateCharacteristicsFinder(
354 base::Bind(&BluetoothLowEnergyConnection::OnCharacteristicsFound, 298 base::Bind(
355 weak_ptr_factory_.GetWeakPtr()), 299 &BluetoothLowEnergyWeaveClientConnection::OnCharacteristicsFound,
356 base::Bind(&BluetoothLowEnergyConnection::OnCharacteristicsFinderError, 300 weak_ptr_factory_.GetWeakPtr()),
301 base::Bind(&BluetoothLowEnergyWeaveClientConnection::
302 OnCharacteristicsFinderError,
357 weak_ptr_factory_.GetWeakPtr()))); 303 weak_ptr_factory_.GetWeakPtr())));
358 } 304 }
359 305
360 BluetoothLowEnergyCharacteristicsFinder* 306 BluetoothLowEnergyCharacteristicsFinder*
361 BluetoothLowEnergyConnection::CreateCharacteristicsFinder( 307 BluetoothLowEnergyWeaveClientConnection::CreateCharacteristicsFinder(
362 const BluetoothLowEnergyCharacteristicsFinder::SuccessCallback& 308 const BluetoothLowEnergyCharacteristicsFinder::SuccessCallback&
363 success_callback, 309 success_callback,
364 const BluetoothLowEnergyCharacteristicsFinder::ErrorCallback& 310 const BluetoothLowEnergyCharacteristicsFinder::ErrorCallback&
365 error_callback) { 311 error_callback) {
366 return new BluetoothLowEnergyCharacteristicsFinder( 312 return new BluetoothLowEnergyCharacteristicsFinder(
367 adapter_, GetRemoteDevice(), remote_service_, to_peripheral_char_, 313 adapter_, GetRemoteDevice(), remote_service_, tx_characteristic_,
368 from_peripheral_char_, success_callback, error_callback); 314 rx_characteristic_, success_callback, error_callback);
369 } 315 }
370 316
371 void BluetoothLowEnergyConnection::OnCharacteristicsFound( 317 void BluetoothLowEnergyWeaveClientConnection::OnCharacteristicsFound(
372 const RemoteAttribute& service, 318 const RemoteAttribute& service,
373 const RemoteAttribute& to_peripheral_char, 319 const RemoteAttribute& tx_characteristic,
374 const RemoteAttribute& from_peripheral_char) { 320 const RemoteAttribute& rx_characteristic) {
375 PA_LOG(INFO) << "Remote chacteristics found."; 321 PA_LOG(INFO) << "Remote chacteristics found.";
376 PrintTimeElapsed(); 322 PrintTimeElapsed();
377 323
378 DCHECK(sub_status() == SubStatus::WAITING_CHARACTERISTICS); 324 DCHECK(sub_status() == SubStatus::WAITING_CHARACTERISTICS);
379 remote_service_ = service; 325 remote_service_ = service;
380 to_peripheral_char_ = to_peripheral_char; 326 tx_characteristic_ = tx_characteristic;
381 from_peripheral_char_ = from_peripheral_char; 327 rx_characteristic_ = rx_characteristic;
382 328
383 SetSubStatus(SubStatus::CHARACTERISTICS_FOUND); 329 SetSubStatus(SubStatus::CHARACTERISTICS_FOUND);
384 StartNotifySession(); 330 StartNotifySession();
385 } 331 }
386 332
387 void BluetoothLowEnergyConnection::OnCharacteristicsFinderError( 333 void BluetoothLowEnergyWeaveClientConnection::OnCharacteristicsFinderError(
388 const RemoteAttribute& to_peripheral_char, 334 const RemoteAttribute& tx_characteristic,
389 const RemoteAttribute& from_peripheral_char) { 335 const RemoteAttribute& rx_characteristic) {
390 DCHECK(sub_status() == SubStatus::WAITING_CHARACTERISTICS); 336 DCHECK(sub_status() == SubStatus::WAITING_CHARACTERISTICS);
391 PA_LOG(WARNING) << "Connection error, missing characteristics for SmartLock " 337 PA_LOG(WARNING) << "Connection error, missing characteristics for SmartLock "
392 "service.\n" 338 "service.\n"
393 << (to_peripheral_char.id.empty() 339 << (tx_characteristic.id.empty()
394 ? to_peripheral_char.uuid.canonical_value() 340 ? tx_characteristic.uuid.canonical_value()
395 : "") 341 : "")
396 << (from_peripheral_char.id.empty() 342 << (rx_characteristic.id.empty()
397 ? ", " + from_peripheral_char.uuid.canonical_value() 343 ? ", " + rx_characteristic.uuid.canonical_value()
398 : "") << " not found."; 344 : "")
345 << " not found.";
399 346
400 Disconnect(); 347 Disconnect();
401 } 348 }
402 349
403 void BluetoothLowEnergyConnection::StartNotifySession() { 350 void BluetoothLowEnergyWeaveClientConnection::StartNotifySession() {
404 if (sub_status() == SubStatus::CHARACTERISTICS_FOUND) { 351 if (sub_status() == SubStatus::CHARACTERISTICS_FOUND) {
405 BluetoothRemoteGattCharacteristic* characteristic = 352 BluetoothRemoteGattCharacteristic* characteristic =
406 GetGattCharacteristic(from_peripheral_char_.id); 353 GetGattCharacteristic(rx_characteristic_.id);
407 DCHECK(characteristic); 354 DCHECK(characteristic);
408 355
409 // This is a workaround for crbug.com/507325. If |characteristic| is already 356 // This is a workaround for crbug.com/507325. If |characteristic| is already
410 // notifying |characteristic->StartNotifySession()| will fail with 357 // notifying |characteristic->StartNotifySession()| will fail with
411 // GATT_ERROR_FAILED. 358 // GATT_ERROR_FAILED.
412 if (characteristic->IsNotifying()) { 359 if (characteristic->IsNotifying()) {
413 PA_LOG(INFO) << characteristic->GetUUID().canonical_value() 360 PA_LOG(INFO) << characteristic->GetUUID().canonical_value()
414 << " already notifying."; 361 << " already notifying.";
415 SetSubStatus(SubStatus::NOTIFY_SESSION_READY); 362 SetSubStatus(SubStatus::NOTIFY_SESSION_READY);
416 SendInviteToConnectSignal(); 363 SendConnectionRequest();
417 return; 364 return;
418 } 365 }
419 366
420 SetSubStatus(SubStatus::WAITING_NOTIFY_SESSION); 367 SetSubStatus(SubStatus::WAITING_NOTIFY_SESSION);
421 characteristic->StartNotifySession( 368 characteristic->StartNotifySession(
422 base::Bind(&BluetoothLowEnergyConnection::OnNotifySessionStarted, 369 base::Bind(
423 weak_ptr_factory_.GetWeakPtr()), 370 &BluetoothLowEnergyWeaveClientConnection::OnNotifySessionStarted,
424 base::Bind(&BluetoothLowEnergyConnection::OnNotifySessionError, 371 weak_ptr_factory_.GetWeakPtr()),
425 weak_ptr_factory_.GetWeakPtr())); 372 base::Bind(
373 &BluetoothLowEnergyWeaveClientConnection::OnNotifySessionError,
374 weak_ptr_factory_.GetWeakPtr()));
426 } 375 }
427 } 376 }
428 377
429 void BluetoothLowEnergyConnection::OnNotifySessionError( 378 void BluetoothLowEnergyWeaveClientConnection::OnNotifySessionStarted(
430 BluetoothRemoteGattService::GattErrorCode error) {
431 DCHECK(sub_status() == SubStatus::WAITING_NOTIFY_SESSION);
432 PA_LOG(WARNING) << "Error starting notification session: " << error;
433 Disconnect();
434 }
435
436 void BluetoothLowEnergyConnection::OnNotifySessionStarted(
437 std::unique_ptr<BluetoothGattNotifySession> notify_session) { 379 std::unique_ptr<BluetoothGattNotifySession> notify_session) {
438 DCHECK(sub_status() == SubStatus::WAITING_NOTIFY_SESSION); 380 DCHECK(sub_status() == SubStatus::WAITING_NOTIFY_SESSION);
439 PA_LOG(INFO) << "Notification session started " 381 PA_LOG(INFO) << "Notification session started "
440 << notify_session->GetCharacteristicIdentifier(); 382 << notify_session->GetCharacteristicIdentifier();
441 PrintTimeElapsed(); 383 PrintTimeElapsed();
442 384
443 SetSubStatus(SubStatus::NOTIFY_SESSION_READY); 385 SetSubStatus(SubStatus::NOTIFY_SESSION_READY);
444 notify_session_ = std::move(notify_session); 386 notify_session_ = std::move(notify_session);
445 387
446 SendInviteToConnectSignal(); 388 SendConnectionRequest();
447 } 389 }
448 390
449 void BluetoothLowEnergyConnection::StopNotifySession() { 391 void BluetoothLowEnergyWeaveClientConnection::OnNotifySessionError(
392 BluetoothRemoteGattService::GattErrorCode error) {
393 DCHECK(sub_status() == SubStatus::WAITING_NOTIFY_SESSION);
394 PA_LOG(WARNING) << "Error starting notification session: " << error;
395 Disconnect();
396 }
397
398 void BluetoothLowEnergyWeaveClientConnection::StopNotifySession() {
450 if (notify_session_) { 399 if (notify_session_) {
451 notify_session_->Stop(base::Bind(&base::DoNothing)); 400 notify_session_->Stop(base::Bind(&base::DoNothing));
452 notify_session_.reset(); 401 notify_session_.reset();
453 } 402 }
454 } 403 }
455 404
456 void BluetoothLowEnergyConnection::SendInviteToConnectSignal() { 405 void BluetoothLowEnergyWeaveClientConnection::SendConnectionRequest() {
457 if (sub_status() == SubStatus::NOTIFY_SESSION_READY) { 406 if (sub_status() == SubStatus::NOTIFY_SESSION_READY) {
458 PA_LOG(INFO) << "Sending invite to connect signal"; 407 PA_LOG(INFO) << "Sending connection request to the server";
459 SetSubStatus(SubStatus::WAITING_RESPONSE_SIGNAL); 408 SetSubStatus(SubStatus::WAITING_CONNECTION_RESPONSE);
460 409
461 WriteRequest write_request = BuildWriteRequest( 410 WriteRequest write_request =
462 ToByteVector( 411 WriteRequest(packet_generator_->CreateConnectionRequest(), false);
463 static_cast<uint32_t>(ControlSignal::kInviteToConnectSignal)),
464 std::vector<uint8_t>(), false);
465 412
466 WriteRemoteCharacteristic(write_request); 413 WriteRemoteCharacteristic(write_request);
467 } 414 }
468 } 415 }
469 416
470 void BluetoothLowEnergyConnection::WriteRemoteCharacteristic( 417 void BluetoothLowEnergyWeaveClientConnection::WriteConnectionClose(
471 WriteRequest request) { 418 const Packet& connection_close) {
419 // TODO(jingxuy): I know this is single threaded, but can it actually still
420 // have arbitrary overlay? If so, then this queue clear can race with
421 // ProcessNextWriteRequest.
422 std::queue<WriteRequest> empty;
423 std::swap(write_requests_queue_, empty);
424
425 // Spin wait on the current pending one unless overwritting is okay.
426 while (write_remote_characteristic_pending_) {
427 };
428
429 BluetoothRemoteGattCharacteristic* characteristic =
430 GetGattCharacteristic(tx_characteristic_.id);
431
432 characteristic->WriteRemoteCharacteristic(
433 connection_close,
434 base::Bind(
435 &BluetoothLowEnergyWeaveClientConnection::OnConnectionCloseWritten,
436 weak_ptr_factory_.GetWeakPtr()),
437 base::Bind(
438 &BluetoothLowEnergyWeaveClientConnection::OnConnectionCloseError,
439 weak_ptr_factory_.GetWeakPtr()));
440 }
441
442 void BluetoothLowEnergyWeaveClientConnection::OnConnectionCloseWritten() {
443 PA_LOG(INFO) << "Connection close written.";
444 Disconnect();
445 }
446
447 void BluetoothLowEnergyWeaveClientConnection::OnConnectionCloseError(
448 BluetoothRemoteGattService::GattErrorCode error) {
449 PA_LOG(INFO) << "Failed to write connection close due to GATT error: "
450 << error;
451 Disconnect();
452 }
453
454 void BluetoothLowEnergyWeaveClientConnection::WriteRemoteCharacteristic(
455 const WriteRequest& request) {
472 write_requests_queue_.push(request); 456 write_requests_queue_.push(request);
473 ProcessNextWriteRequest(); 457 ProcessNextWriteRequest();
474 } 458 }
475 459
476 void BluetoothLowEnergyConnection::ProcessNextWriteRequest() { 460 void BluetoothLowEnergyWeaveClientConnection::ProcessNextWriteRequest() {
477 BluetoothRemoteGattCharacteristic* characteristic = 461 BluetoothRemoteGattCharacteristic* characteristic =
478 GetGattCharacteristic(to_peripheral_char_.id); 462 GetGattCharacteristic(tx_characteristic_.id);
479 if (!write_requests_queue_.empty() && !write_remote_characteristic_pending_ && 463 if (!write_requests_queue_.empty() && !write_remote_characteristic_pending_ &&
480 characteristic) { 464 characteristic) {
481 write_remote_characteristic_pending_ = true; 465 write_remote_characteristic_pending_ = true;
482 WriteRequest next_request = write_requests_queue_.front(); 466 WriteRequest next_request = write_requests_queue_.front();
467
483 PA_LOG(INFO) << "Writing characteristic..."; 468 PA_LOG(INFO) << "Writing characteristic...";
484 characteristic->WriteRemoteCharacteristic( 469 characteristic->WriteRemoteCharacteristic(
485 next_request.value, 470 next_request.value,
486 base::Bind(&BluetoothLowEnergyConnection::OnRemoteCharacteristicWritten, 471 base::Bind(&BluetoothLowEnergyWeaveClientConnection::
472 OnRemoteCharacteristicWritten,
487 weak_ptr_factory_.GetWeakPtr(), 473 weak_ptr_factory_.GetWeakPtr(),
488 next_request.is_last_write_for_wire_message), 474 next_request.is_last_write_for_wire_message),
489 base::Bind( 475 base::Bind(&BluetoothLowEnergyWeaveClientConnection::
490 &BluetoothLowEnergyConnection::OnWriteRemoteCharacteristicError, 476 OnWriteRemoteCharacteristicError,
491 weak_ptr_factory_.GetWeakPtr(), 477 weak_ptr_factory_.GetWeakPtr(),
492 next_request.is_last_write_for_wire_message)); 478 next_request.is_last_write_for_wire_message));
493 } 479 }
494 } 480 }
495 481
496 void BluetoothLowEnergyConnection::OnRemoteCharacteristicWritten( 482 void BluetoothLowEnergyWeaveClientConnection::OnRemoteCharacteristicWritten(
497 bool run_did_send_message_callback) { 483 bool run_did_send_message_callback) {
498 PA_LOG(INFO) << "Characteristic written."; 484 PA_LOG(INFO) << "Characteristic written.";
499 write_remote_characteristic_pending_ = false; 485 write_remote_characteristic_pending_ = false;
500 // TODO(sacomoto): Actually pass the current message to the observer. 486 // TODO(sacomoto): Actually pass the current message to the observer.
501 if (run_did_send_message_callback) 487 if (run_did_send_message_callback)
502 OnDidSendMessage(WireMessage(std::string(), std::string()), true); 488 OnDidSendMessage(WireMessage(std::string(), std::string()), true);
503 489
504 // Removes the top of queue (already processed) and process the next request. 490 // Removes the top of queue (already processed) and process the next request.
505 DCHECK(!write_requests_queue_.empty()); 491 DCHECK(!write_requests_queue_.empty());
506 write_requests_queue_.pop(); 492 write_requests_queue_.pop();
507 ProcessNextWriteRequest(); 493 ProcessNextWriteRequest();
508 } 494 }
509 495
510 void BluetoothLowEnergyConnection::OnWriteRemoteCharacteristicError( 496 void BluetoothLowEnergyWeaveClientConnection::OnWriteRemoteCharacteristicError(
511 bool run_did_send_message_callback, 497 bool run_did_send_message_callback,
512 BluetoothRemoteGattService::GattErrorCode error) { 498 BluetoothRemoteGattService::GattErrorCode error) {
513 PA_LOG(WARNING) << "Error " << error << " writing characteristic: " 499 PA_LOG(WARNING) << "Error " << error << " writing characteristic: "
514 << to_peripheral_char_.uuid.canonical_value(); 500 << tx_characteristic_.uuid.canonical_value();
515 write_remote_characteristic_pending_ = false; 501 write_remote_characteristic_pending_ = false;
516 // TODO(sacomoto): Actually pass the current message to the observer. 502 // TODO(sacomoto): Actually pass the current message to the observer.
517 if (run_did_send_message_callback) 503 if (run_did_send_message_callback)
518 OnDidSendMessage(WireMessage(std::string(), std::string()), false); 504 OnDidSendMessage(WireMessage(std::string(), std::string()), false);
519 505
520 // Increases the number of failed attempts and retry. 506 // Increases the number of failed attempts and retry.
521 DCHECK(!write_requests_queue_.empty()); 507 DCHECK(!write_requests_queue_.empty());
522 if (++write_requests_queue_.front().number_of_failed_attempts >= 508 if (++write_requests_queue_.front().number_of_failed_attempts >=
523 max_number_of_write_attempts_) { 509 max_number_of_write_attempts_) {
524 Disconnect(); 510 Disconnect();
525 return; 511 return;
526 } 512 }
527 ProcessNextWriteRequest(); 513 ProcessNextWriteRequest();
528 } 514 }
529 515
530 BluetoothLowEnergyConnection::WriteRequest 516 void BluetoothLowEnergyWeaveClientConnection::PrintTimeElapsed() {
531 BluetoothLowEnergyConnection::BuildWriteRequest(
532 const std::vector<uint8_t>& signal,
533 const std::vector<uint8_t>& bytes,
534 bool is_last_write_for_wire_message) {
535 std::vector<uint8_t> value(signal.begin(), signal.end());
536 value.insert(value.end(), bytes.begin(), bytes.end());
537 return WriteRequest(value, is_last_write_for_wire_message);
538 }
539
540 void BluetoothLowEnergyConnection::PrintTimeElapsed() {
541 PA_LOG(INFO) << "Time elapsed: " << base::TimeTicks::Now() - start_time_; 517 PA_LOG(INFO) << "Time elapsed: " << base::TimeTicks::Now() - start_time_;
542 } 518 }
543 519
544 std::string BluetoothLowEnergyConnection::GetDeviceAddress() { 520 std::string BluetoothLowEnergyWeaveClientConnection::GetDeviceAddress() {
545 // When the remote device is connected we should rely on the address given by 521 // When the remote device is connected we should rely on the address given by
546 // |gatt_connection_|. As the device address may change if the device is 522 // |gatt_connection_|. As the device address may change if the device is
547 // paired. The address in |gatt_connection_| is automatically updated in this 523 // paired. The address in |gatt_connection_| is automatically updated in this
548 // case. 524 // case.
549 return gatt_connection_ ? gatt_connection_->GetDeviceAddress() 525 return gatt_connection_ ? gatt_connection_->GetDeviceAddress()
550 : remote_device().bluetooth_address; 526 : remote_device().bluetooth_address;
551 } 527 }
552 528
553 BluetoothDevice* BluetoothLowEnergyConnection::GetRemoteDevice() { 529 BluetoothDevice* BluetoothLowEnergyWeaveClientConnection::GetRemoteDevice() {
554 // It's not possible to simply use 530 // It's not possible to simply use
555 // |adapter_->GetDevice(GetDeviceAddress())| to find the device with MAC 531 // |adapter_->GetDevice(GetDeviceAddress())| to find the device with MAC
556 // address |GetDeviceAddress()|. For paired devices, 532 // address |GetDeviceAddress()|. For paired devices,
557 // BluetoothAdapter::GetDevice(XXX) searches for the temporary MAC address 533 // BluetoothAdapter::GetDevice(XXX) searches for the temporary MAC address
558 // XXX, whereas |GetDeviceAddress()| is the real MAC address. This is a 534 // XXX, whereas |GetDeviceAddress()| is the real MAC address. This is a
559 // bug in the way device::BluetoothAdapter is storing the devices (see 535 // bug in the way device::BluetoothAdapter is storing the devices (see
560 // crbug.com/497841). 536 // crbug.com/497841).
561 std::vector<BluetoothDevice*> devices = adapter_->GetDevices(); 537 std::vector<BluetoothDevice*> devices = adapter_->GetDevices();
562 for (const auto& device : devices) { 538 for (const auto& device : devices) {
563 if (device->GetAddress() == GetDeviceAddress()) 539 if (device->GetAddress() == GetDeviceAddress())
564 return device; 540 return device;
565 } 541 }
566 542
567 return nullptr; 543 return nullptr;
568 } 544 }
569 545
570 BluetoothRemoteGattService* BluetoothLowEnergyConnection::GetRemoteService() { 546 BluetoothRemoteGattService*
547 BluetoothLowEnergyWeaveClientConnection::GetRemoteService() {
571 BluetoothDevice* remote_device = GetRemoteDevice(); 548 BluetoothDevice* remote_device = GetRemoteDevice();
572 if (!remote_device) { 549 if (!remote_device) {
573 PA_LOG(WARNING) << "Remote device not found."; 550 PA_LOG(WARNING) << "Remote device not found.";
574 return NULL; 551 return NULL;
575 } 552 }
576 if (remote_service_.id.empty()) { 553 if (remote_service_.id.empty()) {
577 std::vector<BluetoothRemoteGattService*> services = 554 std::vector<BluetoothRemoteGattService*> services =
578 remote_device->GetGattServices(); 555 remote_device->GetGattServices();
579 for (const auto& service : services) 556 for (const auto& service : services)
580 if (service->GetUUID() == remote_service_.uuid) { 557 if (service->GetUUID() == remote_service_.uuid) {
581 remote_service_.id = service->GetIdentifier(); 558 remote_service_.id = service->GetIdentifier();
582 break; 559 break;
583 } 560 }
584 } 561 }
585 return remote_device->GetGattService(remote_service_.id); 562 return remote_device->GetGattService(remote_service_.id);
586 } 563 }
587 564
588 BluetoothRemoteGattCharacteristic* 565 BluetoothRemoteGattCharacteristic*
589 BluetoothLowEnergyConnection::GetGattCharacteristic( 566 BluetoothLowEnergyWeaveClientConnection::GetGattCharacteristic(
590 const std::string& gatt_characteristic) { 567 const std::string& gatt_characteristic) {
591 BluetoothRemoteGattService* remote_service = GetRemoteService(); 568 BluetoothRemoteGattService* remote_service = GetRemoteService();
592 if (!remote_service) { 569 if (!remote_service) {
593 PA_LOG(WARNING) << "Remote service not found."; 570 PA_LOG(WARNING) << "Remote service not found.";
594 return NULL; 571 return NULL;
595 } 572 }
596 return remote_service->GetCharacteristic(gatt_characteristic); 573 return remote_service->GetCharacteristic(gatt_characteristic);
597 } 574 }
598 575
599 // TODO(sacomoto): make this robust to byte ordering in both sides of the 576 std::string BluetoothLowEnergyWeaveClientConnection::GetReasonForClose() {
600 // SmartLock BLE socket. 577 switch (packet_receiver_->GetReasonForClose()) {
601 uint32_t BluetoothLowEnergyConnection::ToUint32( 578 case ReasonForClose::CLOSE_WITHOUT_ERROR:
602 const std::vector<uint8_t>& bytes) { 579 return "CLOSE_WITHOUT_ERROR";
603 return bytes[0] | (bytes[1] << 8) | (bytes[2] << 16) | (bytes[3] << 24); 580 case ReasonForClose::UNKNOWN_ERROR:
581 return "UNKNOWN_ERROR";
582 case ReasonForClose::NO_COMMON_VERSION_SUPPORTED:
583 return "NO_COMMON_VERSION_SUPPORTED";
584 case ReasonForClose::RECEIVED_PACKET_OUT_OF_SEQUENCE:
585 return "RECEIVED_PACKET_OUT_OF_SEQUENCE";
586 case ReasonForClose::APPLICATION_ERROR:
587 return "APPLICATION_ERROR";
588 default:
589 NOTREACHED();
590 }
604 } 591 }
605 592
606 // TODO(sacomoto): make this robust to byte ordering in both sides of the 593 } // namespace weave
607 // SmartLock BLE socket.
608 const std::vector<uint8_t> BluetoothLowEnergyConnection::ToByteVector(
609 const uint32_t value) {
610 std::vector<uint8_t> bytes(4, 0);
611 bytes[0] = static_cast<uint8_t>(value);
612 bytes[1] = static_cast<uint8_t>(value >> 8);
613 bytes[2] = static_cast<uint8_t>(value >> 16);
614 bytes[3] = static_cast<uint8_t>(value >> 24);
615 return bytes;
616 }
617 594
618 } // namespace proximity_auth 595 } // namespace proximity_auth
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698