OLD | NEW |
| (Empty) |
1 // Copyright (c) 2013 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. | |
4 | |
5 #include "chromeos/dbus/fake_bluetooth_adapter_client.h" | |
6 | |
7 #include "base/location.h" | |
8 #include "base/logging.h" | |
9 #include "base/single_thread_task_runner.h" | |
10 #include "base/thread_task_runner_handle.h" | |
11 #include "base/time/time.h" | |
12 #include "chromeos/dbus/dbus_thread_manager.h" | |
13 #include "chromeos/dbus/fake_bluetooth_device_client.h" | |
14 #include "third_party/cros_system_api/dbus/service_constants.h" | |
15 | |
16 namespace chromeos { | |
17 | |
18 namespace { | |
19 | |
20 // Default interval for delayed tasks. | |
21 const int kSimulationIntervalMs = 750; | |
22 | |
23 } // namespace | |
24 | |
25 const char FakeBluetoothAdapterClient::kAdapterPath[] = | |
26 "/fake/hci0"; | |
27 const char FakeBluetoothAdapterClient::kAdapterName[] = | |
28 "Fake Adapter"; | |
29 const char FakeBluetoothAdapterClient::kAdapterAddress[] = | |
30 "01:1A:2B:1A:2B:03"; | |
31 | |
32 const char FakeBluetoothAdapterClient::kSecondAdapterPath[] = | |
33 "/fake/hci1"; | |
34 const char FakeBluetoothAdapterClient::kSecondAdapterName[] = | |
35 "Second Fake Adapter"; | |
36 const char FakeBluetoothAdapterClient::kSecondAdapterAddress[] = | |
37 "00:DE:51:10:01:00"; | |
38 | |
39 FakeBluetoothAdapterClient::Properties::Properties( | |
40 const PropertyChangedCallback& callback) | |
41 : BluetoothAdapterClient::Properties( | |
42 NULL, | |
43 bluetooth_adapter::kBluetoothAdapterInterface, | |
44 callback) { | |
45 } | |
46 | |
47 FakeBluetoothAdapterClient::Properties::~Properties() { | |
48 } | |
49 | |
50 void FakeBluetoothAdapterClient::Properties::Get( | |
51 dbus::PropertyBase* property, | |
52 dbus::PropertySet::GetCallback callback) { | |
53 VLOG(1) << "Get " << property->name(); | |
54 callback.Run(false); | |
55 } | |
56 | |
57 void FakeBluetoothAdapterClient::Properties::GetAll() { | |
58 VLOG(1) << "GetAll"; | |
59 } | |
60 | |
61 void FakeBluetoothAdapterClient::Properties::Set( | |
62 dbus::PropertyBase *property, | |
63 dbus::PropertySet::SetCallback callback) { | |
64 VLOG(1) << "Set " << property->name(); | |
65 if (property->name() == powered.name() || | |
66 property->name() == alias.name() || | |
67 property->name() == discoverable.name() || | |
68 property->name() == discoverable_timeout.name()) { | |
69 callback.Run(true); | |
70 property->ReplaceValueWithSetValue(); | |
71 } else { | |
72 callback.Run(false); | |
73 } | |
74 } | |
75 | |
76 FakeBluetoothAdapterClient::FakeBluetoothAdapterClient() | |
77 : visible_(true), | |
78 second_visible_(false), | |
79 discovering_count_(0), | |
80 set_discovery_filter_should_fail_(false), | |
81 simulation_interval_ms_(kSimulationIntervalMs) { | |
82 properties_.reset(new Properties(base::Bind( | |
83 &FakeBluetoothAdapterClient::OnPropertyChanged, base::Unretained(this)))); | |
84 | |
85 properties_->address.ReplaceValue(kAdapterAddress); | |
86 properties_->name.ReplaceValue("Fake Adapter (Name)"); | |
87 properties_->alias.ReplaceValue(kAdapterName); | |
88 properties_->pairable.ReplaceValue(true); | |
89 | |
90 second_properties_.reset(new Properties(base::Bind( | |
91 &FakeBluetoothAdapterClient::OnPropertyChanged, base::Unretained(this)))); | |
92 | |
93 second_properties_->address.ReplaceValue(kSecondAdapterAddress); | |
94 second_properties_->name.ReplaceValue("Second Fake Adapter (Name)"); | |
95 second_properties_->alias.ReplaceValue(kSecondAdapterName); | |
96 second_properties_->pairable.ReplaceValue(true); | |
97 } | |
98 | |
99 FakeBluetoothAdapterClient::~FakeBluetoothAdapterClient() { | |
100 } | |
101 | |
102 void FakeBluetoothAdapterClient::Init(dbus::Bus* bus) { | |
103 } | |
104 | |
105 void FakeBluetoothAdapterClient::AddObserver(Observer* observer) { | |
106 observers_.AddObserver(observer); | |
107 } | |
108 | |
109 void FakeBluetoothAdapterClient::RemoveObserver(Observer* observer) { | |
110 observers_.RemoveObserver(observer); | |
111 } | |
112 | |
113 std::vector<dbus::ObjectPath> FakeBluetoothAdapterClient::GetAdapters() { | |
114 std::vector<dbus::ObjectPath> object_paths; | |
115 if (visible_) | |
116 object_paths.push_back(dbus::ObjectPath(kAdapterPath)); | |
117 if (second_visible_) | |
118 object_paths.push_back(dbus::ObjectPath(kSecondAdapterPath)); | |
119 return object_paths; | |
120 } | |
121 | |
122 FakeBluetoothAdapterClient::Properties* | |
123 FakeBluetoothAdapterClient::GetProperties(const dbus::ObjectPath& object_path) { | |
124 if (object_path == dbus::ObjectPath(kAdapterPath)) | |
125 return properties_.get(); | |
126 else if (object_path == dbus::ObjectPath(kSecondAdapterPath)) | |
127 return second_properties_.get(); | |
128 else | |
129 return NULL; | |
130 } | |
131 | |
132 void FakeBluetoothAdapterClient::StartDiscovery( | |
133 const dbus::ObjectPath& object_path, | |
134 const base::Closure& callback, | |
135 const ErrorCallback& error_callback) { | |
136 if (object_path != dbus::ObjectPath(kAdapterPath)) { | |
137 PostDelayedTask(base::Bind(error_callback, kNoResponseError, "")); | |
138 return; | |
139 } | |
140 | |
141 ++discovering_count_; | |
142 VLOG(1) << "StartDiscovery: " << object_path.value() << ", " | |
143 << "count is now " << discovering_count_; | |
144 PostDelayedTask(callback); | |
145 | |
146 if (discovering_count_ == 1) { | |
147 properties_->discovering.ReplaceValue(true); | |
148 | |
149 FakeBluetoothDeviceClient* device_client = | |
150 static_cast<FakeBluetoothDeviceClient*>( | |
151 DBusThreadManager::Get()->GetBluetoothDeviceClient()); | |
152 device_client->BeginDiscoverySimulation(dbus::ObjectPath(kAdapterPath)); | |
153 } | |
154 } | |
155 | |
156 void FakeBluetoothAdapterClient::StopDiscovery( | |
157 const dbus::ObjectPath& object_path, | |
158 const base::Closure& callback, | |
159 const ErrorCallback& error_callback) { | |
160 if (object_path != dbus::ObjectPath(kAdapterPath)) { | |
161 PostDelayedTask(base::Bind(error_callback, kNoResponseError, "")); | |
162 return; | |
163 } | |
164 | |
165 if (!discovering_count_) { | |
166 LOG(WARNING) << "StopDiscovery called when not discovering"; | |
167 PostDelayedTask(base::Bind(error_callback, kNoResponseError, "")); | |
168 return; | |
169 } | |
170 | |
171 --discovering_count_; | |
172 VLOG(1) << "StopDiscovery: " << object_path.value() << ", " | |
173 << "count is now " << discovering_count_; | |
174 PostDelayedTask(callback); | |
175 | |
176 if (discovering_count_ == 0) { | |
177 FakeBluetoothDeviceClient* device_client = | |
178 static_cast<FakeBluetoothDeviceClient*>( | |
179 DBusThreadManager::Get()->GetBluetoothDeviceClient()); | |
180 device_client->EndDiscoverySimulation(dbus::ObjectPath(kAdapterPath)); | |
181 | |
182 if (simulation_interval_ms_ > 100) { | |
183 device_client->BeginIncomingPairingSimulation( | |
184 dbus::ObjectPath(kAdapterPath)); | |
185 } | |
186 | |
187 discovery_filter_.reset(); | |
188 properties_->discovering.ReplaceValue(false); | |
189 } | |
190 } | |
191 | |
192 void FakeBluetoothAdapterClient::RemoveDevice( | |
193 const dbus::ObjectPath& object_path, | |
194 const dbus::ObjectPath& device_path, | |
195 const base::Closure& callback, | |
196 const ErrorCallback& error_callback) { | |
197 if (object_path != dbus::ObjectPath(kAdapterPath)) { | |
198 error_callback.Run(kNoResponseError, ""); | |
199 return; | |
200 } | |
201 | |
202 VLOG(1) << "RemoveDevice: " << object_path.value() | |
203 << " " << device_path.value(); | |
204 callback.Run(); | |
205 | |
206 FakeBluetoothDeviceClient* device_client = | |
207 static_cast<FakeBluetoothDeviceClient*>( | |
208 DBusThreadManager::Get()->GetBluetoothDeviceClient()); | |
209 device_client->RemoveDevice(dbus::ObjectPath(kAdapterPath), device_path); | |
210 } | |
211 | |
212 void FakeBluetoothAdapterClient::MakeSetDiscoveryFilterFail() { | |
213 set_discovery_filter_should_fail_ = true; | |
214 } | |
215 | |
216 void FakeBluetoothAdapterClient::SetDiscoveryFilter( | |
217 const dbus::ObjectPath& object_path, | |
218 const DiscoveryFilter& discovery_filter, | |
219 const base::Closure& callback, | |
220 const ErrorCallback& error_callback) { | |
221 if (object_path != dbus::ObjectPath(kAdapterPath)) { | |
222 PostDelayedTask(base::Bind(error_callback, kNoResponseError, "")); | |
223 return; | |
224 } | |
225 VLOG(1) << "SetDiscoveryFilter: " << object_path.value(); | |
226 | |
227 if (set_discovery_filter_should_fail_) { | |
228 PostDelayedTask(base::Bind(error_callback, kNoResponseError, "")); | |
229 set_discovery_filter_should_fail_ = false; | |
230 return; | |
231 } | |
232 | |
233 discovery_filter_.reset(new DiscoveryFilter()); | |
234 discovery_filter_->CopyFrom(discovery_filter); | |
235 PostDelayedTask(callback); | |
236 } | |
237 | |
238 void FakeBluetoothAdapterClient::SetSimulationIntervalMs(int interval_ms) { | |
239 simulation_interval_ms_ = interval_ms; | |
240 } | |
241 | |
242 BluetoothAdapterClient::DiscoveryFilter* | |
243 FakeBluetoothAdapterClient::GetDiscoveryFilter() { | |
244 return discovery_filter_.get(); | |
245 } | |
246 | |
247 void FakeBluetoothAdapterClient::SetVisible( | |
248 bool visible) { | |
249 if (visible && !visible_) { | |
250 // Adapter becoming visible | |
251 visible_ = visible; | |
252 | |
253 FOR_EACH_OBSERVER(BluetoothAdapterClient::Observer, observers_, | |
254 AdapterAdded(dbus::ObjectPath(kAdapterPath))); | |
255 | |
256 } else if (visible_ && !visible) { | |
257 // Adapter becoming invisible | |
258 visible_ = visible; | |
259 | |
260 FOR_EACH_OBSERVER(BluetoothAdapterClient::Observer, observers_, | |
261 AdapterRemoved(dbus::ObjectPath(kAdapterPath))); | |
262 } | |
263 } | |
264 | |
265 void FakeBluetoothAdapterClient::SetSecondVisible( | |
266 bool visible) { | |
267 if (visible && !second_visible_) { | |
268 // Second adapter becoming visible | |
269 second_visible_ = visible; | |
270 | |
271 FOR_EACH_OBSERVER(BluetoothAdapterClient::Observer, observers_, | |
272 AdapterAdded(dbus::ObjectPath(kSecondAdapterPath))); | |
273 | |
274 } else if (second_visible_ && !visible) { | |
275 // Second adapter becoming invisible | |
276 second_visible_ = visible; | |
277 | |
278 FOR_EACH_OBSERVER(BluetoothAdapterClient::Observer, observers_, | |
279 AdapterRemoved(dbus::ObjectPath(kSecondAdapterPath))); | |
280 } | |
281 } | |
282 | |
283 void FakeBluetoothAdapterClient::OnPropertyChanged( | |
284 const std::string& property_name) { | |
285 if (property_name == properties_->powered.name() && | |
286 !properties_->powered.value()) { | |
287 VLOG(1) << "Adapter powered off"; | |
288 | |
289 if (discovering_count_) { | |
290 discovering_count_ = 0; | |
291 properties_->discovering.ReplaceValue(false); | |
292 } | |
293 } | |
294 | |
295 FOR_EACH_OBSERVER(BluetoothAdapterClient::Observer, observers_, | |
296 AdapterPropertyChanged(dbus::ObjectPath(kAdapterPath), | |
297 property_name)); | |
298 } | |
299 | |
300 void FakeBluetoothAdapterClient::PostDelayedTask( | |
301 const base::Closure& callback) { | |
302 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( | |
303 FROM_HERE, callback, | |
304 base::TimeDelta::FromMilliseconds(simulation_interval_ms_)); | |
305 } | |
306 | |
307 } // namespace chromeos | |
OLD | NEW |