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 std::string
GetAddress() const override
{ return ""; }
24 std::string
GetName() const override
{ return ""; }
26 void SetName(const std::string
& name
,
27 const base::Closure
& callback
,
28 const ErrorCallback
& error_callback
) override
{}
30 bool IsInitialized() const override
{ return false; }
32 bool IsPresent() const override
{ return false; }
34 bool IsPowered() const override
{ return false; }
36 void SetPowered(bool powered
,
37 const base::Closure
& callback
,
38 const ErrorCallback
& error_callback
) override
{}
40 bool IsDiscoverable() const override
{ return false; }
42 void SetDiscoverable(bool discoverable
,
43 const base::Closure
& callback
,
44 const ErrorCallback
& error_callback
) override
{}
46 bool IsDiscovering() const override
{ return false; }
48 void StartDiscoverySessionWithFilter(
49 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
,
50 const DiscoverySessionCallback
& callback
,
51 const ErrorCallback
& error_callback
) override
{
52 OnStartDiscoverySession(discovery_filter
.Pass(), callback
);
55 void StartDiscoverySession(const DiscoverySessionCallback
& callback
,
56 const ErrorCallback
& error_callback
) override
{}
57 void CreateRfcommService(
58 const BluetoothUUID
& uuid
,
59 const ServiceOptions
& options
,
60 const CreateServiceCallback
& callback
,
61 const CreateServiceErrorCallback
& error_callback
) override
{}
63 void CreateL2capService(
64 const BluetoothUUID
& uuid
,
65 const ServiceOptions
& options
,
66 const CreateServiceCallback
& callback
,
67 const CreateServiceErrorCallback
& error_callback
) override
{}
69 void RegisterAudioSink(
70 const BluetoothAudioSink::Options
& options
,
71 const AcquiredCallback
& callback
,
72 const BluetoothAudioSink::ErrorCallback
& error_callback
) override
{}
74 void RegisterAdvertisement(
75 scoped_ptr
<BluetoothAdvertisement::Data
> advertisement_data
,
76 const CreateAdvertisementCallback
& callback
,
77 const CreateAdvertisementErrorCallback
& error_callback
) override
{}
79 void TestErrorCallback() {}
81 ScopedVector
<BluetoothDiscoverySession
> discovery_sessions_
;
83 void TestOnStartDiscoverySession(
84 scoped_ptr
<device::BluetoothDiscoverySession
> discovery_session
) {
85 discovery_sessions_
.push_back(discovery_session
.Pass());
88 void CleanupSessions() { discovery_sessions_
.clear(); }
90 void InjectFilteredSession(
91 scoped_ptr
<device::BluetoothDiscoveryFilter
> discovery_filter
) {
92 StartDiscoverySessionWithFilter(
93 discovery_filter
.Pass(),
94 base::Bind(&TestBluetoothAdapter::TestOnStartDiscoverySession
,
95 base::Unretained(this)),
96 base::Bind(&TestBluetoothAdapter::TestErrorCallback
,
97 base::Unretained(this)));
101 ~TestBluetoothAdapter() override
{}
103 void AddDiscoverySession(BluetoothDiscoveryFilter
* discovery_filter
,
104 const base::Closure
& callback
,
105 const ErrorCallback
& error_callback
) override
{}
107 void RemoveDiscoverySession(BluetoothDiscoveryFilter
* discovery_filter
,
108 const base::Closure
& callback
,
109 const ErrorCallback
& error_callback
) override
{}
111 void SetDiscoveryFilter(scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
,
112 const base::Closure
& callback
,
113 const ErrorCallback
& error_callback
) override
{}
115 void RemovePairingDelegateInternal(
116 BluetoothDevice::PairingDelegate
* pairing_delegate
) override
{}
119 class TestPairingDelegate
: public BluetoothDevice::PairingDelegate
{
121 void RequestPinCode(BluetoothDevice
* device
) override
{}
122 void RequestPasskey(BluetoothDevice
* device
) override
{}
123 void DisplayPinCode(BluetoothDevice
* device
,
124 const std::string
& pincode
) override
{}
125 void DisplayPasskey(BluetoothDevice
* device
, uint32 passkey
) override
{}
126 void KeysEntered(BluetoothDevice
* device
, uint32 entered
) override
{}
127 void ConfirmPasskey(BluetoothDevice
* device
, uint32 passkey
) override
{}
128 void AuthorizePairing(BluetoothDevice
* device
) override
{}
132 TEST(BluetoothAdapterTest
, NoDefaultPairingDelegate
) {
133 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
135 // Verify that when there is no registered pairing delegate, NULL is returned.
136 EXPECT_TRUE(adapter
->DefaultPairingDelegate() == NULL
);
139 TEST(BluetoothAdapterTest
, OneDefaultPairingDelegate
) {
140 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
142 // Verify that when there is one registered pairing delegate, it is returned.
143 TestPairingDelegate delegate
;
145 adapter
->AddPairingDelegate(&delegate
,
146 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
148 EXPECT_EQ(&delegate
, adapter
->DefaultPairingDelegate());
151 TEST(BluetoothAdapterTest
, SamePriorityDelegates
) {
152 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
154 // Verify that when there are two registered pairing delegates of the same
155 // priority, the first one registered is returned.
156 TestPairingDelegate delegate1
, delegate2
;
158 adapter
->AddPairingDelegate(&delegate1
,
159 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
160 adapter
->AddPairingDelegate(&delegate2
,
161 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
163 EXPECT_EQ(&delegate1
, adapter
->DefaultPairingDelegate());
165 // After unregistering the first, the second can be returned.
166 adapter
->RemovePairingDelegate(&delegate1
);
168 EXPECT_EQ(&delegate2
, adapter
->DefaultPairingDelegate());
171 TEST(BluetoothAdapterTest
, HighestPriorityDelegate
) {
172 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
174 // Verify that when there are two registered pairing delegates, the one with
175 // the highest priority is returned.
176 TestPairingDelegate delegate1
, delegate2
;
178 adapter
->AddPairingDelegate(&delegate1
,
179 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
180 adapter
->AddPairingDelegate(&delegate2
,
181 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_HIGH
);
183 EXPECT_EQ(&delegate2
, adapter
->DefaultPairingDelegate());
186 TEST(BluetoothAdapterTest
, UnregisterDelegate
) {
187 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
189 // Verify that after unregistering a delegate, NULL is returned.
190 TestPairingDelegate delegate
;
192 adapter
->AddPairingDelegate(&delegate
,
193 BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_LOW
);
194 adapter
->RemovePairingDelegate(&delegate
);
196 EXPECT_TRUE(adapter
->DefaultPairingDelegate() == NULL
);
199 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterEmpty
) {
200 scoped_refptr
<BluetoothAdapter
> adapter
= new TestBluetoothAdapter();
201 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
;
203 discovery_filter
= adapter
->GetMergedDiscoveryFilter();
204 EXPECT_TRUE(discovery_filter
.get() == nullptr);
206 discovery_filter
= adapter
->GetMergedDiscoveryFilterMasked(nullptr);
207 EXPECT_TRUE(discovery_filter
.get() == nullptr);
210 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterRegular
) {
211 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
212 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter
;
214 // make sure adapter have one session wihout filtering.
215 adapter
->InjectFilteredSession(discovery_filter
.Pass());
217 // having one reglar session should result in no filter
218 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
=
219 adapter
->GetMergedDiscoveryFilter();
220 EXPECT_TRUE(resulting_filter
.get() == nullptr);
222 // omiting no filter when having one reglar session should result in no filter
223 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(nullptr);
224 EXPECT_TRUE(resulting_filter
.get() == nullptr);
226 adapter
->CleanupSessions();
229 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterRssi
) {
230 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
231 int16_t resulting_rssi
;
232 uint16_t resulting_pathloss
;
233 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
;
235 BluetoothDiscoveryFilter
* df
= new BluetoothDiscoveryFilter(
236 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
238 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter(df
);
240 BluetoothDiscoveryFilter
* df2
= new BluetoothDiscoveryFilter(
241 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
243 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter2(df2
);
245 // make sure adapter have one session wihout filtering.
246 adapter
->InjectFilteredSession(discovery_filter
.Pass());
248 // DO_NOTHING should have no impact
249 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
250 resulting_filter
->GetRSSI(&resulting_rssi
);
251 EXPECT_EQ(-30, resulting_rssi
);
253 // should not use df2 at all, as it's not associated with adapter yet
254 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df2
);
255 resulting_filter
->GetRSSI(&resulting_rssi
);
256 EXPECT_EQ(-30, resulting_rssi
);
258 adapter
->InjectFilteredSession(discovery_filter2
.Pass());
260 // result of merging two rssi values should be lower one
261 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
262 resulting_filter
->GetRSSI(&resulting_rssi
);
263 EXPECT_EQ(-65, resulting_rssi
);
265 // ommit bigger value, result should stay same
266 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df
);
267 resulting_filter
->GetRSSI(&resulting_rssi
);
268 EXPECT_EQ(-65, resulting_rssi
);
270 // ommit lower value, result should change
271 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df2
);
272 resulting_filter
->GetRSSI(&resulting_rssi
);
273 EXPECT_EQ(-30, resulting_rssi
);
275 BluetoothDiscoveryFilter
* df3
= new BluetoothDiscoveryFilter(
276 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
277 df3
->SetPathloss(60);
278 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter3(df3
);
280 // when rssi and pathloss are merged, both should be cleared, becuase there is
281 // no way to tell which filter will be more generic
282 adapter
->InjectFilteredSession(discovery_filter3
.Pass());
283 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
284 EXPECT_FALSE(resulting_filter
->GetRSSI(&resulting_rssi
));
285 EXPECT_FALSE(resulting_filter
->GetPathloss(&resulting_pathloss
));
287 adapter
->CleanupSessions();
290 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterTransport
) {
291 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
292 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
;
294 BluetoothDiscoveryFilter
* df
= new BluetoothDiscoveryFilter(
295 BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
);
296 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter(df
);
298 BluetoothDiscoveryFilter
* df2
= new BluetoothDiscoveryFilter(
299 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
300 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter2(df2
);
302 adapter
->InjectFilteredSession(discovery_filter
.Pass());
304 // Just one filter, make sure transport was properly rewritten
305 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
306 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
,
307 resulting_filter
->GetTransport());
309 adapter
->InjectFilteredSession(discovery_filter2
.Pass());
311 // Two filters, should have OR of both transport's
312 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
313 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
,
314 resulting_filter
->GetTransport());
316 // When 1st filter is masked, 2nd filter transport should be returned.
317 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df
);
318 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
,
319 resulting_filter
->GetTransport());
321 // When 2nd filter is masked, 1st filter transport should be returned.
322 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df2
);
323 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
,
324 resulting_filter
->GetTransport());
326 BluetoothDiscoveryFilter
* df3
= new BluetoothDiscoveryFilter(
327 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
328 df3
->CopyFrom(BluetoothDiscoveryFilter(
329 BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
));
330 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter3(df3
);
332 // Merging empty filter in should result in empty filter
333 adapter
->InjectFilteredSession(discovery_filter3
.Pass());
334 resulting_filter
= adapter
->GetMergedDiscoveryFilter();
335 EXPECT_TRUE(resulting_filter
->IsDefault());
337 adapter
->CleanupSessions();
340 TEST(BluetoothAdapterTest
, GetMergedDiscoveryFilterAllFields
) {
341 scoped_refptr
<TestBluetoothAdapter
> adapter
= new TestBluetoothAdapter();
342 int16_t resulting_rssi
;
343 std::set
<device::BluetoothUUID
> resulting_uuids
;
345 BluetoothDiscoveryFilter
* df
= new BluetoothDiscoveryFilter(
346 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
348 df
->AddUUID(device::BluetoothUUID("1000"));
349 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter(df
);
351 BluetoothDiscoveryFilter
* df2
= new BluetoothDiscoveryFilter(
352 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
354 df2
->SetTransport(BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
355 df2
->AddUUID(device::BluetoothUUID("1020"));
356 df2
->AddUUID(device::BluetoothUUID("1001"));
357 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter2(df2
);
359 BluetoothDiscoveryFilter
* df3
= new BluetoothDiscoveryFilter(
360 BluetoothDiscoveryFilter::Transport::TRANSPORT_LE
);
362 df3
->SetTransport(BluetoothDiscoveryFilter::Transport::TRANSPORT_CLASSIC
);
363 df3
->AddUUID(device::BluetoothUUID("1020"));
364 df3
->AddUUID(device::BluetoothUUID("1003"));
365 scoped_ptr
<BluetoothDiscoveryFilter
> discovery_filter3(df3
);
367 // make sure adapter have one session wihout filtering.
368 adapter
->InjectFilteredSession(discovery_filter
.Pass());
369 adapter
->InjectFilteredSession(discovery_filter2
.Pass());
370 adapter
->InjectFilteredSession(discovery_filter3
.Pass());
372 scoped_ptr
<BluetoothDiscoveryFilter
> resulting_filter
=
373 adapter
->GetMergedDiscoveryFilter();
374 resulting_filter
->GetRSSI(&resulting_rssi
);
375 resulting_filter
->GetUUIDs(resulting_uuids
);
376 EXPECT_TRUE(resulting_filter
->GetTransport());
377 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
,
378 resulting_filter
->GetTransport());
379 EXPECT_EQ(-85, resulting_rssi
);
380 EXPECT_EQ(4UL, resulting_uuids
.size());
381 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1000")) !=
382 resulting_uuids
.end());
383 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1001")) !=
384 resulting_uuids
.end());
385 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1003")) !=
386 resulting_uuids
.end());
387 EXPECT_TRUE(resulting_uuids
.find(device::BluetoothUUID("1020")) !=
388 resulting_uuids
.end());
390 resulting_filter
= adapter
->GetMergedDiscoveryFilterMasked(df
);
391 EXPECT_EQ(BluetoothDiscoveryFilter::Transport::TRANSPORT_DUAL
,
392 resulting_filter
->GetTransport());
394 adapter
->CleanupSessions();
397 } // namespace device