1 // Copyright 2014 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.
6 #include "base/memory/ref_counted.h"
7 #include "device/bluetooth/bluetooth_adapter.h"
8 #include "device/bluetooth/bluetooth_device.h"
9 #include "device/bluetooth/bluetooth_discovery_session.h"
10 #include "testing/gtest/include/gtest/gtest.h"
12 using device::BluetoothAdapter
;
13 using device::BluetoothDevice
;
17 class TestBluetoothAdapter
: public BluetoothAdapter
{
19 TestBluetoothAdapter() {
22 void AddObserver(BluetoothAdapter::Observer
* observer
) override
{}
24 void RemoveObserver(BluetoothAdapter::Observer
* observer
) override
{}
26 std::string
GetAddress() const override
{ return ""; }
28 std::string
GetName() const override
{ return ""; }
30 void SetName(const std::string
& name
,
31 const base::Closure
& callback
,
32 const ErrorCallback
& error_callback
) override
{}
34 bool IsInitialized() const override
{ return false; }
36 bool IsPresent() const override
{ return false; }
38 bool IsPowered() const override
{ return false; }
40 void SetPowered(bool powered
,
41 const base::Closure
& callback
,
42 const ErrorCallback
& error_callback
) override
{}
44 bool IsDiscoverable() const override
{ return false; }
46 void SetDiscoverable(bool discoverable
,
47 const base::Closure
& callback
,
48 const ErrorCallback
& error_callback
) override
{}
50 bool IsDiscovering() const override
{ return false; }
52 void DeleteOnCorrectThread() const override
{ delete this; }
54 void StartDiscoverySessionWithFilter(
55 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
,
56 const DiscoverySessionCallback
& callback
,
57 const ErrorCallback
& error_callback
) override
{
58 OnStartDiscoverySession(discovery_filter
.Pass(), callback
);
61 void StartDiscoverySession(const DiscoverySessionCallback
& callback
,
62 const ErrorCallback
& error_callback
) override
{}
63 void CreateRfcommService(
64 const BluetoothUUID
& uuid
,
65 const ServiceOptions
& options
,
66 const CreateServiceCallback
& callback
,
67 const CreateServiceErrorCallback
& error_callback
) override
{}
69 void CreateL2capService(
70 const BluetoothUUID
& uuid
,
71 const ServiceOptions
& options
,
72 const CreateServiceCallback
& callback
,
73 const CreateServiceErrorCallback
& error_callback
) override
{}
75 void RegisterAudioSink(
76 const BluetoothAudioSink::Options
& options
,
77 const AcquiredCallback
& callback
,
78 const BluetoothAudioSink::ErrorCallback
& error_callback
) override
{}
80 void TestErrorCallback() {}
82 ScopedVector
<BluetoothDiscoverySession
> discovery_sessions_
;
84 void TestOnStartDiscoverySession(
85 scoped_ptr
<device::BluetoothDiscoverySession
> discovery_session
) {
86 discovery_sessions_
.push_back(discovery_session
.Pass());
89 void CleanupSessions() { discovery_sessions_
.clear(); }
91 void InjectFilteredSession(
92 scoped_ptr
<device::BluetoothDiscoveryFilter
> discovery_filter
) {
93 StartDiscoverySessionWithFilter(
94 discovery_filter
.Pass(),
95 base::Bind(&TestBluetoothAdapter::TestOnStartDiscoverySession
,
96 base::Unretained(this)),
97 base::Bind(&TestBluetoothAdapter::TestErrorCallback
,
98 base::Unretained(this)));
102 ~TestBluetoothAdapter() override
{}
104 void AddDiscoverySession(BluetoothDiscoveryFilter
* discovery_filter
,
105 const base::Closure
& callback
,
106 const ErrorCallback
& error_callback
) override
{}
108 void RemoveDiscoverySession(BluetoothDiscoveryFilter
* discovery_filter
,
109 const base::Closure
& callback
,
110 const ErrorCallback
& error_callback
) override
{}
112 void SetDiscoveryFilter(scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
,
113 const base::Closure
& callback
,
114 const ErrorCallback
& error_callback
) override
{}
116 void RemovePairingDelegateInternal(
117 BluetoothDevice::PairingDelegate
* pairing_delegate
) override
{}
120 class TestPairingDelegate
: public BluetoothDevice::PairingDelegate
{
122 void RequestPinCode(BluetoothDevice
* device
) override
{}
123 void RequestPasskey(BluetoothDevice
* device
) override
{}
124 void DisplayPinCode(BluetoothDevice
* device
,
125 const std::string
& pincode
) override
{}
126 void DisplayPasskey(BluetoothDevice
* device
, uint32 passkey
) override
{}
127 void KeysEntered(BluetoothDevice
* device
, uint32 entered
) override
{}
128 void ConfirmPasskey(BluetoothDevice
* device
, uint32 passkey
) override
{}
129 void AuthorizePairing(BluetoothDevice
* device
) override
{}
133 TEST(BluetoothAdapterTest
, NoDefaultPairingDelegate
) {
134 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
136 // Verify that when there is no registered pairing delegate, NULL is returned.
137 EXPECT_TRUE(adapter
->DefaultPairingDelegate() == NULL
);
140 TEST(BluetoothAdapterTest
, OneDefaultPairingDelegate
) {
141 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
143 // Verify that when there is one registered pairing delegate, it is returned.
144 TestPairingDelegate delegate
;
146 adapter
->AddPairingDelegate(&delegate
,
147 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
149 EXPECT_EQ(&delegate
, adapter
->DefaultPairingDelegate());
152 TEST(BluetoothAdapterTest
, SamePriorityDelegates
) {
153 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
155 // Verify that when there are two registered pairing delegates of the same
156 // priority, the first one registered is returned.
157 TestPairingDelegate delegate1
, delegate2
;
159 adapter
->AddPairingDelegate(&delegate1
,
160 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
161 adapter
->AddPairingDelegate(&delegate2
,
162 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
164 EXPECT_EQ(&delegate1
, adapter
->DefaultPairingDelegate());
166 // After unregistering the first, the second can be returned.
167 adapter
->RemovePairingDelegate(&delegate1
);
169 EXPECT_EQ(&delegate2
, adapter
->DefaultPairingDelegate());
172 TEST(BluetoothAdapterTest
, HighestPriorityDelegate
) {
173 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
175 // Verify that when there are two registered pairing delegates, the one with
176 // the highest priority is returned.
177 TestPairingDelegate delegate1
, delegate2
;
179 adapter
->AddPairingDelegate(&delegate1
,
180 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
181 adapter
->AddPairingDelegate(&delegate2
,
182 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_HIGH
);
184 EXPECT_EQ(&delegate2
, adapter
->DefaultPairingDelegate());
187 TEST(BluetoothAdapterTest
, UnregisterDelegate
) {
188 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
190 // Verify that after unregistering a delegate, NULL is returned.
191 TestPairingDelegate delegate
;
193 adapter
->AddPairingDelegate(&delegate
,
194 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
195 adapter
->RemovePairingDelegate(&delegate
);
197 EXPECT_TRUE(adapter
->DefaultPairingDelegate() == NULL
);
200 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterEmpty
) {
201 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
202 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
;
204 discovery_filter
= adapter
->GetMergedDiscoveryFilter();
205 EXPECT_TRUE(discovery_filter
.get() == nullptr);
207 discovery_filter
= adapter
->GetMergedDiscoveryFilterMasked(nullptr);
208 EXPECT_TRUE(discovery_filter
.get() == nullptr);
211 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterRegular
) {
212 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
213 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
;
215 // make sure adapter have one session wihout filtering.
216 adapter
->InjectFilteredSession(discovery_filter
.Pass());
218 // having one reglar session should result in no filter
219 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
=
220 adapter
->GetMergedDiscoveryFilter();
221 EXPECT_TRUE(resulting_filter
.get() == nullptr);
223 // omiting no filter when having one reglar session should result in no filter
224 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(nullptr);
225 EXPECT_TRUE(resulting_filter
.get() == nullptr);
227 adapter
->CleanupSessions();
230 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterRssi
) {
231 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
232 int16_t resulting_rssi
;
233 uint16_t resulting_pathloss
;
234 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
;
236 BluetoothDiscoveryFilter
* df
= new BluetoothDiscoveryFilter(
237 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
239 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter(df
);
241 BluetoothDiscoveryFilter
* df2
= new BluetoothDiscoveryFilter(
242 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
244 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter2(df2
);
246 // make sure adapter have one session wihout filtering.
247 adapter
->InjectFilteredSession(discovery_filter
.Pass());
249 // DO_NOTHING should have no impact
250 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
251 resulting_filter
->GetRSSI(&resulting_rssi
);
252 EXPECT_EQ(-30, resulting_rssi
);
254 // should not use df2 at all, as it's not associated with adapter yet
255 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df2
);
256 resulting_filter
->GetRSSI(&resulting_rssi
);
257 EXPECT_EQ(-30, resulting_rssi
);
259 adapter
->InjectFilteredSession(discovery_filter2
.Pass());
261 // result of merging two rssi values should be lower one
262 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
263 resulting_filter
->GetRSSI(&resulting_rssi
);
264 EXPECT_EQ(-65, resulting_rssi
);
266 // ommit bigger value, result should stay same
267 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df
);
268 resulting_filter
->GetRSSI(&resulting_rssi
);
269 EXPECT_EQ(-65, resulting_rssi
);
271 // ommit lower value, result should change
272 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df2
);
273 resulting_filter
->GetRSSI(&resulting_rssi
);
274 EXPECT_EQ(-30, resulting_rssi
);
276 BluetoothDiscoveryFilter
* df3
= new BluetoothDiscoveryFilter(
277 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
278 df3
->SetPathloss(60);
279 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter3(df3
);
281 // when rssi and pathloss are merged, both should be cleared, becuase there is
282 // no way to tell which filter will be more generic
283 adapter
->InjectFilteredSession(discovery_filter3
.Pass());
284 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
285 EXPECT_FALSE(resulting_filter
->GetRSSI(&resulting_rssi
));
286 EXPECT_FALSE(resulting_filter
->GetPathloss(&resulting_pathloss
));
288 adapter
->CleanupSessions();
291 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterTransport
) {
292 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
293 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
;
295 BluetoothDiscoveryFilter
* df
= new BluetoothDiscoveryFilter(
296 BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
);
297 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter(df
);
299 BluetoothDiscoveryFilter
* df2
= new BluetoothDiscoveryFilter(
300 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
301 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter2(df2
);
303 adapter
->InjectFilteredSession(discovery_filter
.Pass());
305 // Just one filter, make sure transport was properly rewritten
306 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
307 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
,
308 resulting_filter
->GetTransport());
310 adapter
->InjectFilteredSession(discovery_filter2
.Pass());
312 // Two filters, should have OR of both transport's
313 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
314 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
,
315 resulting_filter
->GetTransport());
317 // When 1st filter is masked, 2nd filter transport should be returned.
318 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df
);
319 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
,
320 resulting_filter
->GetTransport());
322 // When 2nd filter is masked, 1st filter transport should be returned.
323 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df2
);
324 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
,
325 resulting_filter
->GetTransport());
327 BluetoothDiscoveryFilter
* df3
= new BluetoothDiscoveryFilter(
328 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
329 df3
->CopyFrom(BluetoothDiscoveryFilter(
330 BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
));
331 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter3(df3
);
333 // Merging empty filter in should result in empty filter
334 adapter
->InjectFilteredSession(discovery_filter3
.Pass());
335 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
336 EXPECT_TRUE(resulting_filter
->IsDefault());
338 adapter
->CleanupSessions();
341 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterAllFields
) {
342 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
343 int16_t resulting_rssi
;
344 std::set
<device::BluetoothUUID
> resulting_uuids
;
346 BluetoothDiscoveryFilter
* df
= new BluetoothDiscoveryFilter(
347 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
349 df
->AddUUID(device::BluetoothUUID("1000"));
350 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter(df
);
352 BluetoothDiscoveryFilter
* df2
= new BluetoothDiscoveryFilter(
353 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
355 df2
->SetTransport(BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
356 df2
->AddUUID(device::BluetoothUUID("1020"));
357 df2
->AddUUID(device::BluetoothUUID("1001"));
358 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter2(df2
);
360 BluetoothDiscoveryFilter
* df3
= new BluetoothDiscoveryFilter(
361 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
363 df3
->SetTransport(BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
);
364 df3
->AddUUID(device::BluetoothUUID("1020"));
365 df3
->AddUUID(device::BluetoothUUID("1003"));
366 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter3(df3
);
368 // make sure adapter have one session wihout filtering.
369 adapter
->InjectFilteredSession(discovery_filter
.Pass());
370 adapter
->InjectFilteredSession(discovery_filter2
.Pass());
371 adapter
->InjectFilteredSession(discovery_filter3
.Pass());
373 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
=
374 adapter
->GetMergedDiscoveryFilter();
375 resulting_filter
->GetRSSI(&resulting_rssi
);
376 resulting_filter
->GetUUIDs(resulting_uuids
);
377 EXPECT_TRUE(resulting_filter
->GetTransport());
378 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
,
379 resulting_filter
->GetTransport());
380 EXPECT_EQ(-85, resulting_rssi
);
381 EXPECT_EQ(4UL, resulting_uuids
.size());
382 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1000")) !=
383 resulting_uuids
.end());
384 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1001")) !=
385 resulting_uuids
.end());
386 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1003")) !=
387 resulting_uuids
.end());
388 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1020")) !=
389 resulting_uuids
.end());
391 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df
);
392 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
,
393 resulting_filter
->GetTransport());
395 adapter
->CleanupSessions();
398 } // namespace device