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
3// found in the LICENSE file.
4
5#include "base/memory/scoped_vector.h"
6#include "base/message_loop/message_loop.h"
7#include "base/strings/utf_string_conversions.h"
8#include "chromeos/dbus/dbus_thread_manager.h"
9#include "chromeos/dbus/fake_bluetooth_adapter_client.h"
10#include "chromeos/dbus/fake_bluetooth_agent_manager_client.h"
11#include "chromeos/dbus/fake_bluetooth_device_client.h"
12#include "chromeos/dbus/fake_bluetooth_gatt_service_client.h"
13#include "chromeos/dbus/fake_bluetooth_input_client.h"
14#include "dbus/object_path.h"
15#include "device/bluetooth/bluetooth_adapter.h"
16#include "device/bluetooth/bluetooth_adapter_chromeos.h"
17#include "device/bluetooth/bluetooth_adapter_factory.h"
18#include "device/bluetooth/bluetooth_device.h"
19#include "device/bluetooth/bluetooth_device_chromeos.h"
20#include "device/bluetooth/bluetooth_discovery_session.h"
21#include "device/bluetooth/bluetooth_pairing_chromeos.h"
22#include "testing/gtest/include/gtest/gtest.h"
23#include "third_party/cros_system_api/dbus/service_constants.h"
24
25using device::BluetoothAdapter;
26using device::BluetoothAdapterFactory;
27using device::BluetoothDevice;
28using device::BluetoothDiscoverySession;
29using device::BluetoothUUID;
30
31namespace chromeos {
32
33namespace {
34
35class TestObserver : public BluetoothAdapter::Observer {
36 public:
37  TestObserver(scoped_refptr<BluetoothAdapter> adapter)
38      : present_changed_count_(0),
39        powered_changed_count_(0),
40        discoverable_changed_count_(0),
41        discovering_changed_count_(0),
42        last_present_(false),
43        last_powered_(false),
44        last_discovering_(false),
45        device_added_count_(0),
46        device_changed_count_(0),
47        device_removed_count_(0),
48        last_device_(NULL),
49        adapter_(adapter) {
50    adapter_->AddObserver(this);
51  }
52
53  virtual ~TestObserver() {
54    adapter_->RemoveObserver(this);
55  }
56
57  virtual void AdapterPresentChanged(BluetoothAdapter* adapter,
58                                     bool present) OVERRIDE {
59    EXPECT_EQ(adapter_.get(), adapter);
60
61    ++present_changed_count_;
62    last_present_ = present;
63  }
64
65  virtual void AdapterPoweredChanged(BluetoothAdapter* adapter,
66                                     bool powered) OVERRIDE {
67    EXPECT_EQ(adapter_.get(), adapter);
68
69    ++powered_changed_count_;
70    last_powered_ = powered;
71  }
72
73  virtual void AdapterDiscoverableChanged(BluetoothAdapter* adapter,
74                                          bool discoverable) OVERRIDE {
75    EXPECT_EQ(adapter_.get(), adapter);
76
77    ++discoverable_changed_count_;
78  }
79
80  virtual void AdapterDiscoveringChanged(BluetoothAdapter* adapter,
81                                         bool discovering) OVERRIDE {
82    EXPECT_EQ(adapter_.get(), adapter);
83
84    ++discovering_changed_count_;
85    last_discovering_ = discovering;
86  }
87
88  virtual void DeviceAdded(BluetoothAdapter* adapter,
89                           BluetoothDevice* device) OVERRIDE {
90    EXPECT_EQ(adapter_.get(), adapter);
91
92    ++device_added_count_;
93    last_device_ = device;
94    last_device_address_ = device->GetAddress();
95
96    QuitMessageLoop();
97  }
98
99  virtual void DeviceChanged(BluetoothAdapter* adapter,
100                             BluetoothDevice* device) OVERRIDE {
101    EXPECT_EQ(adapter_.get(), adapter);
102
103    ++device_changed_count_;
104    last_device_ = device;
105    last_device_address_ = device->GetAddress();
106
107    QuitMessageLoop();
108  }
109
110  virtual void DeviceRemoved(BluetoothAdapter* adapter,
111                             BluetoothDevice* device) OVERRIDE {
112    EXPECT_EQ(adapter_.get(), adapter);
113
114    ++device_removed_count_;
115    // Can't save device, it may be freed
116    last_device_address_ = device->GetAddress();
117
118    QuitMessageLoop();
119  }
120
121  int present_changed_count_;
122  int powered_changed_count_;
123  int discoverable_changed_count_;
124  int discovering_changed_count_;
125  bool last_present_;
126  bool last_powered_;
127  bool last_discovering_;
128  int device_added_count_;
129  int device_changed_count_;
130  int device_removed_count_;
131  BluetoothDevice* last_device_;
132  std::string last_device_address_;
133
134 private:
135  // Some tests use a message loop since background processing is simulated;
136  // break out of those loops.
137  void QuitMessageLoop() {
138    if (base::MessageLoop::current() &&
139        base::MessageLoop::current()->is_running())
140      base::MessageLoop::current()->Quit();
141  }
142
143  scoped_refptr<BluetoothAdapter> adapter_;
144};
145
146}  // namespace
147
148class TestPairingDelegate : public BluetoothDevice::PairingDelegate {
149 public:
150  TestPairingDelegate()
151      : call_count_(0),
152        request_pincode_count_(0),
153        request_passkey_count_(0),
154        display_pincode_count_(0),
155        display_passkey_count_(0),
156        keys_entered_count_(0),
157        confirm_passkey_count_(0),
158        authorize_pairing_count_(0),
159        last_passkey_(9999999U),
160        last_entered_(999U) {}
161  virtual ~TestPairingDelegate() {}
162
163  virtual void RequestPinCode(BluetoothDevice* device) OVERRIDE {
164    ++call_count_;
165    ++request_pincode_count_;
166    QuitMessageLoop();
167  }
168
169  virtual void RequestPasskey(BluetoothDevice* device) OVERRIDE {
170    ++call_count_;
171    ++request_passkey_count_;
172    QuitMessageLoop();
173  }
174
175  virtual void DisplayPinCode(BluetoothDevice* device,
176                              const std::string& pincode) OVERRIDE {
177    ++call_count_;
178    ++display_pincode_count_;
179    last_pincode_ = pincode;
180    QuitMessageLoop();
181  }
182
183  virtual void DisplayPasskey(BluetoothDevice* device,
184                              uint32 passkey) OVERRIDE {
185    ++call_count_;
186    ++display_passkey_count_;
187    last_passkey_ = passkey;
188    QuitMessageLoop();
189  }
190
191  virtual void KeysEntered(BluetoothDevice* device, uint32 entered) OVERRIDE {
192    ++call_count_;
193    ++keys_entered_count_;
194    last_entered_ = entered;
195    QuitMessageLoop();
196  }
197
198  virtual void ConfirmPasskey(BluetoothDevice* device,
199                              uint32 passkey) OVERRIDE {
200    ++call_count_;
201    ++confirm_passkey_count_;
202    last_passkey_ = passkey;
203    QuitMessageLoop();
204  }
205
206  virtual void AuthorizePairing(BluetoothDevice* device) OVERRIDE {
207    ++call_count_;
208    ++authorize_pairing_count_;
209    QuitMessageLoop();
210  }
211
212  int call_count_;
213  int request_pincode_count_;
214  int request_passkey_count_;
215  int display_pincode_count_;
216  int display_passkey_count_;
217  int keys_entered_count_;
218  int confirm_passkey_count_;
219  int authorize_pairing_count_;
220  uint32 last_passkey_;
221  uint32 last_entered_;
222  std::string last_pincode_;
223
224  private:
225   // Some tests use a message loop since background processing is simulated;
226   // break out of those loops.
227   void QuitMessageLoop() {
228     if (base::MessageLoop::current() &&
229         base::MessageLoop::current()->is_running())
230       base::MessageLoop::current()->Quit();
231   }
232};
233
234class BluetoothChromeOSTest : public testing::Test {
235 public:
236  virtual void SetUp() {
237    scoped_ptr<DBusThreadManagerSetter> dbus_setter =
238        chromeos::DBusThreadManager::GetSetterForTesting();
239    // We need to initialize DBusThreadManager early to prevent
240    // Bluetooth*::Create() methods from picking the real instead of fake
241    // implementations.
242    fake_bluetooth_adapter_client_ = new FakeBluetoothAdapterClient;
243    dbus_setter->SetBluetoothAdapterClient(
244        scoped_ptr<BluetoothAdapterClient>(fake_bluetooth_adapter_client_));
245    fake_bluetooth_device_client_ = new FakeBluetoothDeviceClient;
246    dbus_setter->SetBluetoothDeviceClient(
247        scoped_ptr<BluetoothDeviceClient>(fake_bluetooth_device_client_));
248    dbus_setter->SetBluetoothInputClient(
249        scoped_ptr<BluetoothInputClient>(new FakeBluetoothInputClient));
250    dbus_setter->SetBluetoothAgentManagerClient(
251        scoped_ptr<BluetoothAgentManagerClient>(
252            new FakeBluetoothAgentManagerClient));
253    dbus_setter->SetBluetoothGattServiceClient(
254        scoped_ptr<BluetoothGattServiceClient>(
255            new FakeBluetoothGattServiceClient));
256
257    fake_bluetooth_adapter_client_->SetSimulationIntervalMs(10);
258
259    callback_count_ = 0;
260    error_callback_count_ = 0;
261    last_connect_error_ = BluetoothDevice::ERROR_UNKNOWN;
262    last_client_error_ = "";
263  }
264
265  virtual void TearDown() {
266    for (ScopedVector<BluetoothDiscoverySession>::iterator iter =
267            discovery_sessions_.begin();
268         iter != discovery_sessions_.end();
269         ++iter) {
270      BluetoothDiscoverySession* session = *iter;
271      if (!session->IsActive())
272        continue;
273      callback_count_ = 0;
274      session->Stop(
275          base::Bind(&BluetoothChromeOSTest::Callback,
276                     base::Unretained(this)),
277          base::Bind(&BluetoothChromeOSTest::ErrorCallback,
278                     base::Unretained(this)));
279      message_loop_.Run();
280      ASSERT_EQ(1, callback_count_);
281    }
282    discovery_sessions_.clear();
283    adapter_ = NULL;
284    DBusThreadManager::Shutdown();
285  }
286
287  // Generic callbacks
288  void Callback() {
289    ++callback_count_;
290    QuitMessageLoop();
291  }
292
293  void DiscoverySessionCallback(
294      scoped_ptr<BluetoothDiscoverySession> discovery_session) {
295    ++callback_count_;
296    discovery_sessions_.push_back(discovery_session.release());
297    QuitMessageLoop();
298  }
299
300  void ErrorCallback() {
301    ++error_callback_count_;
302    QuitMessageLoop();
303  }
304
305  void DBusErrorCallback(const std::string& error_name,
306                         const std::string& error_message) {
307    ++error_callback_count_;
308    last_client_error_ = error_name;
309    QuitMessageLoop();
310  }
311
312  void ConnectErrorCallback(BluetoothDevice::ConnectErrorCode error) {
313    ++error_callback_count_;
314    last_connect_error_ = error;
315  }
316
317  // Call to fill the adapter_ member with a BluetoothAdapter instance.
318  void GetAdapter() {
319    adapter_ = new BluetoothAdapterChromeOS();
320    ASSERT_TRUE(adapter_.get() != NULL);
321    ASSERT_TRUE(adapter_->IsInitialized());
322  }
323
324  // Run a discovery phase until the named device is detected, or if the named
325  // device is not created, the discovery process ends without finding it.
326  //
327  // The correct behavior of discovery is tested by the "Discovery" test case
328  // without using this function.
329  void DiscoverDevice(const std::string& address) {
330    ASSERT_TRUE(adapter_.get() != NULL);
331    ASSERT_TRUE(base::MessageLoop::current() != NULL);
332    fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
333
334    TestObserver observer(adapter_);
335
336    adapter_->SetPowered(
337        true,
338        base::Bind(&BluetoothChromeOSTest::Callback,
339                   base::Unretained(this)),
340        base::Bind(&BluetoothChromeOSTest::ErrorCallback,
341                   base::Unretained(this)));
342    adapter_->StartDiscoverySession(
343        base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
344                   base::Unretained(this)),
345        base::Bind(&BluetoothChromeOSTest::ErrorCallback,
346                   base::Unretained(this)));
347    base::MessageLoop::current()->Run();
348    ASSERT_EQ(2, callback_count_);
349    ASSERT_EQ(0, error_callback_count_);
350    ASSERT_EQ((size_t)1, discovery_sessions_.size());
351    ASSERT_TRUE(discovery_sessions_[0]->IsActive());
352    callback_count_ = 0;
353
354    ASSERT_TRUE(adapter_->IsPowered());
355    ASSERT_TRUE(adapter_->IsDiscovering());
356
357    while (!observer.device_removed_count_ &&
358           observer.last_device_address_ != address)
359      base::MessageLoop::current()->Run();
360
361    discovery_sessions_[0]->Stop(
362        base::Bind(&BluetoothChromeOSTest::Callback,
363                   base::Unretained(this)),
364        base::Bind(&BluetoothChromeOSTest::ErrorCallback,
365                   base::Unretained(this)));
366    base::MessageLoop::current()->Run();
367    ASSERT_EQ(1, callback_count_);
368    ASSERT_EQ(0, error_callback_count_);
369    callback_count_ = 0;
370
371    ASSERT_FALSE(adapter_->IsDiscovering());
372  }
373
374  // Run a discovery phase so we have devices that can be paired with.
375  void DiscoverDevices() {
376    // Pass an invalid address for the device so that the discovery process
377    // completes with all devices.
378    DiscoverDevice("does not exist");
379  }
380
381 protected:
382  base::MessageLoop message_loop_;
383  FakeBluetoothAdapterClient* fake_bluetooth_adapter_client_;
384  FakeBluetoothDeviceClient* fake_bluetooth_device_client_;
385  scoped_refptr<BluetoothAdapter> adapter_;
386
387  int callback_count_;
388  int error_callback_count_;
389  enum BluetoothDevice::ConnectErrorCode last_connect_error_;
390  std::string last_client_error_;
391  ScopedVector<BluetoothDiscoverySession> discovery_sessions_;
392
393 private:
394  // Some tests use a message loop since background processing is simulated;
395  // break out of those loops.
396  void QuitMessageLoop() {
397    if (base::MessageLoop::current() &&
398        base::MessageLoop::current()->is_running())
399      base::MessageLoop::current()->Quit();
400  }
401};
402
403TEST_F(BluetoothChromeOSTest, AlreadyPresent) {
404  GetAdapter();
405
406  // This verifies that the class gets the list of adapters when created;
407  // and initializes with an existing adapter if there is one.
408  EXPECT_TRUE(adapter_->IsPresent());
409  EXPECT_FALSE(adapter_->IsPowered());
410  EXPECT_EQ(FakeBluetoothAdapterClient::kAdapterAddress,
411            adapter_->GetAddress());
412  EXPECT_FALSE(adapter_->IsDiscovering());
413
414  // There should be a device
415  BluetoothAdapter::DeviceList devices = adapter_->GetDevices();
416  EXPECT_EQ(1U, devices.size());
417  EXPECT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
418            devices[0]->GetAddress());
419}
420
421TEST_F(BluetoothChromeOSTest, BecomePresent) {
422  fake_bluetooth_adapter_client_->SetVisible(false);
423  GetAdapter();
424  ASSERT_FALSE(adapter_->IsPresent());
425
426  // Install an observer; expect the AdapterPresentChanged to be called
427  // with true, and IsPresent() to return true.
428  TestObserver observer(adapter_);
429
430  fake_bluetooth_adapter_client_->SetVisible(true);
431
432  EXPECT_EQ(1, observer.present_changed_count_);
433  EXPECT_TRUE(observer.last_present_);
434
435  EXPECT_TRUE(adapter_->IsPresent());
436
437  // We should have had a device announced.
438  EXPECT_EQ(1, observer.device_added_count_);
439  EXPECT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
440            observer.last_device_address_);
441
442  // Other callbacks shouldn't be called if the values are false.
443  EXPECT_EQ(0, observer.powered_changed_count_);
444  EXPECT_EQ(0, observer.discovering_changed_count_);
445  EXPECT_FALSE(adapter_->IsPowered());
446  EXPECT_FALSE(adapter_->IsDiscovering());
447}
448
449TEST_F(BluetoothChromeOSTest, BecomeNotPresent) {
450  GetAdapter();
451  ASSERT_TRUE(adapter_->IsPresent());
452
453  // Install an observer; expect the AdapterPresentChanged to be called
454  // with false, and IsPresent() to return false.
455  TestObserver observer(adapter_);
456
457  fake_bluetooth_adapter_client_->SetVisible(false);
458
459  EXPECT_EQ(1, observer.present_changed_count_);
460  EXPECT_FALSE(observer.last_present_);
461
462  EXPECT_FALSE(adapter_->IsPresent());
463
464  // We should have had a device removed.
465  EXPECT_EQ(1, observer.device_removed_count_);
466  EXPECT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
467            observer.last_device_address_);
468
469  // Other callbacks shouldn't be called since the values are false.
470  EXPECT_EQ(0, observer.powered_changed_count_);
471  EXPECT_EQ(0, observer.discovering_changed_count_);
472  EXPECT_FALSE(adapter_->IsPowered());
473  EXPECT_FALSE(adapter_->IsDiscovering());
474}
475
476TEST_F(BluetoothChromeOSTest, SecondAdapter) {
477  GetAdapter();
478  ASSERT_TRUE(adapter_->IsPresent());
479
480  // Install an observer, then add a second adapter. Nothing should change,
481  // we ignore the second adapter.
482  TestObserver observer(adapter_);
483
484  fake_bluetooth_adapter_client_->SetSecondVisible(true);
485
486  EXPECT_EQ(0, observer.present_changed_count_);
487
488  EXPECT_TRUE(adapter_->IsPresent());
489  EXPECT_EQ(FakeBluetoothAdapterClient::kAdapterAddress,
490            adapter_->GetAddress());
491
492  // Try removing the first adapter, we should now act as if the adapter
493  // is no longer present rather than fall back to the second.
494  fake_bluetooth_adapter_client_->SetVisible(false);
495
496  EXPECT_EQ(1, observer.present_changed_count_);
497  EXPECT_FALSE(observer.last_present_);
498
499  EXPECT_FALSE(adapter_->IsPresent());
500
501  // We should have had a device removed.
502  EXPECT_EQ(1, observer.device_removed_count_);
503  EXPECT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
504            observer.last_device_address_);
505
506  // Other callbacks shouldn't be called since the values are false.
507  EXPECT_EQ(0, observer.powered_changed_count_);
508  EXPECT_EQ(0, observer.discovering_changed_count_);
509  EXPECT_FALSE(adapter_->IsPowered());
510  EXPECT_FALSE(adapter_->IsDiscovering());
511
512  observer.device_removed_count_ = 0;
513
514  // Removing the second adapter shouldn't set anything either.
515  fake_bluetooth_adapter_client_->SetSecondVisible(false);
516
517  EXPECT_EQ(0, observer.device_removed_count_);
518  EXPECT_EQ(0, observer.powered_changed_count_);
519  EXPECT_EQ(0, observer.discovering_changed_count_);
520}
521
522TEST_F(BluetoothChromeOSTest, BecomePowered) {
523  GetAdapter();
524  ASSERT_FALSE(adapter_->IsPowered());
525
526  // Install an observer; expect the AdapterPoweredChanged to be called
527  // with true, and IsPowered() to return true.
528  TestObserver observer(adapter_);
529
530  adapter_->SetPowered(
531      true,
532      base::Bind(&BluetoothChromeOSTest::Callback,
533                 base::Unretained(this)),
534      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
535                 base::Unretained(this)));
536  EXPECT_EQ(1, callback_count_);
537  EXPECT_EQ(0, error_callback_count_);
538
539  EXPECT_EQ(1, observer.powered_changed_count_);
540  EXPECT_TRUE(observer.last_powered_);
541
542  EXPECT_TRUE(adapter_->IsPowered());
543}
544
545TEST_F(BluetoothChromeOSTest, BecomeNotPowered) {
546  GetAdapter();
547  adapter_->SetPowered(
548      true,
549      base::Bind(&BluetoothChromeOSTest::Callback,
550                 base::Unretained(this)),
551      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
552                 base::Unretained(this)));
553  EXPECT_EQ(1, callback_count_);
554  EXPECT_EQ(0, error_callback_count_);
555  callback_count_ = 0;
556
557  ASSERT_TRUE(adapter_->IsPowered());
558
559  // Install an observer; expect the AdapterPoweredChanged to be called
560  // with false, and IsPowered() to return false.
561  TestObserver observer(adapter_);
562
563  adapter_->SetPowered(
564      false,
565      base::Bind(&BluetoothChromeOSTest::Callback,
566                 base::Unretained(this)),
567      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
568                 base::Unretained(this)));
569  EXPECT_EQ(1, callback_count_);
570  EXPECT_EQ(0, error_callback_count_);
571
572  EXPECT_EQ(1, observer.powered_changed_count_);
573  EXPECT_FALSE(observer.last_powered_);
574
575  EXPECT_FALSE(adapter_->IsPowered());
576}
577
578TEST_F(BluetoothChromeOSTest, ChangeAdapterName) {
579  GetAdapter();
580
581  static const std::string new_name(".__.");
582
583  adapter_->SetName(
584      new_name,
585      base::Bind(&BluetoothChromeOSTest::Callback,
586                 base::Unretained(this)),
587      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
588                 base::Unretained(this)));
589  EXPECT_EQ(1, callback_count_);
590  EXPECT_EQ(0, error_callback_count_);
591
592  EXPECT_EQ(new_name, adapter_->GetName());
593}
594
595TEST_F(BluetoothChromeOSTest, BecomeDiscoverable) {
596  GetAdapter();
597  ASSERT_FALSE(adapter_->IsDiscoverable());
598
599  // Install an observer; expect the AdapterDiscoverableChanged to be called
600  // with true, and IsDiscoverable() to return true.
601  TestObserver observer(adapter_);
602
603  adapter_->SetDiscoverable(
604      true,
605      base::Bind(&BluetoothChromeOSTest::Callback,
606                 base::Unretained(this)),
607      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
608                 base::Unretained(this)));
609  EXPECT_EQ(1, callback_count_);
610  EXPECT_EQ(0, error_callback_count_);
611
612  EXPECT_EQ(1, observer.discoverable_changed_count_);
613
614  EXPECT_TRUE(adapter_->IsDiscoverable());
615}
616
617TEST_F(BluetoothChromeOSTest, BecomeNotDiscoverable) {
618  GetAdapter();
619  adapter_->SetDiscoverable(
620      true,
621      base::Bind(&BluetoothChromeOSTest::Callback,
622                 base::Unretained(this)),
623      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
624                 base::Unretained(this)));
625  EXPECT_EQ(1, callback_count_);
626  EXPECT_EQ(0, error_callback_count_);
627  callback_count_ = 0;
628
629  ASSERT_TRUE(adapter_->IsDiscoverable());
630
631  // Install an observer; expect the AdapterDiscoverableChanged to be called
632  // with false, and IsDiscoverable() to return false.
633  TestObserver observer(adapter_);
634
635  adapter_->SetDiscoverable(
636      false,
637      base::Bind(&BluetoothChromeOSTest::Callback,
638                 base::Unretained(this)),
639      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
640                 base::Unretained(this)));
641  EXPECT_EQ(1, callback_count_);
642  EXPECT_EQ(0, error_callback_count_);
643
644  EXPECT_EQ(1, observer.discoverable_changed_count_);
645
646  EXPECT_FALSE(adapter_->IsDiscoverable());
647}
648
649TEST_F(BluetoothChromeOSTest, StopDiscovery) {
650  GetAdapter();
651
652  adapter_->SetPowered(
653      true,
654      base::Bind(&BluetoothChromeOSTest::Callback,
655                 base::Unretained(this)),
656      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
657                 base::Unretained(this)));
658  adapter_->StartDiscoverySession(
659      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
660                 base::Unretained(this)),
661      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
662                 base::Unretained(this)));
663  message_loop_.Run();
664  EXPECT_EQ(2, callback_count_);
665  EXPECT_EQ(0, error_callback_count_);
666  callback_count_ = 0;
667
668  ASSERT_TRUE(adapter_->IsPowered());
669  ASSERT_TRUE(adapter_->IsDiscovering());
670  ASSERT_EQ((size_t)1, discovery_sessions_.size());
671  ASSERT_TRUE(discovery_sessions_[0]->IsActive());
672
673  // Install an observer; aside from the callback, expect the
674  // AdapterDiscoveringChanged method to be called and no longer to be
675  // discovering,
676  TestObserver observer(adapter_);
677
678  discovery_sessions_[0]->Stop(
679      base::Bind(&BluetoothChromeOSTest::Callback,
680                 base::Unretained(this)),
681      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
682                 base::Unretained(this)));
683  message_loop_.Run();
684  EXPECT_EQ(1, callback_count_);
685  EXPECT_EQ(0, error_callback_count_);
686
687  EXPECT_EQ(1, observer.discovering_changed_count_);
688  EXPECT_FALSE(observer.last_discovering_);
689
690  EXPECT_FALSE(adapter_->IsDiscovering());
691}
692
693TEST_F(BluetoothChromeOSTest, Discovery) {
694  // Test a simulated discovery session.
695  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
696  GetAdapter();
697
698  TestObserver observer(adapter_);
699
700  adapter_->SetPowered(
701      true,
702      base::Bind(&BluetoothChromeOSTest::Callback,
703                 base::Unretained(this)),
704      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
705                 base::Unretained(this)));
706  adapter_->StartDiscoverySession(
707      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
708                 base::Unretained(this)),
709      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
710                 base::Unretained(this)));
711  message_loop_.Run();
712  EXPECT_EQ(2, callback_count_);
713  EXPECT_EQ(0, error_callback_count_);
714  callback_count_ = 0;
715
716  ASSERT_TRUE(adapter_->IsPowered());
717  ASSERT_TRUE(adapter_->IsDiscovering());
718  ASSERT_EQ((size_t)1, discovery_sessions_.size());
719  ASSERT_TRUE(discovery_sessions_[0]->IsActive());
720
721  // First two devices to appear.
722  message_loop_.Run();
723
724  EXPECT_EQ(2, observer.device_added_count_);
725  EXPECT_EQ(FakeBluetoothDeviceClient::kLowEnergyAddress,
726            observer.last_device_address_);
727
728  // Next we should get another two devices...
729  message_loop_.Run();
730  EXPECT_EQ(4, observer.device_added_count_);
731
732  // Okay, let's run forward until a device is actually removed...
733  while (!observer.device_removed_count_)
734    message_loop_.Run();
735
736  EXPECT_EQ(1, observer.device_removed_count_);
737  EXPECT_EQ(FakeBluetoothDeviceClient::kVanishingDeviceAddress,
738            observer.last_device_address_);
739}
740
741TEST_F(BluetoothChromeOSTest, PoweredAndDiscovering) {
742  GetAdapter();
743  adapter_->SetPowered(
744      true,
745      base::Bind(&BluetoothChromeOSTest::Callback,
746                 base::Unretained(this)),
747      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
748                 base::Unretained(this)));
749  adapter_->StartDiscoverySession(
750      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
751                 base::Unretained(this)),
752      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
753                 base::Unretained(this)));
754  message_loop_.Run();
755  EXPECT_EQ(2, callback_count_);
756  EXPECT_EQ(0, error_callback_count_);
757  callback_count_ = 0;
758  ASSERT_EQ((size_t)1, discovery_sessions_.size());
759  ASSERT_TRUE(discovery_sessions_[0]->IsActive());
760
761  // Stop the timers that the simulation uses
762  fake_bluetooth_device_client_->EndDiscoverySimulation(
763      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath));
764
765  ASSERT_TRUE(adapter_->IsPowered());
766  ASSERT_TRUE(adapter_->IsDiscovering());
767
768  fake_bluetooth_adapter_client_->SetVisible(false);
769  ASSERT_FALSE(adapter_->IsPresent());
770  ASSERT_FALSE(discovery_sessions_[0]->IsActive());
771
772  // Install an observer; expect the AdapterPresentChanged,
773  // AdapterPoweredChanged and AdapterDiscoveringChanged methods to be called
774  // with true, and IsPresent(), IsPowered() and IsDiscovering() to all
775  // return true.
776  TestObserver observer(adapter_);
777
778  fake_bluetooth_adapter_client_->SetVisible(true);
779
780  EXPECT_EQ(1, observer.present_changed_count_);
781  EXPECT_TRUE(observer.last_present_);
782  EXPECT_TRUE(adapter_->IsPresent());
783
784  EXPECT_EQ(1, observer.powered_changed_count_);
785  EXPECT_TRUE(observer.last_powered_);
786  EXPECT_TRUE(adapter_->IsPowered());
787
788  EXPECT_EQ(1, observer.discovering_changed_count_);
789  EXPECT_TRUE(observer.last_discovering_);
790  EXPECT_TRUE(adapter_->IsDiscovering());
791
792  observer.present_changed_count_ = 0;
793  observer.powered_changed_count_ = 0;
794  observer.discovering_changed_count_ = 0;
795
796  // Now mark the adapter not present again. Expect the methods to be called
797  // again, to reset the properties back to false
798  fake_bluetooth_adapter_client_->SetVisible(false);
799
800  EXPECT_EQ(1, observer.present_changed_count_);
801  EXPECT_FALSE(observer.last_present_);
802  EXPECT_FALSE(adapter_->IsPresent());
803
804  EXPECT_EQ(1, observer.powered_changed_count_);
805  EXPECT_FALSE(observer.last_powered_);
806  EXPECT_FALSE(adapter_->IsPowered());
807
808  EXPECT_EQ(1, observer.discovering_changed_count_);
809  EXPECT_FALSE(observer.last_discovering_);
810  EXPECT_FALSE(adapter_->IsDiscovering());
811}
812
813// This unit test asserts that the basic reference counting logic works
814// correctly for discovery requests done via the BluetoothAdapter.
815TEST_F(BluetoothChromeOSTest, MultipleDiscoverySessions) {
816  GetAdapter();
817  adapter_->SetPowered(
818      true,
819      base::Bind(&BluetoothChromeOSTest::Callback,
820                 base::Unretained(this)),
821      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
822                 base::Unretained(this)));
823  EXPECT_EQ(1, callback_count_);
824  EXPECT_EQ(0, error_callback_count_);
825  EXPECT_TRUE(adapter_->IsPowered());
826  callback_count_ = 0;
827
828  TestObserver observer(adapter_);
829
830  EXPECT_EQ(0, observer.discovering_changed_count_);
831  EXPECT_FALSE(observer.last_discovering_);
832  EXPECT_FALSE(adapter_->IsDiscovering());
833
834  // Request device discovery 3 times.
835  for (int i = 0; i < 3; i++) {
836    adapter_->StartDiscoverySession(
837      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
838                 base::Unretained(this)),
839      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
840                 base::Unretained(this)));
841  }
842  // Run only once, as there should have been one D-Bus call.
843  message_loop_.Run();
844
845  // The observer should have received the discovering changed event exactly
846  // once, the success callback should have been called 3 times and the adapter
847  // should be discovering.
848  EXPECT_EQ(1, observer.discovering_changed_count_);
849  EXPECT_EQ(3, callback_count_);
850  EXPECT_EQ(0, error_callback_count_);
851  EXPECT_TRUE(observer.last_discovering_);
852  EXPECT_TRUE(adapter_->IsDiscovering());
853  ASSERT_EQ((size_t)3, discovery_sessions_.size());
854
855  // Request to stop discovery twice.
856  for (int i = 0; i < 2; i++) {
857    discovery_sessions_[i]->Stop(
858      base::Bind(&BluetoothChromeOSTest::Callback,
859                 base::Unretained(this)),
860      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
861                 base::Unretained(this)));
862  }
863
864  // The observer should have received no additional discovering changed events,
865  // the success callback should have been called 2 times and the adapter should
866  // still be discovering.
867  EXPECT_EQ(1, observer.discovering_changed_count_);
868  EXPECT_EQ(5, callback_count_);
869  EXPECT_EQ(0, error_callback_count_);
870  EXPECT_TRUE(observer.last_discovering_);
871  EXPECT_TRUE(adapter_->IsDiscovering());
872  EXPECT_TRUE(adapter_->IsDiscovering());
873  EXPECT_FALSE(discovery_sessions_[0]->IsActive());
874  EXPECT_FALSE(discovery_sessions_[1]->IsActive());
875  EXPECT_TRUE(discovery_sessions_[2]->IsActive());
876
877  // Request device discovery 3 times.
878  for (int i = 0; i < 3; i++) {
879    adapter_->StartDiscoverySession(
880      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
881                 base::Unretained(this)),
882      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
883                 base::Unretained(this)));
884  }
885
886  // The observer should have received no additional discovering changed events,
887  // the success callback should have been called 3 times and the adapter should
888  // still be discovering.
889  EXPECT_EQ(1, observer.discovering_changed_count_);
890  EXPECT_EQ(8, callback_count_);
891  EXPECT_EQ(0, error_callback_count_);
892  EXPECT_TRUE(observer.last_discovering_);
893  EXPECT_TRUE(adapter_->IsDiscovering());
894  ASSERT_EQ((size_t)6, discovery_sessions_.size());
895
896  // Request to stop discovery 4 times.
897  for (int i = 2; i < 6; i++) {
898    discovery_sessions_[i]->Stop(
899      base::Bind(&BluetoothChromeOSTest::Callback,
900                 base::Unretained(this)),
901      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
902                 base::Unretained(this)));
903  }
904  // Run only once, as there should have been one D-Bus call.
905  message_loop_.Run();
906
907  // The observer should have received the discovering changed event exactly
908  // once, the success callback should have been called 4 times and the adapter
909  // should no longer be discovering.
910  EXPECT_EQ(2, observer.discovering_changed_count_);
911  EXPECT_EQ(12, callback_count_);
912  EXPECT_EQ(0, error_callback_count_);
913  EXPECT_FALSE(observer.last_discovering_);
914  EXPECT_FALSE(adapter_->IsDiscovering());
915
916  // All discovery sessions should be inactive.
917  for (int i = 0; i < 6; i++)
918    EXPECT_FALSE(discovery_sessions_[i]->IsActive());
919
920  // Request to stop discovery on of the inactive sessions.
921  discovery_sessions_[0]->Stop(
922    base::Bind(&BluetoothChromeOSTest::Callback,
923               base::Unretained(this)),
924    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
925               base::Unretained(this)));
926
927  // The call should have failed.
928  EXPECT_EQ(2, observer.discovering_changed_count_);
929  EXPECT_EQ(12, callback_count_);
930  EXPECT_EQ(1, error_callback_count_);
931  EXPECT_FALSE(observer.last_discovering_);
932  EXPECT_FALSE(adapter_->IsDiscovering());
933}
934
935// This unit test asserts that the reference counting logic works correctly in
936// the cases when the adapter gets reset and D-Bus calls are made outside of
937// the BluetoothAdapter.
938TEST_F(BluetoothChromeOSTest,
939       UnexpectedChangesDuringMultipleDiscoverySessions) {
940  GetAdapter();
941  adapter_->SetPowered(
942      true,
943      base::Bind(&BluetoothChromeOSTest::Callback,
944                 base::Unretained(this)),
945      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
946                 base::Unretained(this)));
947  EXPECT_EQ(1, callback_count_);
948  EXPECT_EQ(0, error_callback_count_);
949  EXPECT_TRUE(adapter_->IsPowered());
950  callback_count_ = 0;
951
952  TestObserver observer(adapter_);
953
954  EXPECT_EQ(0, observer.discovering_changed_count_);
955  EXPECT_FALSE(observer.last_discovering_);
956  EXPECT_FALSE(adapter_->IsDiscovering());
957
958  // Request device discovery 3 times.
959  for (int i = 0; i < 3; i++) {
960    adapter_->StartDiscoverySession(
961      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
962                 base::Unretained(this)),
963      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
964                 base::Unretained(this)));
965  }
966  // Run only once, as there should have been one D-Bus call.
967  message_loop_.Run();
968
969  // The observer should have received the discovering changed event exactly
970  // once, the success callback should have been called 3 times and the adapter
971  // should be discovering.
972  EXPECT_EQ(1, observer.discovering_changed_count_);
973  EXPECT_EQ(3, callback_count_);
974  EXPECT_EQ(0, error_callback_count_);
975  EXPECT_TRUE(observer.last_discovering_);
976  EXPECT_TRUE(adapter_->IsDiscovering());
977  ASSERT_EQ((size_t)3, discovery_sessions_.size());
978
979  for (int i = 0; i < 3; i++)
980    EXPECT_TRUE(discovery_sessions_[i]->IsActive());
981
982  // Stop the timers that the simulation uses
983  fake_bluetooth_device_client_->EndDiscoverySimulation(
984      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath));
985
986  ASSERT_TRUE(adapter_->IsPowered());
987  ASSERT_TRUE(adapter_->IsDiscovering());
988
989  // Stop device discovery behind the adapter. The adapter and the observer
990  // should be notified of the change and the reference count should be reset.
991  // Even though FakeBluetoothAdapterClient does its own reference counting and
992  // we called 3 BluetoothAdapter::StartDiscoverySession 3 times, the
993  // FakeBluetoothAdapterClient's count should be only 1 and a single call to
994  // FakeBluetoothAdapterClient::StopDiscovery should work.
995  fake_bluetooth_adapter_client_->StopDiscovery(
996      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
997      base::Bind(&BluetoothChromeOSTest::Callback,
998                 base::Unretained(this)),
999      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
1000                 base::Unretained(this)));
1001  message_loop_.Run();
1002  EXPECT_EQ(2, observer.discovering_changed_count_);
1003  EXPECT_EQ(4, callback_count_);
1004  EXPECT_EQ(0, error_callback_count_);
1005  EXPECT_FALSE(observer.last_discovering_);
1006  EXPECT_FALSE(adapter_->IsDiscovering());
1007
1008  // All discovery session instances should have been updated.
1009  for (int i = 0; i < 3; i++)
1010    EXPECT_FALSE(discovery_sessions_[i]->IsActive());
1011  discovery_sessions_.clear();
1012
1013  // It should be possible to successfully start discovery.
1014  for (int i = 0; i < 2; i++) {
1015    adapter_->StartDiscoverySession(
1016      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1017                 base::Unretained(this)),
1018      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1019                 base::Unretained(this)));
1020  }
1021  // Run only once, as there should have been one D-Bus call.
1022  message_loop_.Run();
1023  EXPECT_EQ(3, observer.discovering_changed_count_);
1024  EXPECT_EQ(6, callback_count_);
1025  EXPECT_EQ(0, error_callback_count_);
1026  EXPECT_TRUE(observer.last_discovering_);
1027  EXPECT_TRUE(adapter_->IsDiscovering());
1028  ASSERT_EQ((size_t)2, discovery_sessions_.size());
1029
1030  for (int i = 0; i < 2; i++)
1031    EXPECT_TRUE(discovery_sessions_[i]->IsActive());
1032
1033  fake_bluetooth_device_client_->EndDiscoverySimulation(
1034      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath));
1035
1036  // Make the adapter disappear and appear. This will make it come back as
1037  // discovering. When this happens, the reference count should become and
1038  // remain 0 as no new request was made through the BluetoothAdapter.
1039  fake_bluetooth_adapter_client_->SetVisible(false);
1040  ASSERT_FALSE(adapter_->IsPresent());
1041  EXPECT_EQ(4, observer.discovering_changed_count_);
1042  EXPECT_EQ(6, callback_count_);
1043  EXPECT_EQ(0, error_callback_count_);
1044  EXPECT_FALSE(observer.last_discovering_);
1045  EXPECT_FALSE(adapter_->IsDiscovering());
1046
1047  for (int i = 0; i < 2; i++)
1048    EXPECT_FALSE(discovery_sessions_[i]->IsActive());
1049  discovery_sessions_.clear();
1050
1051  fake_bluetooth_adapter_client_->SetVisible(true);
1052  ASSERT_TRUE(adapter_->IsPresent());
1053  EXPECT_EQ(5, observer.discovering_changed_count_);
1054  EXPECT_EQ(6, callback_count_);
1055  EXPECT_EQ(0, error_callback_count_);
1056  EXPECT_TRUE(observer.last_discovering_);
1057  EXPECT_TRUE(adapter_->IsDiscovering());
1058
1059  // Start and stop discovery. At this point, FakeBluetoothAdapterClient has
1060  // a reference count that is equal to 1. Pretend that this was done by an
1061  // application other than us. Starting and stopping discovery will succeed
1062  // but it won't cause the discovery state to change.
1063  adapter_->StartDiscoverySession(
1064    base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1065               base::Unretained(this)),
1066    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1067               base::Unretained(this)));
1068  message_loop_.Run();  // Run the loop, as there should have been a D-Bus call.
1069  EXPECT_EQ(5, observer.discovering_changed_count_);
1070  EXPECT_EQ(7, callback_count_);
1071  EXPECT_EQ(0, error_callback_count_);
1072  EXPECT_TRUE(observer.last_discovering_);
1073  EXPECT_TRUE(adapter_->IsDiscovering());
1074  ASSERT_EQ((size_t)1, discovery_sessions_.size());
1075  EXPECT_TRUE(discovery_sessions_[0]->IsActive());
1076
1077  discovery_sessions_[0]->Stop(
1078    base::Bind(&BluetoothChromeOSTest::Callback,
1079               base::Unretained(this)),
1080    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1081               base::Unretained(this)));
1082  message_loop_.Run();  // Run the loop, as there should have been a D-Bus call.
1083  EXPECT_EQ(5, observer.discovering_changed_count_);
1084  EXPECT_EQ(8, callback_count_);
1085  EXPECT_EQ(0, error_callback_count_);
1086  EXPECT_TRUE(observer.last_discovering_);
1087  EXPECT_TRUE(adapter_->IsDiscovering());
1088  EXPECT_FALSE(discovery_sessions_[0]->IsActive());
1089  discovery_sessions_.clear();
1090
1091  // Start discovery again.
1092  adapter_->StartDiscoverySession(
1093    base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1094               base::Unretained(this)),
1095    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1096               base::Unretained(this)));
1097  message_loop_.Run();  // Run the loop, as there should have been a D-Bus call.
1098  EXPECT_EQ(5, observer.discovering_changed_count_);
1099  EXPECT_EQ(9, callback_count_);
1100  EXPECT_EQ(0, error_callback_count_);
1101  EXPECT_TRUE(observer.last_discovering_);
1102  EXPECT_TRUE(adapter_->IsDiscovering());
1103  ASSERT_EQ((size_t)1, discovery_sessions_.size());
1104  EXPECT_TRUE(discovery_sessions_[0]->IsActive());
1105
1106  // Stop discovery via D-Bus. The fake client's reference count will drop but
1107  // the discovery state won't change since our BluetoothAdapter also just
1108  // requested it via D-Bus.
1109  fake_bluetooth_adapter_client_->StopDiscovery(
1110      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
1111      base::Bind(&BluetoothChromeOSTest::Callback,
1112                 base::Unretained(this)),
1113      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
1114                 base::Unretained(this)));
1115  message_loop_.Run();
1116  EXPECT_EQ(5, observer.discovering_changed_count_);
1117  EXPECT_EQ(10, callback_count_);
1118  EXPECT_EQ(0, error_callback_count_);
1119  EXPECT_TRUE(observer.last_discovering_);
1120  EXPECT_TRUE(adapter_->IsDiscovering());
1121
1122  // Now end the discovery session. This should change the adapter's discovery
1123  // state.
1124  discovery_sessions_[0]->Stop(
1125    base::Bind(&BluetoothChromeOSTest::Callback,
1126               base::Unretained(this)),
1127    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1128               base::Unretained(this)));
1129  message_loop_.Run();
1130  EXPECT_EQ(6, observer.discovering_changed_count_);
1131  EXPECT_EQ(11, callback_count_);
1132  EXPECT_EQ(0, error_callback_count_);
1133  EXPECT_FALSE(observer.last_discovering_);
1134  EXPECT_FALSE(adapter_->IsDiscovering());
1135  EXPECT_FALSE(discovery_sessions_[0]->IsActive());
1136}
1137
1138TEST_F(BluetoothChromeOSTest, InvalidatedDiscoverySessions) {
1139  GetAdapter();
1140  adapter_->SetPowered(
1141      true,
1142      base::Bind(&BluetoothChromeOSTest::Callback,
1143                 base::Unretained(this)),
1144      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1145                 base::Unretained(this)));
1146  EXPECT_EQ(1, callback_count_);
1147  EXPECT_EQ(0, error_callback_count_);
1148  EXPECT_TRUE(adapter_->IsPowered());
1149  callback_count_ = 0;
1150
1151  TestObserver observer(adapter_);
1152
1153  EXPECT_EQ(0, observer.discovering_changed_count_);
1154  EXPECT_FALSE(observer.last_discovering_);
1155  EXPECT_FALSE(adapter_->IsDiscovering());
1156
1157  // Request device discovery 3 times.
1158  for (int i = 0; i < 3; i++) {
1159    adapter_->StartDiscoverySession(
1160      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1161                 base::Unretained(this)),
1162      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1163                 base::Unretained(this)));
1164  }
1165  // Run only once, as there should have been one D-Bus call.
1166  message_loop_.Run();
1167
1168  // The observer should have received the discovering changed event exactly
1169  // once, the success callback should have been called 3 times and the adapter
1170  // should be discovering.
1171  EXPECT_EQ(1, observer.discovering_changed_count_);
1172  EXPECT_EQ(3, callback_count_);
1173  EXPECT_EQ(0, error_callback_count_);
1174  EXPECT_TRUE(observer.last_discovering_);
1175  EXPECT_TRUE(adapter_->IsDiscovering());
1176  ASSERT_EQ((size_t)3, discovery_sessions_.size());
1177
1178  for (int i = 0; i < 3; i++)
1179    EXPECT_TRUE(discovery_sessions_[i]->IsActive());
1180
1181  // Stop the timers that the simulation uses
1182  fake_bluetooth_device_client_->EndDiscoverySimulation(
1183      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath));
1184
1185  ASSERT_TRUE(adapter_->IsPowered());
1186  ASSERT_TRUE(adapter_->IsDiscovering());
1187
1188  // Delete all but one discovery session.
1189  discovery_sessions_.pop_back();
1190  discovery_sessions_.pop_back();
1191  ASSERT_EQ((size_t)1, discovery_sessions_.size());
1192  EXPECT_TRUE(discovery_sessions_[0]->IsActive());
1193  EXPECT_TRUE(adapter_->IsDiscovering());
1194
1195  // Stop device discovery behind the adapter. The one active discovery session
1196  // should become inactive, but more importantly, we shouldn't run into any
1197  // memory errors as the sessions that we explicitly deleted should get
1198  // cleaned up.
1199  fake_bluetooth_adapter_client_->StopDiscovery(
1200      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
1201      base::Bind(&BluetoothChromeOSTest::Callback,
1202                 base::Unretained(this)),
1203      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
1204                 base::Unretained(this)));
1205  message_loop_.Run();
1206  EXPECT_EQ(2, observer.discovering_changed_count_);
1207  EXPECT_EQ(4, callback_count_);
1208  EXPECT_EQ(0, error_callback_count_);
1209  EXPECT_FALSE(observer.last_discovering_);
1210  EXPECT_FALSE(adapter_->IsDiscovering());
1211  EXPECT_FALSE(discovery_sessions_[0]->IsActive());
1212}
1213
1214TEST_F(BluetoothChromeOSTest, QueuedDiscoveryRequests) {
1215  GetAdapter();
1216
1217  adapter_->SetPowered(
1218      true,
1219      base::Bind(&BluetoothChromeOSTest::Callback,
1220                 base::Unretained(this)),
1221      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1222                 base::Unretained(this)));
1223  EXPECT_EQ(1, callback_count_);
1224  EXPECT_EQ(0, error_callback_count_);
1225  EXPECT_TRUE(adapter_->IsPowered());
1226  callback_count_ = 0;
1227
1228  TestObserver observer(adapter_);
1229
1230  EXPECT_EQ(0, observer.discovering_changed_count_);
1231  EXPECT_FALSE(observer.last_discovering_);
1232  EXPECT_FALSE(adapter_->IsDiscovering());
1233
1234  // Request to start discovery. The call should be pending.
1235  adapter_->StartDiscoverySession(
1236    base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1237               base::Unretained(this)),
1238    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1239               base::Unretained(this)));
1240  EXPECT_EQ(0, callback_count_);
1241
1242  fake_bluetooth_device_client_->EndDiscoverySimulation(
1243      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath));
1244
1245  // The underlying adapter has started discovery, but our call hasn't returned
1246  // yet.
1247  EXPECT_EQ(1, observer.discovering_changed_count_);
1248  EXPECT_TRUE(observer.last_discovering_);
1249  EXPECT_TRUE(adapter_->IsDiscovering());
1250  EXPECT_TRUE(discovery_sessions_.empty());
1251
1252  // Request to start discovery twice. These should get queued and there should
1253  // be no change in state.
1254  for (int i = 0; i < 2; i++) {
1255    adapter_->StartDiscoverySession(
1256      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1257                 base::Unretained(this)),
1258      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1259                 base::Unretained(this)));
1260  }
1261  EXPECT_EQ(0, callback_count_);
1262  EXPECT_EQ(0, error_callback_count_);
1263  EXPECT_EQ(1, observer.discovering_changed_count_);
1264  EXPECT_TRUE(observer.last_discovering_);
1265  EXPECT_TRUE(adapter_->IsDiscovering());
1266  EXPECT_TRUE(discovery_sessions_.empty());
1267
1268  // Process the pending call. The queued calls should execute and the discovery
1269  // session reference count should increase.
1270  message_loop_.Run();
1271  EXPECT_EQ(3, callback_count_);
1272  EXPECT_EQ(0, error_callback_count_);
1273  EXPECT_EQ(1, observer.discovering_changed_count_);
1274  EXPECT_TRUE(observer.last_discovering_);
1275  EXPECT_TRUE(adapter_->IsDiscovering());
1276  ASSERT_EQ((size_t)3, discovery_sessions_.size());
1277
1278  // Verify the reference count by removing sessions 3 times. The last request
1279  // should remain pending.
1280  for (int i = 0; i < 3; i++) {
1281    discovery_sessions_[i]->Stop(
1282      base::Bind(&BluetoothChromeOSTest::Callback,
1283                 base::Unretained(this)),
1284      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1285                 base::Unretained(this)));
1286  }
1287  EXPECT_EQ(5, callback_count_);
1288  EXPECT_EQ(0, error_callback_count_);
1289  EXPECT_EQ(2, observer.discovering_changed_count_);
1290  EXPECT_FALSE(observer.last_discovering_);
1291  EXPECT_FALSE(adapter_->IsDiscovering());
1292  EXPECT_FALSE(discovery_sessions_[0]->IsActive());
1293  EXPECT_FALSE(discovery_sessions_[1]->IsActive());
1294  EXPECT_TRUE(discovery_sessions_[2]->IsActive());
1295
1296  // Request to stop the session whose call is pending should fail.
1297  discovery_sessions_[2]->Stop(
1298    base::Bind(&BluetoothChromeOSTest::Callback,
1299               base::Unretained(this)),
1300    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1301               base::Unretained(this)));
1302  EXPECT_EQ(5, callback_count_);
1303  EXPECT_EQ(1, error_callback_count_);
1304  EXPECT_EQ(2, observer.discovering_changed_count_);
1305  EXPECT_FALSE(observer.last_discovering_);
1306  EXPECT_FALSE(adapter_->IsDiscovering());
1307  EXPECT_TRUE(discovery_sessions_[2]->IsActive());
1308
1309  // Request to start should get queued.
1310  adapter_->StartDiscoverySession(
1311    base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1312               base::Unretained(this)),
1313    base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1314               base::Unretained(this)));
1315  EXPECT_EQ(5, callback_count_);
1316  EXPECT_EQ(1, error_callback_count_);
1317  EXPECT_EQ(2, observer.discovering_changed_count_);
1318  EXPECT_FALSE(observer.last_discovering_);
1319  EXPECT_FALSE(adapter_->IsDiscovering());
1320  ASSERT_EQ((size_t)3, discovery_sessions_.size());
1321
1322  // Run the pending request.
1323  message_loop_.Run();
1324  EXPECT_EQ(6, callback_count_);
1325  EXPECT_EQ(1, error_callback_count_);
1326  EXPECT_EQ(3, observer.discovering_changed_count_);
1327  EXPECT_TRUE(observer.last_discovering_);
1328  EXPECT_TRUE(adapter_->IsDiscovering());
1329  ASSERT_EQ((size_t)3, discovery_sessions_.size());
1330  EXPECT_FALSE(discovery_sessions_[2]->IsActive());
1331
1332  // The queued request to start discovery should have been issued but is still
1333  // pending. Run the loop and verify.
1334  message_loop_.Run();
1335  EXPECT_EQ(7, callback_count_);
1336  EXPECT_EQ(1, error_callback_count_);
1337  EXPECT_EQ(3, observer.discovering_changed_count_);
1338  EXPECT_TRUE(observer.last_discovering_);
1339  EXPECT_TRUE(adapter_->IsDiscovering());
1340  ASSERT_EQ((size_t)4, discovery_sessions_.size());
1341  EXPECT_TRUE(discovery_sessions_[3]->IsActive());
1342}
1343
1344TEST_F(BluetoothChromeOSTest, StartDiscoverySession) {
1345  GetAdapter();
1346
1347  adapter_->SetPowered(
1348      true,
1349      base::Bind(&BluetoothChromeOSTest::Callback,
1350                 base::Unretained(this)),
1351      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1352                 base::Unretained(this)));
1353  EXPECT_EQ(1, callback_count_);
1354  EXPECT_EQ(0, error_callback_count_);
1355  EXPECT_TRUE(adapter_->IsPowered());
1356  callback_count_ = 0;
1357
1358  TestObserver observer(adapter_);
1359
1360  EXPECT_EQ(0, observer.discovering_changed_count_);
1361  EXPECT_FALSE(observer.last_discovering_);
1362  EXPECT_FALSE(adapter_->IsDiscovering());
1363  EXPECT_TRUE(discovery_sessions_.empty());
1364
1365  // Request a new discovery session.
1366  adapter_->StartDiscoverySession(
1367      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1368                 base::Unretained(this)),
1369      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1370                 base::Unretained(this)));
1371  message_loop_.Run();
1372  EXPECT_EQ(1, observer.discovering_changed_count_);
1373  EXPECT_EQ(1, callback_count_);
1374  EXPECT_EQ(0, error_callback_count_);
1375  EXPECT_TRUE(observer.last_discovering_);
1376  EXPECT_TRUE(adapter_->IsDiscovering());
1377  ASSERT_EQ((size_t)1, discovery_sessions_.size());
1378  EXPECT_TRUE(discovery_sessions_[0]->IsActive());
1379
1380  // Start another session. A new one should be returned in the callback, which
1381  // in turn will destroy the previous session. Adapter should still be
1382  // discovering and the reference count should be 1.
1383  adapter_->StartDiscoverySession(
1384      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1385                 base::Unretained(this)),
1386      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1387                 base::Unretained(this)));
1388  message_loop_.Run();
1389  EXPECT_EQ(1, observer.discovering_changed_count_);
1390  EXPECT_EQ(2, callback_count_);
1391  EXPECT_EQ(0, error_callback_count_);
1392  EXPECT_TRUE(observer.last_discovering_);
1393  EXPECT_TRUE(adapter_->IsDiscovering());
1394  ASSERT_EQ((size_t)2, discovery_sessions_.size());
1395  EXPECT_TRUE(discovery_sessions_[0]->IsActive());
1396
1397  // Request a new session.
1398  adapter_->StartDiscoverySession(
1399      base::Bind(&BluetoothChromeOSTest::DiscoverySessionCallback,
1400                 base::Unretained(this)),
1401      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1402                 base::Unretained(this)));
1403  message_loop_.Run();
1404  EXPECT_EQ(1, observer.discovering_changed_count_);
1405  EXPECT_EQ(3, callback_count_);
1406  EXPECT_EQ(0, error_callback_count_);
1407  EXPECT_TRUE(observer.last_discovering_);
1408  EXPECT_TRUE(adapter_->IsDiscovering());
1409  ASSERT_EQ((size_t)3, discovery_sessions_.size());
1410  EXPECT_TRUE(discovery_sessions_[1]->IsActive());
1411  EXPECT_NE(discovery_sessions_[0], discovery_sessions_[1]);
1412
1413  // Stop the previous discovery session. The session should end but discovery
1414  // should continue.
1415  discovery_sessions_[0]->Stop(
1416      base::Bind(&BluetoothChromeOSTest::Callback,
1417                 base::Unretained(this)),
1418      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1419                 base::Unretained(this)));
1420  message_loop_.Run();
1421  EXPECT_EQ(1, observer.discovering_changed_count_);
1422  EXPECT_EQ(4, callback_count_);
1423  EXPECT_EQ(0, error_callback_count_);
1424  EXPECT_TRUE(observer.last_discovering_);
1425  EXPECT_TRUE(adapter_->IsDiscovering());
1426  ASSERT_EQ((size_t)3, discovery_sessions_.size());
1427  EXPECT_FALSE(discovery_sessions_[0]->IsActive());
1428  EXPECT_TRUE(discovery_sessions_[1]->IsActive());
1429
1430  // Delete the current active session. Discovery should eventually stop.
1431  discovery_sessions_.clear();
1432  while (observer.last_discovering_)
1433    message_loop_.RunUntilIdle();
1434
1435  EXPECT_EQ(2, observer.discovering_changed_count_);
1436  EXPECT_EQ(4, callback_count_);
1437  EXPECT_EQ(0, error_callback_count_);
1438  EXPECT_FALSE(observer.last_discovering_);
1439  EXPECT_FALSE(adapter_->IsDiscovering());
1440}
1441
1442TEST_F(BluetoothChromeOSTest, DeviceProperties) {
1443  GetAdapter();
1444
1445  BluetoothAdapter::DeviceList devices = adapter_->GetDevices();
1446  ASSERT_EQ(1U, devices.size());
1447  ASSERT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
1448            devices[0]->GetAddress());
1449
1450  // Verify the other device properties.
1451  EXPECT_EQ(base::UTF8ToUTF16(FakeBluetoothDeviceClient::kPairedDeviceName),
1452            devices[0]->GetName());
1453  EXPECT_EQ(BluetoothDevice::DEVICE_COMPUTER, devices[0]->GetDeviceType());
1454  EXPECT_TRUE(devices[0]->IsPaired());
1455  EXPECT_FALSE(devices[0]->IsConnected());
1456  EXPECT_FALSE(devices[0]->IsConnecting());
1457
1458  // Non HID devices are always connectable.
1459  EXPECT_TRUE(devices[0]->IsConnectable());
1460
1461  BluetoothDevice::UUIDList uuids = devices[0]->GetUUIDs();
1462  ASSERT_EQ(2U, uuids.size());
1463  EXPECT_EQ(uuids[0], BluetoothUUID("1800"));
1464  EXPECT_EQ(uuids[1], BluetoothUUID("1801"));
1465
1466  EXPECT_EQ(BluetoothDevice::VENDOR_ID_USB, devices[0]->GetVendorIDSource());
1467  EXPECT_EQ(0x05ac, devices[0]->GetVendorID());
1468  EXPECT_EQ(0x030d, devices[0]->GetProductID());
1469  EXPECT_EQ(0x0306, devices[0]->GetDeviceID());
1470}
1471
1472TEST_F(BluetoothChromeOSTest, DeviceClassChanged) {
1473  // Simulate a change of class of a device, as sometimes occurs
1474  // during discovery.
1475  GetAdapter();
1476
1477  BluetoothAdapter::DeviceList devices = adapter_->GetDevices();
1478  ASSERT_EQ(1U, devices.size());
1479  ASSERT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
1480            devices[0]->GetAddress());
1481  ASSERT_EQ(BluetoothDevice::DEVICE_COMPUTER, devices[0]->GetDeviceType());
1482
1483  // Install an observer; expect the DeviceChanged method to be called when
1484  // we change the class of the device.
1485  TestObserver observer(adapter_);
1486
1487  FakeBluetoothDeviceClient::Properties* properties =
1488      fake_bluetooth_device_client_->GetProperties(
1489          dbus::ObjectPath(FakeBluetoothDeviceClient::kPairedDevicePath));
1490
1491  properties->bluetooth_class.ReplaceValue(0x002580);
1492
1493  EXPECT_EQ(1, observer.device_changed_count_);
1494  EXPECT_EQ(devices[0], observer.last_device_);
1495
1496  EXPECT_EQ(BluetoothDevice::DEVICE_MOUSE, devices[0]->GetDeviceType());
1497}
1498
1499TEST_F(BluetoothChromeOSTest, DeviceNameChanged) {
1500  // Simulate a change of name of a device.
1501  GetAdapter();
1502
1503  BluetoothAdapter::DeviceList devices = adapter_->GetDevices();
1504  ASSERT_EQ(1U, devices.size());
1505  ASSERT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
1506            devices[0]->GetAddress());
1507  ASSERT_EQ(base::UTF8ToUTF16(FakeBluetoothDeviceClient::kPairedDeviceName),
1508            devices[0]->GetName());
1509
1510  // Install an observer; expect the DeviceChanged method to be called when
1511  // we change the alias of the device.
1512  TestObserver observer(adapter_);
1513
1514  FakeBluetoothDeviceClient::Properties* properties =
1515      fake_bluetooth_device_client_->GetProperties(
1516          dbus::ObjectPath(FakeBluetoothDeviceClient::kPairedDevicePath));
1517
1518  static const std::string new_name("New Device Name");
1519  properties->alias.ReplaceValue(new_name);
1520
1521  EXPECT_EQ(1, observer.device_changed_count_);
1522  EXPECT_EQ(devices[0], observer.last_device_);
1523
1524  EXPECT_EQ(base::UTF8ToUTF16(new_name), devices[0]->GetName());
1525}
1526
1527TEST_F(BluetoothChromeOSTest, DeviceUuidsChanged) {
1528  // Simulate a change of advertised services of a device.
1529  GetAdapter();
1530
1531  BluetoothAdapter::DeviceList devices = adapter_->GetDevices();
1532  ASSERT_EQ(1U, devices.size());
1533  ASSERT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
1534            devices[0]->GetAddress());
1535
1536  BluetoothDevice::UUIDList uuids = devices[0]->GetUUIDs();
1537  ASSERT_EQ(2U, uuids.size());
1538  ASSERT_EQ(uuids[0], BluetoothUUID("1800"));
1539  ASSERT_EQ(uuids[1], BluetoothUUID("1801"));
1540
1541  // Install an observer; expect the DeviceChanged method to be called when
1542  // we change the class of the device.
1543  TestObserver observer(adapter_);
1544
1545  FakeBluetoothDeviceClient::Properties* properties =
1546      fake_bluetooth_device_client_->GetProperties(
1547          dbus::ObjectPath(FakeBluetoothDeviceClient::kPairedDevicePath));
1548
1549  std::vector<std::string> new_uuids;
1550  new_uuids.push_back(uuids[0].canonical_value());
1551  new_uuids.push_back(uuids[1].canonical_value());
1552  new_uuids.push_back("0000110c-0000-1000-8000-00805f9b34fb");
1553  new_uuids.push_back("0000110e-0000-1000-8000-00805f9b34fb");
1554  new_uuids.push_back("0000110a-0000-1000-8000-00805f9b34fb");
1555
1556  properties->uuids.ReplaceValue(new_uuids);
1557
1558  EXPECT_EQ(1, observer.device_changed_count_);
1559  EXPECT_EQ(devices[0], observer.last_device_);
1560
1561  // Fetching the value should give the new one.
1562  uuids = devices[0]->GetUUIDs();
1563  ASSERT_EQ(5U, uuids.size());
1564  EXPECT_EQ(uuids[0], BluetoothUUID("1800"));
1565  EXPECT_EQ(uuids[1], BluetoothUUID("1801"));
1566  EXPECT_EQ(uuids[2], BluetoothUUID("110c"));
1567  EXPECT_EQ(uuids[3], BluetoothUUID("110e"));
1568  EXPECT_EQ(uuids[4], BluetoothUUID("110a"));
1569}
1570
1571TEST_F(BluetoothChromeOSTest, ForgetDevice) {
1572  GetAdapter();
1573
1574  BluetoothAdapter::DeviceList devices = adapter_->GetDevices();
1575  ASSERT_EQ(1U, devices.size());
1576  ASSERT_EQ(FakeBluetoothDeviceClient::kPairedDeviceAddress,
1577            devices[0]->GetAddress());
1578
1579  std::string address = devices[0]->GetAddress();
1580
1581  // Install an observer; expect the DeviceRemoved method to be called
1582  // with the device we remove.
1583  TestObserver observer(adapter_);
1584
1585  devices[0]->Forget(
1586      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1587                 base::Unretained(this)));
1588  EXPECT_EQ(0, error_callback_count_);
1589
1590  EXPECT_EQ(1, observer.device_removed_count_);
1591  EXPECT_EQ(address, observer.last_device_address_);
1592
1593  // GetDevices shouldn't return the device either.
1594  devices = adapter_->GetDevices();
1595  ASSERT_EQ(0U, devices.size());
1596}
1597
1598TEST_F(BluetoothChromeOSTest, ForgetUnpairedDevice) {
1599  GetAdapter();
1600  DiscoverDevices();
1601
1602  BluetoothDevice* device = adapter_->GetDevice(
1603      FakeBluetoothDeviceClient::kConnectUnpairableAddress);
1604  ASSERT_TRUE(device != NULL);
1605  ASSERT_FALSE(device->IsPaired());
1606
1607  // Connect the device so it becomes trusted and remembered.
1608  device->Connect(
1609      NULL,
1610      base::Bind(&BluetoothChromeOSTest::Callback,
1611                 base::Unretained(this)),
1612      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1613                 base::Unretained(this)));
1614
1615  ASSERT_EQ(1, callback_count_);
1616  ASSERT_EQ(0, error_callback_count_);
1617  callback_count_ = 0;
1618
1619  ASSERT_TRUE(device->IsConnected());
1620  ASSERT_FALSE(device->IsConnecting());
1621
1622  // Make sure the trusted property has been set to true.
1623  FakeBluetoothDeviceClient::Properties* properties =
1624      fake_bluetooth_device_client_->GetProperties(
1625          dbus::ObjectPath(FakeBluetoothDeviceClient::kConnectUnpairablePath));
1626  ASSERT_TRUE(properties->trusted.value());
1627
1628  // Install an observer; expect the DeviceRemoved method to be called
1629  // with the device we remove.
1630  TestObserver observer(adapter_);
1631
1632  device->Forget(
1633      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1634                 base::Unretained(this)));
1635  EXPECT_EQ(0, error_callback_count_);
1636
1637  EXPECT_EQ(1, observer.device_removed_count_);
1638  EXPECT_EQ(FakeBluetoothDeviceClient::kConnectUnpairableAddress,
1639            observer.last_device_address_);
1640
1641  // GetDevices shouldn't return the device either.
1642  device = adapter_->GetDevice(
1643      FakeBluetoothDeviceClient::kConnectUnpairableAddress);
1644  EXPECT_FALSE(device != NULL);
1645}
1646
1647TEST_F(BluetoothChromeOSTest, ConnectPairedDevice) {
1648  GetAdapter();
1649
1650  BluetoothDevice* device = adapter_->GetDevice(
1651      FakeBluetoothDeviceClient::kPairedDeviceAddress);
1652  ASSERT_TRUE(device != NULL);
1653  ASSERT_TRUE(device->IsPaired());
1654
1655  TestObserver observer(adapter_);
1656
1657  // Connect without a pairing delegate; since the device is already Paired
1658  // this should succeed and the device should become connected.
1659  device->Connect(
1660      NULL,
1661      base::Bind(&BluetoothChromeOSTest::Callback,
1662                 base::Unretained(this)),
1663      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1664                 base::Unretained(this)));
1665
1666  EXPECT_EQ(1, callback_count_);
1667  EXPECT_EQ(0, error_callback_count_);
1668
1669  // Two changes for connecting, one for connected and one for for trusted
1670  // after connecting.
1671  EXPECT_EQ(4, observer.device_changed_count_);
1672  EXPECT_EQ(device, observer.last_device_);
1673
1674  EXPECT_TRUE(device->IsConnected());
1675  EXPECT_FALSE(device->IsConnecting());
1676}
1677
1678TEST_F(BluetoothChromeOSTest, ConnectUnpairableDevice) {
1679  GetAdapter();
1680  DiscoverDevices();
1681
1682  BluetoothDevice* device = adapter_->GetDevice(
1683      FakeBluetoothDeviceClient::kConnectUnpairableAddress);
1684  ASSERT_TRUE(device != NULL);
1685  ASSERT_FALSE(device->IsPaired());
1686
1687  TestObserver observer(adapter_);
1688
1689  // Connect without a pairing delegate; since the device does not require
1690  // pairing, this should succeed and the device should become connected.
1691  device->Connect(
1692      NULL,
1693      base::Bind(&BluetoothChromeOSTest::Callback,
1694                 base::Unretained(this)),
1695      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1696                 base::Unretained(this)));
1697
1698  EXPECT_EQ(1, callback_count_);
1699  EXPECT_EQ(0, error_callback_count_);
1700
1701  // Two changes for connecting, one for connected, one for for trusted after
1702  // connection, and one for the reconnect mode (IsConnectable).
1703  EXPECT_EQ(5, observer.device_changed_count_);
1704  EXPECT_EQ(device, observer.last_device_);
1705
1706  EXPECT_TRUE(device->IsConnected());
1707  EXPECT_FALSE(device->IsConnecting());
1708
1709  // Make sure the trusted property has been set to true.
1710  FakeBluetoothDeviceClient::Properties* properties =
1711      fake_bluetooth_device_client_->GetProperties(
1712          dbus::ObjectPath(FakeBluetoothDeviceClient::kConnectUnpairablePath));
1713  EXPECT_TRUE(properties->trusted.value());
1714
1715  // Verify is a HID device and is not connectable.
1716  BluetoothDevice::UUIDList uuids = device->GetUUIDs();
1717  ASSERT_EQ(1U, uuids.size());
1718  EXPECT_EQ(uuids[0], BluetoothUUID("1124"));
1719  EXPECT_FALSE(device->IsConnectable());
1720}
1721
1722TEST_F(BluetoothChromeOSTest, ConnectConnectedDevice) {
1723  GetAdapter();
1724
1725  BluetoothDevice* device = adapter_->GetDevice(
1726      FakeBluetoothDeviceClient::kPairedDeviceAddress);
1727  ASSERT_TRUE(device != NULL);
1728  ASSERT_TRUE(device->IsPaired());
1729
1730  device->Connect(
1731      NULL,
1732      base::Bind(&BluetoothChromeOSTest::Callback,
1733                 base::Unretained(this)),
1734      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1735                 base::Unretained(this)));
1736
1737  ASSERT_EQ(1, callback_count_);
1738  ASSERT_EQ(0, error_callback_count_);
1739  callback_count_ = 0;
1740
1741  ASSERT_TRUE(device->IsConnected());
1742
1743  // Connect again; since the device is already Connected, this shouldn't do
1744  // anything to initiate the connection.
1745  TestObserver observer(adapter_);
1746
1747  device->Connect(
1748      NULL,
1749      base::Bind(&BluetoothChromeOSTest::Callback,
1750                 base::Unretained(this)),
1751      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1752                 base::Unretained(this)));
1753
1754  EXPECT_EQ(1, callback_count_);
1755  EXPECT_EQ(0, error_callback_count_);
1756
1757  // The observer will be called because Connecting will toggle true and false,
1758  // and the trusted property will be updated to true.
1759  EXPECT_EQ(3, observer.device_changed_count_);
1760
1761  EXPECT_TRUE(device->IsConnected());
1762  EXPECT_FALSE(device->IsConnecting());
1763}
1764
1765TEST_F(BluetoothChromeOSTest, ConnectDeviceFails) {
1766  GetAdapter();
1767  DiscoverDevices();
1768
1769  BluetoothDevice* device = adapter_->GetDevice(
1770      FakeBluetoothDeviceClient::kLegacyAutopairAddress);
1771  ASSERT_TRUE(device != NULL);
1772  ASSERT_FALSE(device->IsPaired());
1773
1774  TestObserver observer(adapter_);
1775
1776  // Connect without a pairing delegate; since the device requires pairing,
1777  // this should fail with an error.
1778  device->Connect(
1779      NULL,
1780      base::Bind(&BluetoothChromeOSTest::Callback,
1781                 base::Unretained(this)),
1782      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1783                 base::Unretained(this)));
1784
1785  EXPECT_EQ(0, callback_count_);
1786  EXPECT_EQ(1, error_callback_count_);
1787  EXPECT_EQ(BluetoothDevice::ERROR_FAILED, last_connect_error_);
1788
1789  EXPECT_EQ(2, observer.device_changed_count_);
1790
1791  EXPECT_FALSE(device->IsConnected());
1792  EXPECT_FALSE(device->IsConnecting());
1793}
1794
1795TEST_F(BluetoothChromeOSTest, DisconnectDevice) {
1796  GetAdapter();
1797
1798  BluetoothDevice* device = adapter_->GetDevice(
1799      FakeBluetoothDeviceClient::kPairedDeviceAddress);
1800  ASSERT_TRUE(device != NULL);
1801  ASSERT_TRUE(device->IsPaired());
1802
1803  device->Connect(
1804      NULL,
1805      base::Bind(&BluetoothChromeOSTest::Callback,
1806                 base::Unretained(this)),
1807      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1808                 base::Unretained(this)));
1809
1810  ASSERT_EQ(1, callback_count_);
1811  ASSERT_EQ(0, error_callback_count_);
1812  callback_count_ = 0;
1813
1814  ASSERT_TRUE(device->IsConnected());
1815  ASSERT_FALSE(device->IsConnecting());
1816
1817  // Disconnect the device, we should see the observer method fire and the
1818  // device get dropped.
1819  TestObserver observer(adapter_);
1820
1821  device->Disconnect(
1822      base::Bind(&BluetoothChromeOSTest::Callback,
1823                 base::Unretained(this)),
1824      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1825                 base::Unretained(this)));
1826
1827  EXPECT_EQ(1, callback_count_);
1828  EXPECT_EQ(0, error_callback_count_);
1829
1830  EXPECT_EQ(1, observer.device_changed_count_);
1831  EXPECT_EQ(device, observer.last_device_);
1832
1833  EXPECT_FALSE(device->IsConnected());
1834}
1835
1836TEST_F(BluetoothChromeOSTest, DisconnectUnconnectedDevice) {
1837  GetAdapter();
1838
1839  BluetoothDevice* device = adapter_->GetDevice(
1840      FakeBluetoothDeviceClient::kPairedDeviceAddress);
1841  ASSERT_TRUE(device != NULL);
1842  ASSERT_TRUE(device->IsPaired());
1843  ASSERT_FALSE(device->IsConnected());
1844
1845  // Disconnect the device, we should see the observer method fire and the
1846  // device get dropped.
1847  TestObserver observer(adapter_);
1848
1849  device->Disconnect(
1850      base::Bind(&BluetoothChromeOSTest::Callback,
1851                 base::Unretained(this)),
1852      base::Bind(&BluetoothChromeOSTest::ErrorCallback,
1853                 base::Unretained(this)));
1854
1855  EXPECT_EQ(0, callback_count_);
1856  EXPECT_EQ(1, error_callback_count_);
1857
1858  EXPECT_EQ(0, observer.device_changed_count_);
1859
1860  EXPECT_FALSE(device->IsConnected());
1861}
1862
1863TEST_F(BluetoothChromeOSTest, PairLegacyAutopair) {
1864  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
1865
1866  GetAdapter();
1867  DiscoverDevices();
1868
1869  // The Legacy Autopair device requires no PIN or Passkey to pair because
1870  // the daemon provides 0000 to the device for us.
1871  BluetoothDevice* device = adapter_->GetDevice(
1872      FakeBluetoothDeviceClient::kLegacyAutopairAddress);
1873  ASSERT_TRUE(device != NULL);
1874  ASSERT_FALSE(device->IsPaired());
1875
1876  TestObserver observer(adapter_);
1877
1878  TestPairingDelegate pairing_delegate;
1879  device->Connect(
1880      &pairing_delegate,
1881      base::Bind(&BluetoothChromeOSTest::Callback,
1882                 base::Unretained(this)),
1883      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1884                 base::Unretained(this)));
1885
1886  EXPECT_EQ(0, pairing_delegate.call_count_);
1887  EXPECT_TRUE(device->IsConnecting());
1888
1889  message_loop_.Run();
1890
1891  EXPECT_EQ(1, callback_count_);
1892  EXPECT_EQ(0, error_callback_count_);
1893
1894  // Two changes for connecting, one change for connected, one for paired,
1895  // two for trusted (after pairing and connection), and one for the reconnect
1896  // mode (IsConnectable).
1897  EXPECT_EQ(7, observer.device_changed_count_);
1898  EXPECT_EQ(device, observer.last_device_);
1899
1900  EXPECT_TRUE(device->IsConnected());
1901  EXPECT_FALSE(device->IsConnecting());
1902
1903  EXPECT_TRUE(device->IsPaired());
1904
1905  // Verify is a HID device and is connectable.
1906  BluetoothDevice::UUIDList uuids = device->GetUUIDs();
1907  ASSERT_EQ(1U, uuids.size());
1908  EXPECT_EQ(uuids[0], BluetoothUUID("1124"));
1909  EXPECT_TRUE(device->IsConnectable());
1910
1911  // Make sure the trusted property has been set to true.
1912  FakeBluetoothDeviceClient::Properties* properties =
1913      fake_bluetooth_device_client_->GetProperties(
1914          dbus::ObjectPath(FakeBluetoothDeviceClient::kLegacyAutopairPath));
1915  EXPECT_TRUE(properties->trusted.value());
1916}
1917
1918TEST_F(BluetoothChromeOSTest, PairDisplayPinCode) {
1919  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
1920
1921  GetAdapter();
1922  DiscoverDevices();
1923
1924  // Requires that we display a randomly generated PIN on the screen.
1925  BluetoothDevice* device = adapter_->GetDevice(
1926      FakeBluetoothDeviceClient::kDisplayPinCodeAddress);
1927  ASSERT_TRUE(device != NULL);
1928  ASSERT_FALSE(device->IsPaired());
1929
1930  TestObserver observer(adapter_);
1931
1932  TestPairingDelegate pairing_delegate;
1933  device->Connect(
1934      &pairing_delegate,
1935      base::Bind(&BluetoothChromeOSTest::Callback,
1936                 base::Unretained(this)),
1937      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1938                 base::Unretained(this)));
1939
1940  EXPECT_EQ(1, pairing_delegate.call_count_);
1941  EXPECT_EQ(1, pairing_delegate.display_pincode_count_);
1942  EXPECT_EQ("123456", pairing_delegate.last_pincode_);
1943  EXPECT_TRUE(device->IsConnecting());
1944
1945  message_loop_.Run();
1946
1947  EXPECT_EQ(1, callback_count_);
1948  EXPECT_EQ(0, error_callback_count_);
1949
1950  // Two changes for connecting, one change for connected, one for paired,
1951  // two for trusted (after pairing and connection), and one for the reconnect
1952  // mode (IsConnectable).
1953  EXPECT_EQ(7, observer.device_changed_count_);
1954  EXPECT_EQ(device, observer.last_device_);
1955
1956  EXPECT_TRUE(device->IsConnected());
1957  EXPECT_FALSE(device->IsConnecting());
1958
1959  EXPECT_TRUE(device->IsPaired());
1960
1961  // Verify is a HID device and is connectable.
1962  BluetoothDevice::UUIDList uuids = device->GetUUIDs();
1963  ASSERT_EQ(1U, uuids.size());
1964  EXPECT_EQ(uuids[0], BluetoothUUID("1124"));
1965  EXPECT_TRUE(device->IsConnectable());
1966
1967  // Make sure the trusted property has been set to true.
1968  FakeBluetoothDeviceClient::Properties* properties =
1969      fake_bluetooth_device_client_->GetProperties(
1970          dbus::ObjectPath(FakeBluetoothDeviceClient::kDisplayPinCodePath));
1971  EXPECT_TRUE(properties->trusted.value());
1972}
1973
1974TEST_F(BluetoothChromeOSTest, PairDisplayPasskey) {
1975  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
1976
1977  GetAdapter();
1978  DiscoverDevices();
1979
1980  // Requires that we display a randomly generated Passkey on the screen,
1981  // and notifies us as it's typed in.
1982  BluetoothDevice* device = adapter_->GetDevice(
1983      FakeBluetoothDeviceClient::kDisplayPasskeyAddress);
1984  ASSERT_TRUE(device != NULL);
1985  ASSERT_FALSE(device->IsPaired());
1986
1987  TestObserver observer(adapter_);
1988
1989  TestPairingDelegate pairing_delegate;
1990  device->Connect(
1991      &pairing_delegate,
1992      base::Bind(&BluetoothChromeOSTest::Callback,
1993                 base::Unretained(this)),
1994      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
1995                 base::Unretained(this)));
1996
1997  // One call for DisplayPasskey() and one for KeysEntered().
1998  EXPECT_EQ(2, pairing_delegate.call_count_);
1999  EXPECT_EQ(1, pairing_delegate.display_passkey_count_);
2000  EXPECT_EQ(123456U, pairing_delegate.last_passkey_);
2001  EXPECT_EQ(1, pairing_delegate.keys_entered_count_);
2002  EXPECT_EQ(0U, pairing_delegate.last_entered_);
2003
2004  EXPECT_TRUE(device->IsConnecting());
2005
2006  // One call to KeysEntered() for each key, including [enter].
2007  for(int i = 1; i <= 7; ++i) {
2008    message_loop_.Run();
2009
2010    EXPECT_EQ(2 + i, pairing_delegate.call_count_);
2011    EXPECT_EQ(1 + i, pairing_delegate.keys_entered_count_);
2012    EXPECT_EQ(static_cast<uint32_t>(i), pairing_delegate.last_entered_);
2013  }
2014
2015  message_loop_.Run();
2016
2017  // 8 KeysEntered notifications (0 to 7, inclusive) and one aditional call for
2018  // DisplayPasskey().
2019  EXPECT_EQ(9, pairing_delegate.call_count_);
2020  EXPECT_EQ(8, pairing_delegate.keys_entered_count_);
2021  EXPECT_EQ(7U, pairing_delegate.last_entered_);
2022
2023  EXPECT_EQ(1, callback_count_);
2024  EXPECT_EQ(0, error_callback_count_);
2025
2026  // Two changes for connecting, one change for connected, one for paired,
2027  // two for trusted (after pairing and connection), and one for the reconnect
2028  // mode (IsConnectable).
2029  EXPECT_EQ(7, observer.device_changed_count_);
2030  EXPECT_EQ(device, observer.last_device_);
2031
2032  EXPECT_TRUE(device->IsConnected());
2033  EXPECT_FALSE(device->IsConnecting());
2034
2035  EXPECT_TRUE(device->IsPaired());
2036
2037  // Verify is a HID device.
2038  BluetoothDevice::UUIDList uuids = device->GetUUIDs();
2039  ASSERT_EQ(1U, uuids.size());
2040  EXPECT_EQ(uuids[0], BluetoothUUID("1124"));
2041
2042  // And usually not connectable.
2043  EXPECT_FALSE(device->IsConnectable());
2044
2045  // Make sure the trusted property has been set to true.
2046  FakeBluetoothDeviceClient::Properties* properties =
2047      fake_bluetooth_device_client_->GetProperties(
2048          dbus::ObjectPath(FakeBluetoothDeviceClient::kDisplayPasskeyPath));
2049  EXPECT_TRUE(properties->trusted.value());
2050}
2051
2052TEST_F(BluetoothChromeOSTest, PairRequestPinCode) {
2053  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2054
2055  GetAdapter();
2056  DiscoverDevices();
2057
2058  // Requires that the user enters a PIN for them.
2059  BluetoothDevice* device = adapter_->GetDevice(
2060      FakeBluetoothDeviceClient::kRequestPinCodeAddress);
2061  ASSERT_TRUE(device != NULL);
2062  ASSERT_FALSE(device->IsPaired());
2063
2064  TestObserver observer(adapter_);
2065
2066  TestPairingDelegate pairing_delegate;
2067  device->Connect(
2068      &pairing_delegate,
2069      base::Bind(&BluetoothChromeOSTest::Callback,
2070                 base::Unretained(this)),
2071      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2072                 base::Unretained(this)));
2073
2074  EXPECT_EQ(1, pairing_delegate.call_count_);
2075  EXPECT_EQ(1, pairing_delegate.request_pincode_count_);
2076  EXPECT_TRUE(device->IsConnecting());
2077
2078  // Set the PIN.
2079  device->SetPinCode("1234");
2080  message_loop_.Run();
2081
2082  EXPECT_EQ(1, callback_count_);
2083  EXPECT_EQ(0, error_callback_count_);
2084
2085  // Two changes for connecting, one change for connected, one for paired and
2086  // two for trusted (after pairing and connection).
2087  EXPECT_EQ(6, observer.device_changed_count_);
2088  EXPECT_EQ(device, observer.last_device_);
2089
2090  EXPECT_TRUE(device->IsConnected());
2091  EXPECT_FALSE(device->IsConnecting());
2092
2093  EXPECT_TRUE(device->IsPaired());
2094
2095  // Verify is not a HID device.
2096  BluetoothDevice::UUIDList uuids = device->GetUUIDs();
2097  ASSERT_EQ(0U, uuids.size());
2098
2099  // Non HID devices are always connectable.
2100  EXPECT_TRUE(device->IsConnectable());
2101
2102  // Make sure the trusted property has been set to true.
2103  FakeBluetoothDeviceClient::Properties* properties =
2104      fake_bluetooth_device_client_->GetProperties(
2105          dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPinCodePath));
2106  EXPECT_TRUE(properties->trusted.value());
2107}
2108
2109TEST_F(BluetoothChromeOSTest, PairConfirmPasskey) {
2110  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2111
2112  GetAdapter();
2113  DiscoverDevices();
2114
2115  // Requests that we confirm a displayed passkey.
2116  BluetoothDevice* device = adapter_->GetDevice(
2117      FakeBluetoothDeviceClient::kConfirmPasskeyAddress);
2118  ASSERT_TRUE(device != NULL);
2119  ASSERT_FALSE(device->IsPaired());
2120
2121  TestObserver observer(adapter_);
2122
2123  TestPairingDelegate pairing_delegate;
2124  device->Connect(
2125      &pairing_delegate,
2126      base::Bind(&BluetoothChromeOSTest::Callback,
2127                 base::Unretained(this)),
2128      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2129                 base::Unretained(this)));
2130
2131  EXPECT_EQ(1, pairing_delegate.call_count_);
2132  EXPECT_EQ(1, pairing_delegate.confirm_passkey_count_);
2133  EXPECT_EQ(123456U, pairing_delegate.last_passkey_);
2134  EXPECT_TRUE(device->IsConnecting());
2135
2136  // Confirm the passkey.
2137  device->ConfirmPairing();
2138  message_loop_.Run();
2139
2140  EXPECT_EQ(1, callback_count_);
2141  EXPECT_EQ(0, error_callback_count_);
2142
2143  // Two changes for connecting, one change for connected, one for paired and
2144  // two for trusted (after pairing and connection).
2145  EXPECT_EQ(6, observer.device_changed_count_);
2146  EXPECT_EQ(device, observer.last_device_);
2147
2148  EXPECT_TRUE(device->IsConnected());
2149  EXPECT_FALSE(device->IsConnecting());
2150
2151  EXPECT_TRUE(device->IsPaired());
2152
2153  // Non HID devices are always connectable.
2154  EXPECT_TRUE(device->IsConnectable());
2155
2156  // Make sure the trusted property has been set to true.
2157  FakeBluetoothDeviceClient::Properties* properties =
2158      fake_bluetooth_device_client_->GetProperties(
2159          dbus::ObjectPath(FakeBluetoothDeviceClient::kConfirmPasskeyPath));
2160  EXPECT_TRUE(properties->trusted.value());
2161}
2162
2163TEST_F(BluetoothChromeOSTest, PairRequestPasskey) {
2164  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2165
2166  GetAdapter();
2167  DiscoverDevices();
2168
2169  // Requires that the user enters a Passkey, this would be some kind of
2170  // device that has a display, but doesn't use "just works" - maybe a car?
2171  BluetoothDevice* device = adapter_->GetDevice(
2172      FakeBluetoothDeviceClient::kRequestPasskeyAddress);
2173  ASSERT_TRUE(device != NULL);
2174  ASSERT_FALSE(device->IsPaired());
2175
2176  TestObserver observer(adapter_);
2177
2178  TestPairingDelegate pairing_delegate;
2179  device->Connect(
2180      &pairing_delegate,
2181      base::Bind(&BluetoothChromeOSTest::Callback,
2182                 base::Unretained(this)),
2183      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2184                 base::Unretained(this)));
2185
2186  EXPECT_EQ(1, pairing_delegate.call_count_);
2187  EXPECT_EQ(1, pairing_delegate.request_passkey_count_);
2188  EXPECT_TRUE(device->IsConnecting());
2189
2190  // Set the Passkey.
2191  device->SetPasskey(1234);
2192  message_loop_.Run();
2193
2194  EXPECT_EQ(1, callback_count_);
2195  EXPECT_EQ(0, error_callback_count_);
2196
2197  // Two changes for connecting, one change for connected, one for paired and
2198  // two for trusted (after pairing and connection).
2199  EXPECT_EQ(6, observer.device_changed_count_);
2200  EXPECT_EQ(device, observer.last_device_);
2201
2202  EXPECT_TRUE(device->IsConnected());
2203  EXPECT_FALSE(device->IsConnecting());
2204
2205  EXPECT_TRUE(device->IsPaired());
2206
2207  // Non HID devices are always connectable.
2208  EXPECT_TRUE(device->IsConnectable());
2209
2210  // Make sure the trusted property has been set to true.
2211  FakeBluetoothDeviceClient::Properties* properties =
2212      fake_bluetooth_device_client_->GetProperties(
2213          dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath));
2214  EXPECT_TRUE(properties->trusted.value());
2215}
2216
2217TEST_F(BluetoothChromeOSTest, PairJustWorks) {
2218  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2219
2220  GetAdapter();
2221  DiscoverDevices();
2222
2223  // Uses just-works pairing, since this is an outgoing pairing, no delegate
2224  // interaction is required.
2225  BluetoothDevice* device = adapter_->GetDevice(
2226      FakeBluetoothDeviceClient::kJustWorksAddress);
2227  ASSERT_TRUE(device != NULL);
2228  ASSERT_FALSE(device->IsPaired());
2229
2230  TestObserver observer(adapter_);
2231
2232  TestPairingDelegate pairing_delegate;
2233  device->Connect(
2234      &pairing_delegate,
2235      base::Bind(&BluetoothChromeOSTest::Callback,
2236                 base::Unretained(this)),
2237      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2238                 base::Unretained(this)));
2239
2240  EXPECT_EQ(0, pairing_delegate.call_count_);
2241
2242  message_loop_.Run();
2243
2244  EXPECT_EQ(1, callback_count_);
2245  EXPECT_EQ(0, error_callback_count_);
2246
2247  // Two changes for connecting, one change for connected, one for paired and
2248  // two for trusted (after pairing and connection).
2249  EXPECT_EQ(6, observer.device_changed_count_);
2250  EXPECT_EQ(device, observer.last_device_);
2251
2252  EXPECT_TRUE(device->IsConnected());
2253  EXPECT_FALSE(device->IsConnecting());
2254
2255  EXPECT_TRUE(device->IsPaired());
2256
2257  // Non HID devices are always connectable.
2258  EXPECT_TRUE(device->IsConnectable());
2259
2260  // Make sure the trusted property has been set to true.
2261  FakeBluetoothDeviceClient::Properties* properties =
2262      fake_bluetooth_device_client_->GetProperties(
2263          dbus::ObjectPath(FakeBluetoothDeviceClient::kJustWorksPath));
2264  EXPECT_TRUE(properties->trusted.value());
2265}
2266
2267TEST_F(BluetoothChromeOSTest, PairUnpairableDeviceFails) {
2268  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2269
2270  GetAdapter();
2271  DiscoverDevice(FakeBluetoothDeviceClient::kUnconnectableDeviceAddress);
2272
2273  BluetoothDevice* device = adapter_->GetDevice(
2274      FakeBluetoothDeviceClient::kUnpairableDeviceAddress);
2275  ASSERT_TRUE(device != NULL);
2276  ASSERT_FALSE(device->IsPaired());
2277
2278  TestObserver observer(adapter_);
2279
2280  TestPairingDelegate pairing_delegate;
2281  device->Connect(
2282      &pairing_delegate,
2283      base::Bind(&BluetoothChromeOSTest::Callback,
2284                 base::Unretained(this)),
2285      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2286                 base::Unretained(this)));
2287
2288  EXPECT_EQ(0, pairing_delegate.call_count_);
2289  EXPECT_TRUE(device->IsConnecting());
2290
2291  // Run the loop to get the error..
2292  message_loop_.Run();
2293
2294  EXPECT_EQ(0, callback_count_);
2295  EXPECT_EQ(1, error_callback_count_);
2296
2297  EXPECT_EQ(BluetoothDevice::ERROR_FAILED, last_connect_error_);
2298
2299  EXPECT_FALSE(device->IsConnected());
2300  EXPECT_FALSE(device->IsConnecting());
2301  EXPECT_FALSE(device->IsPaired());
2302}
2303
2304TEST_F(BluetoothChromeOSTest, PairingFails) {
2305  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2306
2307  GetAdapter();
2308  DiscoverDevice(FakeBluetoothDeviceClient::kVanishingDeviceAddress);
2309
2310  // The vanishing device times out during pairing
2311  BluetoothDevice* device = adapter_->GetDevice(
2312      FakeBluetoothDeviceClient::kVanishingDeviceAddress);
2313  ASSERT_TRUE(device != NULL);
2314  ASSERT_FALSE(device->IsPaired());
2315
2316  TestObserver observer(adapter_);
2317
2318  TestPairingDelegate pairing_delegate;
2319  device->Connect(
2320      &pairing_delegate,
2321      base::Bind(&BluetoothChromeOSTest::Callback,
2322                 base::Unretained(this)),
2323      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2324                 base::Unretained(this)));
2325
2326  EXPECT_EQ(0, pairing_delegate.call_count_);
2327  EXPECT_TRUE(device->IsConnecting());
2328
2329  // Run the loop to get the error..
2330  message_loop_.Run();
2331
2332  EXPECT_EQ(0, callback_count_);
2333  EXPECT_EQ(1, error_callback_count_);
2334
2335  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_TIMEOUT, last_connect_error_);
2336
2337  EXPECT_FALSE(device->IsConnected());
2338  EXPECT_FALSE(device->IsConnecting());
2339  EXPECT_FALSE(device->IsPaired());
2340}
2341
2342TEST_F(BluetoothChromeOSTest, PairingFailsAtConnection) {
2343  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2344
2345  GetAdapter();
2346  DiscoverDevices();
2347
2348  // Everything seems to go according to plan with the unconnectable device;
2349  // it pairs, but then you can't make connections to it after.
2350  BluetoothDevice* device = adapter_->GetDevice(
2351      FakeBluetoothDeviceClient::kUnconnectableDeviceAddress);
2352  ASSERT_TRUE(device != NULL);
2353  ASSERT_FALSE(device->IsPaired());
2354
2355  TestObserver observer(adapter_);
2356
2357  TestPairingDelegate pairing_delegate;
2358  device->Connect(
2359      &pairing_delegate,
2360      base::Bind(&BluetoothChromeOSTest::Callback,
2361                 base::Unretained(this)),
2362      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2363                 base::Unretained(this)));
2364
2365  EXPECT_EQ(0, pairing_delegate.call_count_);
2366  EXPECT_TRUE(device->IsConnecting());
2367
2368  message_loop_.Run();
2369
2370  EXPECT_EQ(0, callback_count_);
2371  EXPECT_EQ(1, error_callback_count_);
2372  EXPECT_EQ(BluetoothDevice::ERROR_FAILED, last_connect_error_);
2373
2374  // Two changes for connecting, one for paired and one for trusted after
2375  // pairing. The device should not be connected.
2376  EXPECT_EQ(4, observer.device_changed_count_);
2377  EXPECT_EQ(device, observer.last_device_);
2378
2379  EXPECT_FALSE(device->IsConnected());
2380  EXPECT_FALSE(device->IsConnecting());
2381
2382  EXPECT_TRUE(device->IsPaired());
2383
2384  // Make sure the trusted property has been set to true still (since pairing
2385  // worked).
2386  FakeBluetoothDeviceClient::Properties* properties =
2387      fake_bluetooth_device_client_->GetProperties(
2388          dbus::ObjectPath(
2389              FakeBluetoothDeviceClient::kUnconnectableDevicePath));
2390  EXPECT_TRUE(properties->trusted.value());
2391}
2392
2393TEST_F(BluetoothChromeOSTest, PairingRejectedAtPinCode) {
2394  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2395
2396  GetAdapter();
2397  DiscoverDevices();
2398
2399  // Reject the pairing after we receive a request for the PIN code.
2400  BluetoothDevice* device = adapter_->GetDevice(
2401      FakeBluetoothDeviceClient::kRequestPinCodeAddress);
2402  ASSERT_TRUE(device != NULL);
2403  ASSERT_FALSE(device->IsPaired());
2404
2405  TestObserver observer(adapter_);
2406
2407  TestPairingDelegate pairing_delegate;
2408  device->Connect(
2409      &pairing_delegate,
2410      base::Bind(&BluetoothChromeOSTest::Callback,
2411                 base::Unretained(this)),
2412      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2413                 base::Unretained(this)));
2414
2415  EXPECT_EQ(1, pairing_delegate.call_count_);
2416  EXPECT_EQ(1, pairing_delegate.request_pincode_count_);
2417  EXPECT_TRUE(device->IsConnecting());
2418
2419  // Reject the pairing.
2420  device->RejectPairing();
2421  message_loop_.Run();
2422
2423  EXPECT_EQ(0, callback_count_);
2424  EXPECT_EQ(1, error_callback_count_);
2425  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_REJECTED, last_connect_error_);
2426
2427  // Should be no changes except connecting going true and false.
2428  EXPECT_EQ(2, observer.device_changed_count_);
2429  EXPECT_FALSE(device->IsConnected());
2430  EXPECT_FALSE(device->IsConnecting());
2431  EXPECT_FALSE(device->IsPaired());
2432}
2433
2434TEST_F(BluetoothChromeOSTest, PairingCancelledAtPinCode) {
2435  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2436
2437  GetAdapter();
2438  DiscoverDevices();
2439
2440  // Cancel the pairing after we receive a request for the PIN code.
2441  BluetoothDevice* device = adapter_->GetDevice(
2442      FakeBluetoothDeviceClient::kRequestPinCodeAddress);
2443  ASSERT_TRUE(device != NULL);
2444  ASSERT_FALSE(device->IsPaired());
2445
2446  TestObserver observer(adapter_);
2447
2448  TestPairingDelegate pairing_delegate;
2449  device->Connect(
2450      &pairing_delegate,
2451      base::Bind(&BluetoothChromeOSTest::Callback,
2452                 base::Unretained(this)),
2453      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2454                 base::Unretained(this)));
2455
2456  EXPECT_EQ(1, pairing_delegate.call_count_);
2457  EXPECT_EQ(1, pairing_delegate.request_pincode_count_);
2458  EXPECT_TRUE(device->IsConnecting());
2459
2460  // Cancel the pairing.
2461  device->CancelPairing();
2462  message_loop_.Run();
2463
2464  EXPECT_EQ(0, callback_count_);
2465  EXPECT_EQ(1, error_callback_count_);
2466  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_CANCELED, last_connect_error_);
2467
2468  // Should be no changes except connecting going true and false.
2469  EXPECT_EQ(2, observer.device_changed_count_);
2470  EXPECT_FALSE(device->IsConnected());
2471  EXPECT_FALSE(device->IsConnecting());
2472  EXPECT_FALSE(device->IsPaired());
2473}
2474
2475TEST_F(BluetoothChromeOSTest, PairingRejectedAtPasskey) {
2476  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2477
2478  GetAdapter();
2479  DiscoverDevices();
2480
2481  // Reject the pairing after we receive a request for the passkey.
2482  BluetoothDevice* device = adapter_->GetDevice(
2483      FakeBluetoothDeviceClient::kRequestPasskeyAddress);
2484  ASSERT_TRUE(device != NULL);
2485  ASSERT_FALSE(device->IsPaired());
2486
2487  TestObserver observer(adapter_);
2488
2489  TestPairingDelegate pairing_delegate;
2490  device->Connect(
2491      &pairing_delegate,
2492      base::Bind(&BluetoothChromeOSTest::Callback,
2493                 base::Unretained(this)),
2494      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2495                 base::Unretained(this)));
2496
2497  EXPECT_EQ(1, pairing_delegate.call_count_);
2498  EXPECT_EQ(1, pairing_delegate.request_passkey_count_);
2499  EXPECT_TRUE(device->IsConnecting());
2500
2501  // Reject the pairing.
2502  device->RejectPairing();
2503  message_loop_.Run();
2504
2505  EXPECT_EQ(0, callback_count_);
2506  EXPECT_EQ(1, error_callback_count_);
2507  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_REJECTED, last_connect_error_);
2508
2509  // Should be no changes except connecting going true and false.
2510  EXPECT_EQ(2, observer.device_changed_count_);
2511  EXPECT_FALSE(device->IsConnected());
2512  EXPECT_FALSE(device->IsConnecting());
2513  EXPECT_FALSE(device->IsPaired());
2514}
2515
2516TEST_F(BluetoothChromeOSTest, PairingCancelledAtPasskey) {
2517  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2518
2519  GetAdapter();
2520  DiscoverDevices();
2521
2522  // Cancel the pairing after we receive a request for the passkey.
2523  BluetoothDevice* device = adapter_->GetDevice(
2524      FakeBluetoothDeviceClient::kRequestPasskeyAddress);
2525  ASSERT_TRUE(device != NULL);
2526  ASSERT_FALSE(device->IsPaired());
2527
2528  TestObserver observer(adapter_);
2529
2530  TestPairingDelegate pairing_delegate;
2531  device->Connect(
2532      &pairing_delegate,
2533      base::Bind(&BluetoothChromeOSTest::Callback,
2534                 base::Unretained(this)),
2535      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2536                 base::Unretained(this)));
2537
2538  EXPECT_EQ(1, pairing_delegate.call_count_);
2539  EXPECT_EQ(1, pairing_delegate.request_passkey_count_);
2540  EXPECT_TRUE(device->IsConnecting());
2541
2542  // Cancel the pairing.
2543  device->CancelPairing();
2544  message_loop_.Run();
2545
2546  EXPECT_EQ(0, callback_count_);
2547  EXPECT_EQ(1, error_callback_count_);
2548  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_CANCELED, last_connect_error_);
2549
2550  // Should be no changes except connecting going true and false.
2551  EXPECT_EQ(2, observer.device_changed_count_);
2552  EXPECT_FALSE(device->IsConnected());
2553  EXPECT_FALSE(device->IsConnecting());
2554  EXPECT_FALSE(device->IsPaired());
2555}
2556
2557TEST_F(BluetoothChromeOSTest, PairingRejectedAtConfirmation) {
2558  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2559
2560  GetAdapter();
2561  DiscoverDevices();
2562
2563  // Reject the pairing after we receive a request for passkey confirmation.
2564  BluetoothDevice* device = adapter_->GetDevice(
2565      FakeBluetoothDeviceClient::kConfirmPasskeyAddress);
2566  ASSERT_TRUE(device != NULL);
2567  ASSERT_FALSE(device->IsPaired());
2568
2569  TestObserver observer(adapter_);
2570
2571  TestPairingDelegate pairing_delegate;
2572  device->Connect(
2573      &pairing_delegate,
2574      base::Bind(&BluetoothChromeOSTest::Callback,
2575                 base::Unretained(this)),
2576      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2577                 base::Unretained(this)));
2578
2579  EXPECT_EQ(1, pairing_delegate.call_count_);
2580  EXPECT_EQ(1, pairing_delegate.confirm_passkey_count_);
2581  EXPECT_TRUE(device->IsConnecting());
2582
2583  // Reject the pairing.
2584  device->RejectPairing();
2585  message_loop_.Run();
2586
2587  EXPECT_EQ(0, callback_count_);
2588  EXPECT_EQ(1, error_callback_count_);
2589  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_REJECTED, last_connect_error_);
2590
2591  // Should be no changes except connecting going true and false.
2592  EXPECT_EQ(2, observer.device_changed_count_);
2593  EXPECT_FALSE(device->IsConnected());
2594  EXPECT_FALSE(device->IsConnecting());
2595  EXPECT_FALSE(device->IsPaired());
2596}
2597
2598TEST_F(BluetoothChromeOSTest, PairingCancelledAtConfirmation) {
2599  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2600
2601  GetAdapter();
2602  DiscoverDevices();
2603
2604  // Cancel the pairing after we receive a request for the passkey.
2605  BluetoothDevice* device = adapter_->GetDevice(
2606      FakeBluetoothDeviceClient::kConfirmPasskeyAddress);
2607  ASSERT_TRUE(device != NULL);
2608  ASSERT_FALSE(device->IsPaired());
2609
2610  TestObserver observer(adapter_);
2611
2612  TestPairingDelegate pairing_delegate;
2613  device->Connect(
2614      &pairing_delegate,
2615      base::Bind(&BluetoothChromeOSTest::Callback,
2616                 base::Unretained(this)),
2617      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2618                 base::Unretained(this)));
2619
2620  EXPECT_EQ(1, pairing_delegate.call_count_);
2621  EXPECT_EQ(1, pairing_delegate.confirm_passkey_count_);
2622  EXPECT_TRUE(device->IsConnecting());
2623
2624  // Cancel the pairing.
2625  device->CancelPairing();
2626  message_loop_.Run();
2627
2628  EXPECT_EQ(0, callback_count_);
2629  EXPECT_EQ(1, error_callback_count_);
2630  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_CANCELED, last_connect_error_);
2631
2632  // Should be no changes except connecting going true and false.
2633  EXPECT_EQ(2, observer.device_changed_count_);
2634  EXPECT_FALSE(device->IsConnected());
2635  EXPECT_FALSE(device->IsConnecting());
2636  EXPECT_FALSE(device->IsPaired());
2637}
2638
2639TEST_F(BluetoothChromeOSTest, PairingCancelledInFlight) {
2640  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2641
2642  GetAdapter();
2643  DiscoverDevices();
2644
2645  // Cancel the pairing while we're waiting for the remote host.
2646  BluetoothDevice* device = adapter_->GetDevice(
2647      FakeBluetoothDeviceClient::kLegacyAutopairAddress);
2648  ASSERT_TRUE(device != NULL);
2649  ASSERT_FALSE(device->IsPaired());
2650
2651  TestObserver observer(adapter_);
2652
2653  TestPairingDelegate pairing_delegate;
2654  device->Connect(
2655      &pairing_delegate,
2656      base::Bind(&BluetoothChromeOSTest::Callback,
2657                 base::Unretained(this)),
2658      base::Bind(&BluetoothChromeOSTest::ConnectErrorCallback,
2659                 base::Unretained(this)));
2660
2661  EXPECT_EQ(0, pairing_delegate.call_count_);
2662  EXPECT_TRUE(device->IsConnecting());
2663
2664  // Cancel the pairing.
2665  device->CancelPairing();
2666  message_loop_.Run();
2667
2668  EXPECT_EQ(0, callback_count_);
2669  EXPECT_EQ(1, error_callback_count_);
2670  EXPECT_EQ(BluetoothDevice::ERROR_AUTH_CANCELED, last_connect_error_);
2671
2672  // Should be no changes except connecting going true and false.
2673  EXPECT_EQ(2, observer.device_changed_count_);
2674  EXPECT_FALSE(device->IsConnected());
2675  EXPECT_FALSE(device->IsConnecting());
2676  EXPECT_FALSE(device->IsPaired());
2677}
2678
2679TEST_F(BluetoothChromeOSTest, IncomingPairRequestPinCode) {
2680  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2681
2682  GetAdapter();
2683
2684  TestPairingDelegate pairing_delegate;
2685  adapter_->AddPairingDelegate(
2686      &pairing_delegate,
2687      BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_HIGH);
2688
2689  // Requires that we provide a PIN code.
2690  fake_bluetooth_device_client_->CreateDevice(
2691      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
2692      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPinCodePath));
2693  BluetoothDevice* device = adapter_->GetDevice(
2694      FakeBluetoothDeviceClient::kRequestPinCodeAddress);
2695  ASSERT_TRUE(device != NULL);
2696  ASSERT_FALSE(device->IsPaired());
2697
2698  TestObserver observer(adapter_);
2699
2700  fake_bluetooth_device_client_->SimulatePairing(
2701      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPinCodePath),
2702      true,
2703      base::Bind(&BluetoothChromeOSTest::Callback,
2704                 base::Unretained(this)),
2705      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
2706                 base::Unretained(this)));
2707
2708  EXPECT_EQ(1, pairing_delegate.call_count_);
2709  EXPECT_EQ(1, pairing_delegate.request_pincode_count_);
2710
2711  // Set the PIN.
2712  device->SetPinCode("1234");
2713  message_loop_.Run();
2714
2715  EXPECT_EQ(1, callback_count_);
2716  EXPECT_EQ(0, error_callback_count_);
2717
2718  // One change for paired, and one for trusted.
2719  EXPECT_EQ(2, observer.device_changed_count_);
2720  EXPECT_EQ(device, observer.last_device_);
2721
2722  EXPECT_TRUE(device->IsPaired());
2723
2724  // Make sure the trusted property has been set to true.
2725  FakeBluetoothDeviceClient::Properties* properties =
2726      fake_bluetooth_device_client_->GetProperties(
2727          dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPinCodePath));
2728  ASSERT_TRUE(properties->trusted.value());
2729
2730  // No pairing context should remain on the device.
2731  BluetoothDeviceChromeOS* device_chromeos =
2732      static_cast<BluetoothDeviceChromeOS*>(device);
2733  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
2734}
2735
2736TEST_F(BluetoothChromeOSTest, IncomingPairConfirmPasskey) {
2737  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2738
2739  GetAdapter();
2740
2741  TestPairingDelegate pairing_delegate;
2742  adapter_->AddPairingDelegate(
2743      &pairing_delegate,
2744      BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_HIGH);
2745
2746  // Requests that we confirm a displayed passkey.
2747  fake_bluetooth_device_client_->CreateDevice(
2748      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
2749      dbus::ObjectPath(FakeBluetoothDeviceClient::kConfirmPasskeyPath));
2750  BluetoothDevice* device = adapter_->GetDevice(
2751      FakeBluetoothDeviceClient::kConfirmPasskeyAddress);
2752  ASSERT_TRUE(device != NULL);
2753  ASSERT_FALSE(device->IsPaired());
2754
2755  TestObserver observer(adapter_);
2756
2757  fake_bluetooth_device_client_->SimulatePairing(
2758      dbus::ObjectPath(FakeBluetoothDeviceClient::kConfirmPasskeyPath),
2759      true,
2760      base::Bind(&BluetoothChromeOSTest::Callback,
2761                 base::Unretained(this)),
2762      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
2763                 base::Unretained(this)));
2764
2765  EXPECT_EQ(1, pairing_delegate.call_count_);
2766  EXPECT_EQ(1, pairing_delegate.confirm_passkey_count_);
2767  EXPECT_EQ(123456U, pairing_delegate.last_passkey_);
2768
2769  // Confirm the passkey.
2770  device->ConfirmPairing();
2771  message_loop_.Run();
2772
2773  EXPECT_EQ(1, callback_count_);
2774  EXPECT_EQ(0, error_callback_count_);
2775
2776  // One change for paired, and one for trusted.
2777  EXPECT_EQ(2, observer.device_changed_count_);
2778  EXPECT_EQ(device, observer.last_device_);
2779
2780  EXPECT_TRUE(device->IsPaired());
2781
2782  // Make sure the trusted property has been set to true.
2783  FakeBluetoothDeviceClient::Properties* properties =
2784      fake_bluetooth_device_client_->GetProperties(
2785          dbus::ObjectPath(FakeBluetoothDeviceClient::kConfirmPasskeyPath));
2786  ASSERT_TRUE(properties->trusted.value());
2787
2788  // No pairing context should remain on the device.
2789  BluetoothDeviceChromeOS* device_chromeos =
2790      static_cast<BluetoothDeviceChromeOS*>(device);
2791  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
2792}
2793
2794TEST_F(BluetoothChromeOSTest, IncomingPairRequestPasskey) {
2795  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2796
2797  GetAdapter();
2798
2799  TestPairingDelegate pairing_delegate;
2800  adapter_->AddPairingDelegate(
2801      &pairing_delegate,
2802      BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_HIGH);
2803
2804  // Requests that we provide a Passkey.
2805  fake_bluetooth_device_client_->CreateDevice(
2806      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
2807      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath));
2808  BluetoothDevice* device = adapter_->GetDevice(
2809      FakeBluetoothDeviceClient::kRequestPasskeyAddress);
2810  ASSERT_TRUE(device != NULL);
2811  ASSERT_FALSE(device->IsPaired());
2812
2813  TestObserver observer(adapter_);
2814
2815  fake_bluetooth_device_client_->SimulatePairing(
2816      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath),
2817      true,
2818      base::Bind(&BluetoothChromeOSTest::Callback,
2819                 base::Unretained(this)),
2820      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
2821                 base::Unretained(this)));
2822
2823  EXPECT_EQ(1, pairing_delegate.call_count_);
2824  EXPECT_EQ(1, pairing_delegate.request_passkey_count_);
2825
2826  // Set the Passkey.
2827  device->SetPasskey(1234);
2828  message_loop_.Run();
2829
2830  EXPECT_EQ(1, callback_count_);
2831  EXPECT_EQ(0, error_callback_count_);
2832
2833  // One change for paired, and one for trusted.
2834  EXPECT_EQ(2, observer.device_changed_count_);
2835  EXPECT_EQ(device, observer.last_device_);
2836
2837  EXPECT_TRUE(device->IsPaired());
2838
2839  // Make sure the trusted property has been set to true.
2840  FakeBluetoothDeviceClient::Properties* properties =
2841      fake_bluetooth_device_client_->GetProperties(
2842          dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath));
2843  ASSERT_TRUE(properties->trusted.value());
2844
2845  // No pairing context should remain on the device.
2846  BluetoothDeviceChromeOS* device_chromeos =
2847      static_cast<BluetoothDeviceChromeOS*>(device);
2848  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
2849}
2850
2851TEST_F(BluetoothChromeOSTest, IncomingPairJustWorks) {
2852  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2853
2854  GetAdapter();
2855
2856  TestPairingDelegate pairing_delegate;
2857  adapter_->AddPairingDelegate(
2858      &pairing_delegate,
2859      BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_HIGH);
2860
2861  // Uses just-works pairing so, sinec this an incoming pairing, require
2862  // authorization from the user.
2863  fake_bluetooth_device_client_->CreateDevice(
2864      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
2865      dbus::ObjectPath(FakeBluetoothDeviceClient::kJustWorksPath));
2866  BluetoothDevice* device = adapter_->GetDevice(
2867      FakeBluetoothDeviceClient::kJustWorksAddress);
2868  ASSERT_TRUE(device != NULL);
2869  ASSERT_FALSE(device->IsPaired());
2870
2871  TestObserver observer(adapter_);
2872
2873  fake_bluetooth_device_client_->SimulatePairing(
2874      dbus::ObjectPath(FakeBluetoothDeviceClient::kJustWorksPath),
2875      true,
2876      base::Bind(&BluetoothChromeOSTest::Callback,
2877                 base::Unretained(this)),
2878      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
2879                 base::Unretained(this)));
2880
2881  EXPECT_EQ(1, pairing_delegate.call_count_);
2882  EXPECT_EQ(1, pairing_delegate.authorize_pairing_count_);
2883
2884  // Confirm the pairing.
2885  device->ConfirmPairing();
2886  message_loop_.Run();
2887
2888  EXPECT_EQ(1, callback_count_);
2889  EXPECT_EQ(0, error_callback_count_);
2890
2891  // One change for paired, and one for trusted.
2892  EXPECT_EQ(2, observer.device_changed_count_);
2893  EXPECT_EQ(device, observer.last_device_);
2894
2895  EXPECT_TRUE(device->IsPaired());
2896
2897  // Make sure the trusted property has been set to true.
2898  FakeBluetoothDeviceClient::Properties* properties =
2899      fake_bluetooth_device_client_->GetProperties(
2900          dbus::ObjectPath(FakeBluetoothDeviceClient::kJustWorksPath));
2901  ASSERT_TRUE(properties->trusted.value());
2902
2903  // No pairing context should remain on the device.
2904  BluetoothDeviceChromeOS* device_chromeos =
2905      static_cast<BluetoothDeviceChromeOS*>(device);
2906  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
2907}
2908
2909TEST_F(BluetoothChromeOSTest, IncomingPairRequestPinCodeWithoutDelegate) {
2910  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2911
2912  GetAdapter();
2913
2914  // Requires that we provide a PIN Code, without a pairing delegate,
2915  // that will be rejected.
2916  fake_bluetooth_device_client_->CreateDevice(
2917      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
2918      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPinCodePath));
2919  BluetoothDevice* device = adapter_->GetDevice(
2920      FakeBluetoothDeviceClient::kRequestPinCodeAddress);
2921  ASSERT_TRUE(device != NULL);
2922  ASSERT_FALSE(device->IsPaired());
2923
2924  TestObserver observer(adapter_);
2925
2926  fake_bluetooth_device_client_->SimulatePairing(
2927      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPinCodePath),
2928      true,
2929      base::Bind(&BluetoothChromeOSTest::Callback,
2930                 base::Unretained(this)),
2931      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
2932                 base::Unretained(this)));
2933
2934  message_loop_.Run();
2935
2936  EXPECT_EQ(0, callback_count_);
2937  EXPECT_EQ(1, error_callback_count_);
2938  EXPECT_EQ(bluetooth_device::kErrorAuthenticationRejected, last_client_error_);
2939
2940  // No changes should be observer.
2941  EXPECT_EQ(0, observer.device_changed_count_);
2942
2943  EXPECT_FALSE(device->IsPaired());
2944
2945  // No pairing context should remain on the device.
2946  BluetoothDeviceChromeOS* device_chromeos =
2947      static_cast<BluetoothDeviceChromeOS*>(device);
2948  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
2949}
2950
2951TEST_F(BluetoothChromeOSTest, IncomingPairConfirmPasskeyWithoutDelegate) {
2952  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2953
2954  GetAdapter();
2955
2956  // Requests that we confirm a displayed passkey, without a pairing delegate,
2957  // that will be rejected.
2958  fake_bluetooth_device_client_->CreateDevice(
2959      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
2960      dbus::ObjectPath(FakeBluetoothDeviceClient::kConfirmPasskeyPath));
2961  BluetoothDevice* device = adapter_->GetDevice(
2962      FakeBluetoothDeviceClient::kConfirmPasskeyAddress);
2963  ASSERT_TRUE(device != NULL);
2964  ASSERT_FALSE(device->IsPaired());
2965
2966  TestObserver observer(adapter_);
2967
2968  fake_bluetooth_device_client_->SimulatePairing(
2969      dbus::ObjectPath(FakeBluetoothDeviceClient::kConfirmPasskeyPath),
2970      true,
2971      base::Bind(&BluetoothChromeOSTest::Callback,
2972                 base::Unretained(this)),
2973      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
2974                 base::Unretained(this)));
2975
2976  message_loop_.Run();
2977
2978  EXPECT_EQ(0, callback_count_);
2979  EXPECT_EQ(1, error_callback_count_);
2980  EXPECT_EQ(bluetooth_device::kErrorAuthenticationRejected, last_client_error_);
2981
2982  // No changes should be observer.
2983  EXPECT_EQ(0, observer.device_changed_count_);
2984
2985  EXPECT_FALSE(device->IsPaired());
2986
2987  // No pairing context should remain on the device.
2988  BluetoothDeviceChromeOS* device_chromeos =
2989      static_cast<BluetoothDeviceChromeOS*>(device);
2990  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
2991}
2992
2993TEST_F(BluetoothChromeOSTest, IncomingPairRequestPasskeyWithoutDelegate) {
2994  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
2995
2996  GetAdapter();
2997
2998  // Requests that we provide a displayed passkey, without a pairing delegate,
2999  // that will be rejected.
3000  fake_bluetooth_device_client_->CreateDevice(
3001      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
3002      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath));
3003  BluetoothDevice* device = adapter_->GetDevice(
3004      FakeBluetoothDeviceClient::kRequestPasskeyAddress);
3005  ASSERT_TRUE(device != NULL);
3006  ASSERT_FALSE(device->IsPaired());
3007
3008  TestObserver observer(adapter_);
3009
3010  fake_bluetooth_device_client_->SimulatePairing(
3011      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath),
3012      true,
3013      base::Bind(&BluetoothChromeOSTest::Callback,
3014                 base::Unretained(this)),
3015      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
3016                 base::Unretained(this)));
3017
3018  message_loop_.Run();
3019
3020  EXPECT_EQ(0, callback_count_);
3021  EXPECT_EQ(1, error_callback_count_);
3022  EXPECT_EQ(bluetooth_device::kErrorAuthenticationRejected, last_client_error_);
3023
3024  // No changes should be observer.
3025  EXPECT_EQ(0, observer.device_changed_count_);
3026
3027  EXPECT_FALSE(device->IsPaired());
3028
3029  // No pairing context should remain on the device.
3030  BluetoothDeviceChromeOS* device_chromeos =
3031      static_cast<BluetoothDeviceChromeOS*>(device);
3032  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
3033}
3034
3035TEST_F(BluetoothChromeOSTest, IncomingPairJustWorksWithoutDelegate) {
3036  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
3037
3038  GetAdapter();
3039
3040  // Uses just-works pairing and thus requires authorization for incoming
3041  // pairings, without a pairing delegate, that will be rejected.
3042  fake_bluetooth_device_client_->CreateDevice(
3043      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
3044      dbus::ObjectPath(FakeBluetoothDeviceClient::kJustWorksPath));
3045  BluetoothDevice* device = adapter_->GetDevice(
3046      FakeBluetoothDeviceClient::kJustWorksAddress);
3047  ASSERT_TRUE(device != NULL);
3048  ASSERT_FALSE(device->IsPaired());
3049
3050  TestObserver observer(adapter_);
3051
3052  fake_bluetooth_device_client_->SimulatePairing(
3053      dbus::ObjectPath(FakeBluetoothDeviceClient::kJustWorksPath),
3054      true,
3055      base::Bind(&BluetoothChromeOSTest::Callback,
3056                 base::Unretained(this)),
3057      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
3058                 base::Unretained(this)));
3059
3060  message_loop_.Run();
3061
3062  EXPECT_EQ(0, callback_count_);
3063  EXPECT_EQ(1, error_callback_count_);
3064  EXPECT_EQ(bluetooth_device::kErrorAuthenticationRejected, last_client_error_);
3065
3066  // No changes should be observer.
3067  EXPECT_EQ(0, observer.device_changed_count_);
3068
3069  EXPECT_FALSE(device->IsPaired());
3070
3071  // No pairing context should remain on the device.
3072  BluetoothDeviceChromeOS* device_chromeos =
3073      static_cast<BluetoothDeviceChromeOS*>(device);
3074  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
3075}
3076
3077TEST_F(BluetoothChromeOSTest, RemovePairingDelegateDuringPairing) {
3078  fake_bluetooth_device_client_->SetSimulationIntervalMs(10);
3079
3080  GetAdapter();
3081
3082  TestPairingDelegate pairing_delegate;
3083  adapter_->AddPairingDelegate(
3084      &pairing_delegate,
3085      BluetoothAdapter::PAIRING_DELEGATE_PRIORITY_HIGH);
3086
3087  // Requests that we provide a Passkey.
3088  fake_bluetooth_device_client_->CreateDevice(
3089      dbus::ObjectPath(FakeBluetoothAdapterClient::kAdapterPath),
3090      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath));
3091  BluetoothDevice* device = adapter_->GetDevice(
3092      FakeBluetoothDeviceClient::kRequestPasskeyAddress);
3093  ASSERT_TRUE(device != NULL);
3094  ASSERT_FALSE(device->IsPaired());
3095
3096  TestObserver observer(adapter_);
3097
3098  fake_bluetooth_device_client_->SimulatePairing(
3099      dbus::ObjectPath(FakeBluetoothDeviceClient::kRequestPasskeyPath),
3100      true,
3101      base::Bind(&BluetoothChromeOSTest::Callback,
3102                 base::Unretained(this)),
3103      base::Bind(&BluetoothChromeOSTest::DBusErrorCallback,
3104                 base::Unretained(this)));
3105
3106  EXPECT_EQ(1, pairing_delegate.call_count_);
3107  EXPECT_EQ(1, pairing_delegate.request_passkey_count_);
3108
3109  // A pairing context should now be set on the device.
3110  BluetoothDeviceChromeOS* device_chromeos =
3111      static_cast<BluetoothDeviceChromeOS*>(device);
3112  ASSERT_TRUE(device_chromeos->GetPairing() != NULL);
3113
3114  // Removing the pairing delegate should remove that pairing context.
3115  adapter_->RemovePairingDelegate(&pairing_delegate);
3116
3117  EXPECT_TRUE(device_chromeos->GetPairing() == NULL);
3118
3119  // Set the Passkey, this should now have no effect since the pairing has
3120  // been, in-effect, cancelled
3121  device->SetPasskey(1234);
3122
3123  EXPECT_EQ(0, callback_count_);
3124  EXPECT_EQ(0, error_callback_count_);
3125  EXPECT_EQ(0, observer.device_changed_count_);
3126
3127  EXPECT_FALSE(device->IsPaired());
3128}
3129
3130TEST_F(BluetoothChromeOSTest, DeviceId) {
3131  GetAdapter();
3132
3133  // Use the built-in paired device for this test, grab its Properties
3134  // structure so we can adjust the underlying modalias property.
3135  BluetoothDevice* device = adapter_->GetDevice(
3136      FakeBluetoothDeviceClient::kPairedDeviceAddress);
3137  FakeBluetoothDeviceClient::Properties* properties =
3138      fake_bluetooth_device_client_->GetProperties(
3139          dbus::ObjectPath(FakeBluetoothDeviceClient::kPairedDevicePath));
3140
3141  ASSERT_TRUE(device != NULL);
3142  ASSERT_TRUE(properties != NULL);
3143
3144  // Valid USB IF-assigned identifier.
3145  ASSERT_EQ("usb:v05ACp030Dd0306", properties->modalias.value());
3146
3147  EXPECT_EQ(BluetoothDevice::VENDOR_ID_USB, device->GetVendorIDSource());
3148  EXPECT_EQ(0x05ac, device->GetVendorID());
3149  EXPECT_EQ(0x030d, device->GetProductID());
3150  EXPECT_EQ(0x0306, device->GetDeviceID());
3151
3152  // Valid Bluetooth SIG-assigned identifier.
3153  properties->modalias.ReplaceValue("bluetooth:v00E0p2400d0400");
3154
3155  EXPECT_EQ(BluetoothDevice::VENDOR_ID_BLUETOOTH, device->GetVendorIDSource());
3156  EXPECT_EQ(0x00e0, device->GetVendorID());
3157  EXPECT_EQ(0x2400, device->GetProductID());
3158  EXPECT_EQ(0x0400, device->GetDeviceID());
3159
3160  // Invalid USB IF-assigned identifier.
3161  properties->modalias.ReplaceValue("usb:x00E0p2400d0400");
3162
3163  EXPECT_EQ(BluetoothDevice::VENDOR_ID_UNKNOWN, device->GetVendorIDSource());
3164  EXPECT_EQ(0, device->GetVendorID());
3165  EXPECT_EQ(0, device->GetProductID());
3166  EXPECT_EQ(0, device->GetDeviceID());
3167
3168  // Invalid Bluetooth SIG-assigned identifier.
3169  properties->modalias.ReplaceValue("bluetooth:x00E0p2400d0400");
3170
3171  EXPECT_EQ(BluetoothDevice::VENDOR_ID_UNKNOWN, device->GetVendorIDSource());
3172  EXPECT_EQ(0, device->GetVendorID());
3173  EXPECT_EQ(0, device->GetProductID());
3174  EXPECT_EQ(0, device->GetDeviceID());
3175
3176  // Unknown vendor specification identifier.
3177  properties->modalias.ReplaceValue("chrome:v00E0p2400d0400");
3178
3179  EXPECT_EQ(BluetoothDevice::VENDOR_ID_UNKNOWN, device->GetVendorIDSource());
3180  EXPECT_EQ(0, device->GetVendorID());
3181  EXPECT_EQ(0, device->GetProductID());
3182  EXPECT_EQ(0, device->GetDeviceID());
3183}
3184
3185}  // namespace chromeos
3186