Chromium Code Reviews| 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 #include "chrome/browser/chromeos/bluetooth/bluetooth_device.h" | 5 #include "chrome/browser/chromeos/bluetooth/bluetooth_device.h" |
| 6 | 6 |
| 7 #include <map> | |
| 7 #include <string> | 8 #include <string> |
| 8 #include <vector> | 9 #include <vector> |
| 9 | 10 |
| 11 #include <bluetooth/bluetooth.h> | |
| 12 #include <bluetooth/rfcomm.h> | |
| 13 #include <errno.h> | |
| 14 #include <sys/socket.h> | |
| 15 #include <sys/types.h> | |
| 16 | |
| 10 #include "base/bind.h" | 17 #include "base/bind.h" |
| 11 #include "base/logging.h" | 18 #include "base/logging.h" |
| 19 #include "base/memory/weak_ptr.h" | |
| 12 #include "base/string16.h" | 20 #include "base/string16.h" |
| 13 #include "base/string_util.h" | 21 #include "base/string_util.h" |
| 14 #include "base/utf_string_conversions.h" | 22 #include "base/utf_string_conversions.h" |
| 15 #include "base/values.h" | 23 #include "base/values.h" |
| 16 #include "chrome/browser/chromeos/bluetooth/bluetooth_adapter.h" | 24 #include "chrome/browser/chromeos/bluetooth/bluetooth_adapter.h" |
| 17 #include "chrome/browser/chromeos/bluetooth/bluetooth_service_record.h" | 25 #include "chrome/browser/chromeos/bluetooth/bluetooth_service_record.h" |
| 26 #include "chrome/browser/chromeos/bluetooth/bluetooth_socket.h" | |
| 18 #include "chrome/browser/chromeos/dbus/introspect_util.h" | 27 #include "chrome/browser/chromeos/dbus/introspect_util.h" |
| 19 #include "chromeos/dbus/bluetooth_adapter_client.h" | 28 #include "chromeos/dbus/bluetooth_adapter_client.h" |
| 20 #include "chromeos/dbus/bluetooth_agent_service_provider.h" | 29 #include "chromeos/dbus/bluetooth_agent_service_provider.h" |
| 21 #include "chromeos/dbus/bluetooth_device_client.h" | 30 #include "chromeos/dbus/bluetooth_device_client.h" |
| 22 #include "chromeos/dbus/bluetooth_input_client.h" | 31 #include "chromeos/dbus/bluetooth_input_client.h" |
| 23 #include "chromeos/dbus/dbus_thread_manager.h" | 32 #include "chromeos/dbus/dbus_thread_manager.h" |
| 24 #include "chromeos/dbus/introspectable_client.h" | 33 #include "chromeos/dbus/introspectable_client.h" |
| 25 #include "dbus/bus.h" | 34 #include "dbus/bus.h" |
| 26 #include "dbus/object_path.h" | 35 #include "dbus/object_path.h" |
| 27 #include "grit/generated_resources.h" | 36 #include "grit/generated_resources.h" |
| (...skipping 421 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 449 | 458 |
| 450 void BluetoothDevice::Forget(ErrorCallback error_callback) { | 459 void BluetoothDevice::Forget(ErrorCallback error_callback) { |
| 451 DBusThreadManager::Get()->GetBluetoothAdapterClient()-> | 460 DBusThreadManager::Get()->GetBluetoothAdapterClient()-> |
| 452 RemoveDevice(adapter_->object_path_, | 461 RemoveDevice(adapter_->object_path_, |
| 453 object_path_, | 462 object_path_, |
| 454 base::Bind(&BluetoothDevice::ForgetCallback, | 463 base::Bind(&BluetoothDevice::ForgetCallback, |
| 455 weak_ptr_factory_.GetWeakPtr(), | 464 weak_ptr_factory_.GetWeakPtr(), |
| 456 error_callback)); | 465 error_callback)); |
| 457 } | 466 } |
| 458 | 467 |
| 468 scoped_refptr<BluetoothSocket> BluetoothDevice::OpenSocket( | |
| 469 const std::string& service_uuid, uint8_t channel) { | |
| 470 // TODO(bryeung): add support for L2CAP sockets as well. | |
|
keybuk
2012/04/19 01:05:40
This seems to be in the wrong place, I was expecti
bryeung
2012/04/19 19:42:43
I put the code here because I wasn't sure how to d
| |
| 471 | |
| 472 // open a non-blocking socket, so the call to connect below will not block | |
| 473 int socket_fd = socket( | |
| 474 AF_BLUETOOTH, SOCK_STREAM | SOCK_NONBLOCK, BTPROTO_RFCOMM); | |
| 475 struct sockaddr_rc socket_address = { 0 }; | |
| 476 socket_address.rc_family = AF_BLUETOOTH; | |
| 477 socket_address.rc_channel = channel; | |
| 478 bdaddr_t* bluetooth_address = strtoba(address().c_str()); | |
| 479 bacpy(&(socket_address.rc_bdaddr), bluetooth_address); | |
| 480 free(bluetooth_address); | |
| 481 | |
| 482 // If EINPROGRESS, optimisticly assume that it will succeed eventually | |
|
keybuk
2012/04/19 01:05:40
I believe EINPROGRESS is the only likely return va
bryeung
2012/04/19 19:42:43
Done.
| |
| 483 int status = connect(socket_fd, (struct sockaddr *)&socket_address, | |
| 484 sizeof(socket_address)); | |
| 485 if (status == 0 || status == EINPROGRESS) { | |
|
keybuk
2012/04/19 01:05:40
connect doesn't return EINPROGRESS, it sets errno
bryeung
2012/04/19 19:42:43
Oops. Good catch. Thanks.
| |
| 486 BluetoothSocket* socket = new BluetoothSocket( | |
| 487 this, service_uuid, socket_fd); | |
| 488 return scoped_refptr<BluetoothSocket>(socket); | |
| 489 } | |
| 490 | |
| 491 return NULL; | |
| 492 } | |
| 493 | |
| 494 void BluetoothDevice::ConnectToMatchingService( | |
| 495 const std::string& service_uuid, | |
| 496 base::Callback<void(scoped_refptr<BluetoothSocket>)> callback, | |
| 497 const dbus::ObjectPath& object_path, | |
| 498 const BluetoothDeviceClient::ServiceMap& service_map, | |
| 499 bool success) { | |
| 500 if (success) { | |
| 501 // If multiple service records are found, use the first one that works. | |
| 502 BluetoothServiceRecord service_record; | |
| 503 for (BluetoothDeviceClient::ServiceMap::const_iterator i = | |
| 504 service_map.begin(); i != service_map.end(); ++i) { | |
| 505 if (!service_record.Init(i->second)) | |
|
keybuk
2012/04/19 01:05:40
Didn't we drop this Init stuff for a constructor?
bryeung
2012/04/19 19:42:43
Yep: we hadn't finished iterating on the other CL
| |
| 506 continue; | |
| 507 | |
|
keybuk
2012/04/19 01:05:40
You don't check if this is an rfcomm service?
bryeung
2012/04/19 19:42:43
Done.
| |
| 508 scoped_refptr<BluetoothSocket> socket = OpenSocket( | |
| 509 service_uuid, service_record.rfcomm_channel()); | |
|
keybuk
2012/04/19 01:05:40
Would be cleaner if this was a BluetoothSocket con
bryeung
2012/04/19 19:42:43
Done.
| |
| 510 if (socket.get() != NULL) { | |
| 511 callback.Run(socket); | |
| 512 break; | |
| 513 } | |
| 514 } | |
| 515 } | |
| 516 callback.Run(NULL); | |
| 517 } | |
| 518 | |
| 519 void BluetoothDevice::ConnectToService(const std::string& service_uuid, | |
| 520 base::Callback<void(scoped_refptr<BluetoothSocket>)> callback) { | |
| 521 // quick sanity check | |
| 522 if (!ProvidesServiceWithUUID(service_uuid)) { | |
| 523 callback.Run(NULL); | |
| 524 return; | |
| 525 } | |
| 526 | |
| 527 DBusThreadManager::Get()->GetBluetoothDeviceClient()-> | |
| 528 DiscoverServices( | |
| 529 object_path_, | |
| 530 service_uuid, | |
| 531 base::Bind(&BluetoothDevice::ConnectToMatchingService, | |
| 532 weak_ptr_factory_.GetWeakPtr(), | |
| 533 service_uuid, | |
| 534 callback)); | |
| 535 } | |
| 536 | |
| 459 void BluetoothDevice::ForgetCallback(ErrorCallback error_callback, | 537 void BluetoothDevice::ForgetCallback(ErrorCallback error_callback, |
| 460 const dbus::ObjectPath& adapter_path, | 538 const dbus::ObjectPath& adapter_path, |
| 461 bool success) { | 539 bool success) { |
| 462 // It's quite normal that this path never gets called on success; we use a | 540 // It's quite normal that this path never gets called on success; we use a |
| 463 // weak pointer, and bluetoothd might send the DeviceRemoved signal before | 541 // weak pointer, and bluetoothd might send the DeviceRemoved signal before |
| 464 // the method reply, in which case this object is deleted and the | 542 // the method reply, in which case this object is deleted and the |
| 465 // callback never takes place. Therefore don't do anything here for the | 543 // callback never takes place. Therefore don't do anything here for the |
| 466 // success case. | 544 // success case. |
| 467 if (!success) { | 545 if (!success) { |
| 468 LOG(WARNING) << "Forget failed: " << address_; | 546 LOG(WARNING) << "Forget failed: " << address_; |
| (...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 587 // static | 665 // static |
| 588 BluetoothDevice* BluetoothDevice::CreateUnbound( | 666 BluetoothDevice* BluetoothDevice::CreateUnbound( |
| 589 BluetoothAdapter* adapter, | 667 BluetoothAdapter* adapter, |
| 590 const BluetoothDeviceClient::Properties* properties) { | 668 const BluetoothDeviceClient::Properties* properties) { |
| 591 BluetoothDevice* device = new BluetoothDevice(adapter); | 669 BluetoothDevice* device = new BluetoothDevice(adapter); |
| 592 device->Update(properties, false); | 670 device->Update(properties, false); |
| 593 return device; | 671 return device; |
| 594 } | 672 } |
| 595 | 673 |
| 596 } // namespace chromeos | 674 } // namespace chromeos |
| OLD | NEW |