OLD | NEW |
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 "device/bluetooth/bluez/bluetooth_adapter_bluez.h" | 5 #include "device/bluetooth/bluez/bluetooth_adapter_bluez.h" |
6 | 6 |
7 #include <memory> | 7 #include <memory> |
8 #include <set> | 8 #include <set> |
9 #include <string> | 9 #include <string> |
10 #include <utility> | 10 #include <utility> |
11 | 11 |
12 #include "base/bind.h" | 12 #include "base/bind.h" |
13 #include "base/location.h" | 13 #include "base/location.h" |
14 #include "base/logging.h" | 14 #include "base/logging.h" |
15 #include "base/metrics/histogram.h" | 15 #include "base/metrics/histogram.h" |
16 #include "base/sequenced_task_runner.h" | 16 #include "base/sequenced_task_runner.h" |
17 #include "base/single_thread_task_runner.h" | 17 #include "base/single_thread_task_runner.h" |
18 #include "base/strings/stringprintf.h" | 18 #include "base/strings/stringprintf.h" |
19 #include "base/thread_task_runner_handle.h" | 19 #include "base/thread_task_runner_handle.h" |
20 #include "build/build_config.h" | 20 #include "build/build_config.h" |
21 #include "device/bluetooth/bluetooth_device.h" | 21 #include "device/bluetooth/bluetooth_device.h" |
22 #include "device/bluetooth/bluetooth_discovery_session_outcome.h" | 22 #include "device/bluetooth/bluetooth_discovery_session_outcome.h" |
23 #include "device/bluetooth/bluetooth_socket_thread.h" | 23 #include "device/bluetooth/bluetooth_socket_thread.h" |
24 #include "device/bluetooth/bluetooth_uuid.h" | 24 #include "device/bluetooth/bluetooth_uuid.h" |
25 #include "device/bluetooth/bluez/bluetooth_adapter_profile_bluez.h" | 25 #include "device/bluetooth/bluez/bluetooth_adapter_profile_bluez.h" |
26 #include "device/bluetooth/bluez/bluetooth_advertisement_bluez.h" | 26 #include "device/bluetooth/bluez/bluetooth_advertisement_bluez.h" |
27 #include "device/bluetooth/bluez/bluetooth_audio_sink_bluez.h" | 27 #include "device/bluetooth/bluez/bluetooth_audio_sink_bluez.h" |
28 #include "device/bluetooth/bluez/bluetooth_device_bluez.h" | 28 #include "device/bluetooth/bluez/bluetooth_device_bluez.h" |
| 29 #include "device/bluetooth/bluez/bluetooth_gatt_service_bluez.h" |
29 #include "device/bluetooth/bluez/bluetooth_local_gatt_service_bluez.h" | 30 #include "device/bluetooth/bluez/bluetooth_local_gatt_service_bluez.h" |
30 #include "device/bluetooth/bluez/bluetooth_pairing_bluez.h" | 31 #include "device/bluetooth/bluez/bluetooth_pairing_bluez.h" |
31 #include "device/bluetooth/bluez/bluetooth_socket_bluez.h" | 32 #include "device/bluetooth/bluez/bluetooth_socket_bluez.h" |
32 #include "device/bluetooth/dbus/bluetooth_adapter_client.h" | 33 #include "device/bluetooth/dbus/bluetooth_adapter_client.h" |
33 #include "device/bluetooth/dbus/bluetooth_agent_manager_client.h" | 34 #include "device/bluetooth/dbus/bluetooth_agent_manager_client.h" |
34 #include "device/bluetooth/dbus/bluetooth_agent_service_provider.h" | 35 #include "device/bluetooth/dbus/bluetooth_agent_service_provider.h" |
35 #include "device/bluetooth/dbus/bluetooth_device_client.h" | 36 #include "device/bluetooth/dbus/bluetooth_device_client.h" |
| 37 #include "device/bluetooth/dbus/bluetooth_gatt_application_service_provider.h" |
| 38 #include "device/bluetooth/dbus/bluetooth_gatt_manager_client.h" |
36 #include "device/bluetooth/dbus/bluetooth_input_client.h" | 39 #include "device/bluetooth/dbus/bluetooth_input_client.h" |
37 #include "device/bluetooth/dbus/bluez_dbus_manager.h" | 40 #include "device/bluetooth/dbus/bluez_dbus_manager.h" |
38 #include "third_party/cros_system_api/dbus/service_constants.h" | 41 #include "third_party/cros_system_api/dbus/service_constants.h" |
39 | 42 |
40 #if defined(OS_CHROMEOS) | 43 #if defined(OS_CHROMEOS) |
41 #include "chromeos/system/devicetype.h" | 44 #include "chromeos/system/devicetype.h" |
42 #endif | 45 #endif |
43 | 46 |
44 using device::BluetoothAdapter; | 47 using device::BluetoothAdapter; |
45 using device::BluetoothAudioSink; | 48 using device::BluetoothAudioSink; |
46 using device::BluetoothDevice; | 49 using device::BluetoothDevice; |
47 using device::BluetoothDiscoveryFilter; | 50 using device::BluetoothDiscoveryFilter; |
48 using device::BluetoothSocket; | 51 using device::BluetoothSocket; |
49 using device::BluetoothUUID; | 52 using device::BluetoothUUID; |
50 using device::UMABluetoothDiscoverySessionOutcome; | 53 using device::UMABluetoothDiscoverySessionOutcome; |
51 | 54 |
52 namespace { | 55 namespace { |
53 | 56 |
54 // The agent path is relatively meaningless since BlueZ only permits one to | 57 // The agent path is relatively meaningless since BlueZ only permits one to |
55 // exist per D-Bus connection, it just has to be unique within Chromium. | 58 // exist per D-Bus connection, it just has to be unique within Chromium. |
56 const char kAgentPath[] = "/org/chromium/bluetooth_agent"; | 59 const char kAgentPath[] = "/org/chromium/bluetooth_agent"; |
| 60 const char kGattApplicationObjectPath[] = "/gatt_application"; |
57 | 61 |
58 void OnUnregisterAgentError(const std::string& error_name, | 62 void OnUnregisterAgentError(const std::string& error_name, |
59 const std::string& error_message) { | 63 const std::string& error_message) { |
60 // It's okay if the agent didn't exist, it means we never saw an adapter. | 64 // It's okay if the agent didn't exist, it means we never saw an adapter. |
61 if (error_name == bluetooth_agent_manager::kErrorDoesNotExist) | 65 if (error_name == bluetooth_agent_manager::kErrorDoesNotExist) |
62 return; | 66 return; |
63 | 67 |
64 LOG(WARNING) << "Failed to unregister pairing agent: " << error_name << ": " | 68 LOG(WARNING) << "Failed to unregister pairing agent: " << error_name << ": " |
65 << error_message; | 69 << error_message; |
66 } | 70 } |
(...skipping 25 matching lines...) Expand all Loading... |
92 // static | 96 // static |
93 base::WeakPtr<BluetoothAdapter> BluetoothAdapter::CreateAdapter( | 97 base::WeakPtr<BluetoothAdapter> BluetoothAdapter::CreateAdapter( |
94 const InitCallback& init_callback) { | 98 const InitCallback& init_callback) { |
95 return bluez::BluetoothAdapterBlueZ::CreateAdapter(init_callback); | 99 return bluez::BluetoothAdapterBlueZ::CreateAdapter(init_callback); |
96 } | 100 } |
97 | 101 |
98 } // namespace device | 102 } // namespace device |
99 | 103 |
100 namespace bluez { | 104 namespace bluez { |
101 | 105 |
| 106 namespace { |
| 107 |
| 108 void OnServiceErrorCallback( |
| 109 const device::BluetoothGattService::ErrorCallback& error_callback, |
| 110 const std::string& error_name, |
| 111 const std::string& error_message) { |
| 112 VLOG(1) << "Failed to [Un]register service: " << error_name << ", " |
| 113 << error_message; |
| 114 error_callback.Run( |
| 115 BluetoothGattServiceBlueZ::DBusErrorToServiceError(error_name)); |
| 116 } |
| 117 |
| 118 } // namespace |
| 119 |
102 // static | 120 // static |
103 base::WeakPtr<BluetoothAdapter> BluetoothAdapterBlueZ::CreateAdapter( | 121 base::WeakPtr<BluetoothAdapter> BluetoothAdapterBlueZ::CreateAdapter( |
104 const InitCallback& init_callback) { | 122 const InitCallback& init_callback) { |
105 BluetoothAdapterBlueZ* adapter = new BluetoothAdapterBlueZ(init_callback); | 123 BluetoothAdapterBlueZ* adapter = new BluetoothAdapterBlueZ(init_callback); |
106 return adapter->weak_ptr_factory_.GetWeakPtr(); | 124 return adapter->weak_ptr_factory_.GetWeakPtr(); |
107 } | 125 } |
108 | 126 |
109 void BluetoothAdapterBlueZ::Shutdown() { | 127 void BluetoothAdapterBlueZ::Shutdown() { |
110 if (dbus_is_shutdown_) | 128 if (dbus_is_shutdown_) |
111 return; | 129 return; |
(...skipping 927 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1039 } | 1057 } |
1040 delete iter->second; | 1058 delete iter->second; |
1041 released_profiles_.erase(iter); | 1059 released_profiles_.erase(iter); |
1042 } | 1060 } |
1043 | 1061 |
1044 void BluetoothAdapterBlueZ::AddLocalGattService( | 1062 void BluetoothAdapterBlueZ::AddLocalGattService( |
1045 std::unique_ptr<BluetoothLocalGattServiceBlueZ> service) { | 1063 std::unique_ptr<BluetoothLocalGattServiceBlueZ> service) { |
1046 owned_gatt_services_.push_back(std::move(service)); | 1064 owned_gatt_services_.push_back(std::move(service)); |
1047 } | 1065 } |
1048 | 1066 |
| 1067 void BluetoothAdapterBlueZ::RegisterGattService( |
| 1068 BluetoothLocalGattServiceBlueZ* service, |
| 1069 const base::Closure& callback, |
| 1070 const device::BluetoothGattService::ErrorCallback& error_callback) { |
| 1071 if (registered_gatt_services_.count(service->object_path()) > 0) { |
| 1072 LOG(WARNING) << "Re-registering a service that is already registered!"; |
| 1073 error_callback.Run(device::BluetoothGattService::GATT_ERROR_FAILED); |
| 1074 return; |
| 1075 } |
| 1076 |
| 1077 registered_gatt_services_[service->object_path()] = service; |
| 1078 gatt_application_provider_ = BluetoothGattApplicationServiceProvider::Create( |
| 1079 bluez::BluezDBusManager::Get()->GetSystemBus(), |
| 1080 GetApplicationObjectPath(), registered_gatt_services_); |
| 1081 |
| 1082 RegisterApplication(callback, error_callback); |
| 1083 } |
| 1084 |
| 1085 void BluetoothAdapterBlueZ::RegisterApplication( |
| 1086 const base::Closure& callback, |
| 1087 const device::BluetoothGattService::ErrorCallback& error_callback) { |
| 1088 DCHECK(bluez::BluezDBusManager::Get()); |
| 1089 bluez::BluezDBusManager::Get() |
| 1090 ->GetBluetoothGattManagerClient() |
| 1091 ->RegisterApplication( |
| 1092 GetApplicationObjectPath(), BluetoothGattManagerClient::Options(), |
| 1093 callback, base::Bind(&OnServiceErrorCallback, error_callback)); |
| 1094 } |
| 1095 |
| 1096 void BluetoothAdapterBlueZ::UnregisterGattService( |
| 1097 BluetoothLocalGattServiceBlueZ* service, |
| 1098 const base::Closure& callback, |
| 1099 const device::BluetoothGattService::ErrorCallback& error_callback) { |
| 1100 DCHECK(bluez::BluezDBusManager::Get()); |
| 1101 |
| 1102 if (registered_gatt_services_.count(service->object_path()) == 0) { |
| 1103 LOG(WARNING) << "Unregistering a service that isn't registered! path: " |
| 1104 << service->object_path().value(); |
| 1105 error_callback.Run(device::BluetoothGattService::GATT_ERROR_FAILED); |
| 1106 return; |
| 1107 } |
| 1108 |
| 1109 registered_gatt_services_.erase(service->object_path()); |
| 1110 |
| 1111 // If we have no GATT services left, unregister our application. |
| 1112 if (registered_gatt_services_.size() == 0) { |
| 1113 bluez::BluezDBusManager::Get() |
| 1114 ->GetBluetoothGattManagerClient() |
| 1115 ->UnregisterApplication( |
| 1116 GetApplicationObjectPath(), callback, |
| 1117 base::Bind(&OnServiceErrorCallback, error_callback)); |
| 1118 return; |
| 1119 } |
| 1120 |
| 1121 // Otherwise, this is tricky (since at the moment, BlueZ does not support |
| 1122 // adding/removing services individually). We need to update our list of |
| 1123 // services, then unregister our application, then re-register it with the |
| 1124 // updated services. TODO(rkc): Fix this once BlueZ is fixed. |
| 1125 gatt_application_provider_ = BluetoothGattApplicationServiceProvider::Create( |
| 1126 bluez::BluezDBusManager::Get()->GetSystemBus(), object_path_, |
| 1127 registered_gatt_services_); |
| 1128 |
| 1129 // Unregister our current application. If we are successful, make a call to |
| 1130 // register the application again with the current set of services. |
| 1131 bluez::BluezDBusManager::Get() |
| 1132 ->GetBluetoothGattManagerClient() |
| 1133 ->UnregisterApplication( |
| 1134 GetApplicationObjectPath(), |
| 1135 base::Bind(&BluetoothAdapterBlueZ::RegisterApplication, |
| 1136 weak_ptr_factory_.GetWeakPtr(), callback, error_callback), |
| 1137 base::Bind(&OnServiceErrorCallback, error_callback)); |
| 1138 } |
| 1139 |
| 1140 // Returns the object path of the adapter. |
| 1141 dbus::ObjectPath BluetoothAdapterBlueZ::GetApplicationObjectPath() const { |
| 1142 return dbus::ObjectPath(object_path_.value() + kGattApplicationObjectPath); |
| 1143 } |
| 1144 |
1049 void BluetoothAdapterBlueZ::OnRegisterProfile( | 1145 void BluetoothAdapterBlueZ::OnRegisterProfile( |
1050 const BluetoothUUID& uuid, | 1146 const BluetoothUUID& uuid, |
1051 std::unique_ptr<BluetoothAdapterProfileBlueZ> profile) { | 1147 std::unique_ptr<BluetoothAdapterProfileBlueZ> profile) { |
1052 profiles_[uuid] = profile.release(); | 1148 profiles_[uuid] = profile.release(); |
1053 | 1149 |
1054 if (profile_queues_.find(uuid) == profile_queues_.end()) | 1150 if (profile_queues_.find(uuid) == profile_queues_.end()) |
1055 return; | 1151 return; |
1056 | 1152 |
1057 for (auto& it : *profile_queues_[uuid]) | 1153 for (auto& it : *profile_queues_[uuid]) |
1058 it.first.Run(); | 1154 it.first.Run(); |
(...skipping 415 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1474 | 1570 |
1475 // If the queued request resulted in a pending call, then let it | 1571 // If the queued request resulted in a pending call, then let it |
1476 // asynchonously process the remaining queued requests once the pending | 1572 // asynchonously process the remaining queued requests once the pending |
1477 // call returns. | 1573 // call returns. |
1478 if (discovery_request_pending_) | 1574 if (discovery_request_pending_) |
1479 return; | 1575 return; |
1480 } | 1576 } |
1481 } | 1577 } |
1482 | 1578 |
1483 } // namespace bluez | 1579 } // namespace bluez |
OLD | NEW |