add flags for future skia api change
[chromium-blink-merge.git] / device / bluetooth / bluetooth_adapter_win.cc
blob158defc8d1c82f07789d555746782b0fb277d6ab
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
3 // found in the LICENSE file.
5 #include "device/bluetooth/bluetooth_adapter_win.h"
7 #include <string>
8 #include <utility>
10 #include "base/location.h"
11 #include "base/logging.h"
12 #include "base/sequenced_task_runner.h"
13 #include "base/single_thread_task_runner.h"
14 #include "base/stl_util.h"
15 #include "base/thread_task_runner_handle.h"
16 #include "device/bluetooth/bluetooth_device_win.h"
17 #include "device/bluetooth/bluetooth_socket_thread.h"
18 #include "device/bluetooth/bluetooth_socket_win.h"
19 #include "device/bluetooth/bluetooth_task_manager_win.h"
20 #include "device/bluetooth/bluetooth_uuid.h"
22 namespace device {
24 // static
25 base::WeakPtr<BluetoothAdapter> BluetoothAdapter::CreateAdapter(
26 const InitCallback& init_callback) {
27 return BluetoothAdapterWin::CreateAdapter(init_callback);
30 // static
31 base::WeakPtr<BluetoothAdapter> BluetoothAdapterWin::CreateAdapter(
32 const InitCallback& init_callback) {
33 BluetoothAdapterWin* adapter = new BluetoothAdapterWin(init_callback);
34 adapter->Init();
35 return adapter->weak_ptr_factory_.GetWeakPtr();
38 BluetoothAdapterWin::BluetoothAdapterWin(const InitCallback& init_callback)
39 : BluetoothAdapter(),
40 init_callback_(init_callback),
41 initialized_(false),
42 powered_(false),
43 discovery_status_(NOT_DISCOVERING),
44 num_discovery_listeners_(0),
45 weak_ptr_factory_(this) {
48 BluetoothAdapterWin::~BluetoothAdapterWin() {
49 if (task_manager_.get()) {
50 task_manager_->RemoveObserver(this);
51 task_manager_->Shutdown();
55 std::string BluetoothAdapterWin::GetAddress() const {
56 return address_;
59 std::string BluetoothAdapterWin::GetName() const {
60 return name_;
63 void BluetoothAdapterWin::SetName(const std::string& name,
64 const base::Closure& callback,
65 const ErrorCallback& error_callback) {
66 NOTIMPLEMENTED();
69 // TODO(youngki): Return true when |task_manager_| initializes the adapter
70 // state.
71 bool BluetoothAdapterWin::IsInitialized() const {
72 return initialized_;
75 bool BluetoothAdapterWin::IsPresent() const {
76 return !address_.empty();
79 bool BluetoothAdapterWin::IsPowered() const {
80 return powered_;
83 void BluetoothAdapterWin::SetPowered(
84 bool powered,
85 const base::Closure& callback,
86 const ErrorCallback& error_callback) {
87 task_manager_->PostSetPoweredBluetoothTask(powered, callback, error_callback);
90 bool BluetoothAdapterWin::IsDiscoverable() const {
91 NOTIMPLEMENTED();
92 return false;
95 void BluetoothAdapterWin::SetDiscoverable(
96 bool discoverable,
97 const base::Closure& callback,
98 const ErrorCallback& error_callback) {
99 NOTIMPLEMENTED();
102 bool BluetoothAdapterWin::IsDiscovering() const {
103 return discovery_status_ == DISCOVERING ||
104 discovery_status_ == DISCOVERY_STOPPING;
107 void BluetoothAdapterWin::DiscoveryStarted(bool success) {
108 discovery_status_ = success ? DISCOVERING : NOT_DISCOVERING;
109 for (std::vector<std::pair<base::Closure, ErrorCallback> >::const_iterator
110 iter = on_start_discovery_callbacks_.begin();
111 iter != on_start_discovery_callbacks_.end();
112 ++iter) {
113 if (success)
114 ui_task_runner_->PostTask(FROM_HERE, iter->first);
115 else
116 ui_task_runner_->PostTask(FROM_HERE, iter->second);
118 num_discovery_listeners_ = on_start_discovery_callbacks_.size();
119 on_start_discovery_callbacks_.clear();
121 if (success) {
122 FOR_EACH_OBSERVER(BluetoothAdapter::Observer, observers_,
123 AdapterDiscoveringChanged(this, true));
125 // If there are stop discovery requests, post the stop discovery again.
126 MaybePostStopDiscoveryTask();
127 } else if (!on_stop_discovery_callbacks_.empty()) {
128 // If there are stop discovery requests but start discovery has failed,
129 // notify that stop discovery has been complete.
130 DiscoveryStopped();
134 void BluetoothAdapterWin::DiscoveryStopped() {
135 discovered_devices_.clear();
136 bool was_discovering = IsDiscovering();
137 discovery_status_ = NOT_DISCOVERING;
138 for (std::vector<base::Closure>::const_iterator iter =
139 on_stop_discovery_callbacks_.begin();
140 iter != on_stop_discovery_callbacks_.end();
141 ++iter) {
142 ui_task_runner_->PostTask(FROM_HERE, *iter);
144 num_discovery_listeners_ = 0;
145 on_stop_discovery_callbacks_.clear();
146 if (was_discovering)
147 FOR_EACH_OBSERVER(BluetoothAdapter::Observer, observers_,
148 AdapterDiscoveringChanged(this, false));
150 // If there are start discovery requests, post the start discovery again.
151 MaybePostStartDiscoveryTask();
154 void BluetoothAdapterWin::CreateRfcommService(
155 const BluetoothUUID& uuid,
156 const ServiceOptions& options,
157 const CreateServiceCallback& callback,
158 const CreateServiceErrorCallback& error_callback) {
159 scoped_refptr<BluetoothSocketWin> socket =
160 BluetoothSocketWin::CreateBluetoothSocket(
161 ui_task_runner_, socket_thread_);
162 socket->Listen(this, uuid, options,
163 base::Bind(callback, socket),
164 error_callback);
167 void BluetoothAdapterWin::CreateL2capService(
168 const BluetoothUUID& uuid,
169 const ServiceOptions& options,
170 const CreateServiceCallback& callback,
171 const CreateServiceErrorCallback& error_callback) {
172 // TODO(keybuk): implement.
173 NOTIMPLEMENTED();
176 void BluetoothAdapterWin::RegisterAudioSink(
177 const BluetoothAudioSink::Options& options,
178 const AcquiredCallback& callback,
179 const BluetoothAudioSink::ErrorCallback& error_callback) {
180 NOTIMPLEMENTED();
181 error_callback.Run(BluetoothAudioSink::ERROR_UNSUPPORTED_PLATFORM);
184 void BluetoothAdapterWin::RegisterAdvertisement(
185 scoped_ptr<BluetoothAdvertisement::Data> advertisement_data,
186 const CreateAdvertisementCallback& callback,
187 const CreateAdvertisementErrorCallback& error_callback) {
188 NOTIMPLEMENTED();
189 error_callback.Run(BluetoothAdvertisement::ERROR_UNSUPPORTED_PLATFORM);
192 void BluetoothAdapterWin::RemovePairingDelegateInternal(
193 BluetoothDevice::PairingDelegate* pairing_delegate) {
196 void BluetoothAdapterWin::AdapterStateChanged(
197 const BluetoothTaskManagerWin::AdapterState& state) {
198 DCHECK(thread_checker_.CalledOnValidThread());
199 name_ = state.name;
200 bool was_present = IsPresent();
201 bool is_present = !state.address.empty();
202 address_ = BluetoothDevice::CanonicalizeAddress(state.address);
203 if (was_present != is_present) {
204 FOR_EACH_OBSERVER(BluetoothAdapter::Observer, observers_,
205 AdapterPresentChanged(this, is_present));
207 if (powered_ != state.powered) {
208 powered_ = state.powered;
209 FOR_EACH_OBSERVER(BluetoothAdapter::Observer, observers_,
210 AdapterPoweredChanged(this, powered_));
212 if (!initialized_) {
213 initialized_ = true;
214 init_callback_.Run();
218 void BluetoothAdapterWin::DevicesPolled(
219 const ScopedVector<BluetoothTaskManagerWin::DeviceState>& devices) {
220 DCHECK(thread_checker_.CalledOnValidThread());
222 // We are receiving a new list of all devices known to the system. Merge this
223 // new list with the list we know of (|devices_|) and raise corresponding
224 // DeviceAdded, DeviceRemoved and DeviceChanged events.
226 typedef std::set<std::string> DeviceAddressSet;
227 DeviceAddressSet known_devices;
228 for (DevicesMap::const_iterator iter = devices_.begin();
229 iter != devices_.end();
230 ++iter) {
231 known_devices.insert((*iter).first);
234 DeviceAddressSet new_devices;
235 for (ScopedVector<BluetoothTaskManagerWin::DeviceState>::const_iterator iter =
236 devices.begin();
237 iter != devices.end();
238 ++iter) {
239 new_devices.insert((*iter)->address);
242 // Process device removal first
243 DeviceAddressSet removed_devices =
244 base::STLSetDifference<DeviceAddressSet>(known_devices, new_devices);
245 for (DeviceAddressSet::const_iterator iter = removed_devices.begin();
246 iter != removed_devices.end();
247 ++iter) {
248 BluetoothDevice* device_win = devices_[(*iter)];
249 devices_.erase(*iter);
250 FOR_EACH_OBSERVER(BluetoothAdapter::Observer,
251 observers_,
252 DeviceRemoved(this, device_win));
253 delete device_win;
256 // Process added and (maybe) changed devices in one pass
257 DeviceAddressSet added_devices =
258 base::STLSetDifference<DeviceAddressSet>(new_devices, known_devices);
259 DeviceAddressSet changed_devices =
260 base::STLSetIntersection<DeviceAddressSet>(known_devices, new_devices);
261 for (ScopedVector<BluetoothTaskManagerWin::DeviceState>::const_iterator iter =
262 devices.begin();
263 iter != devices.end();
264 ++iter) {
265 BluetoothTaskManagerWin::DeviceState* device_state = (*iter);
266 if (added_devices.find(device_state->address) != added_devices.end()) {
267 BluetoothDeviceWin* device_win =
268 new BluetoothDeviceWin(*device_state,
269 ui_task_runner_,
270 socket_thread_,
271 NULL,
272 net::NetLog::Source());
273 devices_[device_state->address] = device_win;
274 FOR_EACH_OBSERVER(BluetoothAdapter::Observer,
275 observers_,
276 DeviceAdded(this, device_win));
277 } else if (changed_devices.find(device_state->address) !=
278 changed_devices.end()) {
279 BluetoothDeviceWin* device_win =
280 static_cast<BluetoothDeviceWin*>(devices_[device_state->address]);
281 if (!device_win->IsEqual(*device_state)) {
282 device_win->Update(*device_state);
283 FOR_EACH_OBSERVER(BluetoothAdapter::Observer,
284 observers_,
285 DeviceChanged(this, device_win));
291 // If the method is called when |discovery_status_| is DISCOVERY_STOPPING,
292 // starting again is handled by BluetoothAdapterWin::DiscoveryStopped().
293 void BluetoothAdapterWin::AddDiscoverySession(
294 BluetoothDiscoveryFilter* discovery_filter,
295 const base::Closure& callback,
296 const ErrorCallback& error_callback) {
297 if (discovery_status_ == DISCOVERING) {
298 num_discovery_listeners_++;
299 callback.Run();
300 return;
302 on_start_discovery_callbacks_.push_back(
303 std::make_pair(callback, error_callback));
304 MaybePostStartDiscoveryTask();
307 void BluetoothAdapterWin::RemoveDiscoverySession(
308 BluetoothDiscoveryFilter* discovery_filter,
309 const base::Closure& callback,
310 const ErrorCallback& error_callback) {
311 if (discovery_status_ == NOT_DISCOVERING) {
312 error_callback.Run();
313 return;
315 on_stop_discovery_callbacks_.push_back(callback);
316 MaybePostStopDiscoveryTask();
319 void BluetoothAdapterWin::SetDiscoveryFilter(
320 scoped_ptr<BluetoothDiscoveryFilter> discovery_filter,
321 const base::Closure& callback,
322 const ErrorCallback& error_callback) {
323 NOTIMPLEMENTED();
324 error_callback.Run();
327 void BluetoothAdapterWin::Init() {
328 ui_task_runner_ = base::ThreadTaskRunnerHandle::Get();
329 socket_thread_ = BluetoothSocketThread::Get();
330 task_manager_ =
331 new BluetoothTaskManagerWin(ui_task_runner_);
332 task_manager_->AddObserver(this);
333 task_manager_->Initialize();
336 void BluetoothAdapterWin::InitForTest(
337 scoped_refptr<base::SequencedTaskRunner> ui_task_runner,
338 scoped_refptr<base::SequencedTaskRunner> bluetooth_task_runner) {
339 ui_task_runner_ = ui_task_runner;
340 task_manager_ =
341 new BluetoothTaskManagerWin(ui_task_runner_);
342 task_manager_->AddObserver(this);
343 task_manager_->InitializeWithBluetoothTaskRunner(bluetooth_task_runner);
346 void BluetoothAdapterWin::MaybePostStartDiscoveryTask() {
347 if (discovery_status_ == NOT_DISCOVERING &&
348 !on_start_discovery_callbacks_.empty()) {
349 discovery_status_ = DISCOVERY_STARTING;
350 task_manager_->PostStartDiscoveryTask();
354 void BluetoothAdapterWin::MaybePostStopDiscoveryTask() {
355 if (discovery_status_ != DISCOVERING)
356 return;
358 if (on_stop_discovery_callbacks_.size() < num_discovery_listeners_) {
359 for (std::vector<base::Closure>::const_iterator iter =
360 on_stop_discovery_callbacks_.begin();
361 iter != on_stop_discovery_callbacks_.end();
362 ++iter) {
363 ui_task_runner_->PostTask(FROM_HERE, *iter);
365 num_discovery_listeners_ -= on_stop_discovery_callbacks_.size();
366 on_stop_discovery_callbacks_.clear();
367 return;
370 discovery_status_ = DISCOVERY_STOPPING;
371 task_manager_->PostStopDiscoveryTask();
374 } // namespace device