Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(11)

Side by Side Diff: device/bluetooth/bluetooth_gatt_characteristic_unittest.cc

Issue 1502833002: bluetooth: android: Enable characteristic change notification events. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@bta-check-null-
Patch Set: GattCharacteristicValueChanged_AfterDeleted Created 4 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "device/bluetooth/bluetooth_gatt_characteristic.h" 5 #include "device/bluetooth/bluetooth_gatt_characteristic.h"
6 6
7 #include <stdint.h> 7 #include <stdint.h>
8 8
9 #include "base/macros.h" 9 #include "base/macros.h"
10 #include "base/run_loop.h" 10 #include "base/run_loop.h"
11 #include "build/build_config.h" 11 #include "build/build_config.h"
12 #include "device/bluetooth/bluetooth_gatt_service.h" 12 #include "device/bluetooth/bluetooth_gatt_service.h"
13 #include "device/bluetooth/test/test_bluetooth_adapter_observer.h"
13 #include "testing/gtest/include/gtest/gtest.h" 14 #include "testing/gtest/include/gtest/gtest.h"
14 15
15 #if defined(OS_ANDROID) 16 #if defined(OS_ANDROID)
16 #include "device/bluetooth/test/bluetooth_test_android.h" 17 #include "device/bluetooth/test/bluetooth_test_android.h"
17 #elif defined(OS_MACOSX) 18 #elif defined(OS_MACOSX)
18 #include "device/bluetooth/test/bluetooth_test_mac.h" 19 #include "device/bluetooth/test/bluetooth_test_mac.h"
19 #endif 20 #endif
20 21
21 namespace device { 22 namespace device {
22 23
23 #if defined(OS_ANDROID) || defined(OS_MACOSX) 24 #if defined(OS_ANDROID) || defined(OS_MACOSX)
24 class BluetoothGattCharacteristicTest : public BluetoothTest { 25 class BluetoothGattCharacteristicTest : public BluetoothTest {
25 public: 26 public:
26 // Creates adapter_, device_, service_, characteristic1_, & characteristic2_. 27 // Creates adapter_, device_, service_, characteristic1_, & characteristic2_.
27 void FakeCharacteristicBoilerplate() { 28 // |properties| will be used for each characteristic.
29 void FakeCharacteristicBoilerplate(int properties = 0) {
28 InitWithFakeAdapter(); 30 InitWithFakeAdapter();
29 StartLowEnergyDiscoverySession(); 31 StartLowEnergyDiscoverySession();
30 device_ = DiscoverLowEnergyDevice(3); 32 device_ = DiscoverLowEnergyDevice(3);
31 device_->CreateGattConnection(GetGattConnectionCallback(Call::EXPECTED), 33 device_->CreateGattConnection(GetGattConnectionCallback(Call::EXPECTED),
32 GetConnectErrorCallback(Call::NOT_EXPECTED)); 34 GetConnectErrorCallback(Call::NOT_EXPECTED));
33 SimulateGattConnection(device_); 35 SimulateGattConnection(device_);
34 std::vector<std::string> services; 36 std::vector<std::string> services;
35 std::string uuid("00000000-0000-1000-8000-00805f9b34fb"); 37 std::string uuid("00000000-0000-1000-8000-00805f9b34fb");
36 services.push_back(uuid); 38 services.push_back(uuid);
37 SimulateGattServicesDiscovered(device_, services); 39 SimulateGattServicesDiscovered(device_, services);
38 ASSERT_EQ(1u, device_->GetGattServices().size()); 40 ASSERT_EQ(1u, device_->GetGattServices().size());
39 service_ = device_->GetGattServices()[0]; 41 service_ = device_->GetGattServices()[0];
40 SimulateGattCharacteristic(service_, uuid, /* properties */ 0); 42 SimulateGattCharacteristic(service_, uuid, properties);
41 SimulateGattCharacteristic(service_, uuid, /* properties */ 0); 43 SimulateGattCharacteristic(service_, uuid, properties);
42 ASSERT_EQ(2u, service_->GetCharacteristics().size()); 44 ASSERT_EQ(2u, service_->GetCharacteristics().size());
43 characteristic1_ = service_->GetCharacteristics()[0]; 45 characteristic1_ = service_->GetCharacteristics()[0];
44 characteristic2_ = service_->GetCharacteristics()[1]; 46 characteristic2_ = service_->GetCharacteristics()[1];
45 ResetEventCounts(); 47 ResetEventCounts();
46 } 48 }
47 49
50 // Constructs characteristics with |properties|, calls StartNotifySession,
51 // and verifies the appropriate |expected_config_descriptor_value| is written.
52 void StartNotifyBoilerplate(int properties,
53 uint16_t expected_config_descriptor_value) {
54 ASSERT_NO_FATAL_FAILURE(FakeCharacteristicBoilerplate(properties));
55 SimulateGattDescriptor(
56 characteristic1_,
57 /* Client Characteristic Configuration descriptor's standard UUID: */
58 "00002902-0000-1000-8000-00805F9B34FB");
59 ASSERT_EQ(1u, characteristic1_->GetDescriptors().size());
60
61 characteristic1_->StartNotifySession(
62 GetNotifyCallback(Call::EXPECTED),
63 GetGattErrorCallback(Call::NOT_EXPECTED));
64 EXPECT_EQ(1, gatt_notify_characteristic_attempts_);
65 EXPECT_EQ(0, callback_count_);
66 SimulateGattNotifySessionStarted(characteristic1_);
67 EXPECT_EQ(1, callback_count_);
68 EXPECT_EQ(0, error_callback_count_);
69 ASSERT_EQ(1u, notify_sessions_.size());
70 ASSERT_TRUE(notify_sessions_[0]);
71 EXPECT_EQ(characteristic1_->GetIdentifier(),
72 notify_sessions_[0]->GetCharacteristicIdentifier());
73 EXPECT_TRUE(notify_sessions_[0]->IsActive());
74
75 // Verify the Client Characteristic Configuration descriptor was written to.
76 EXPECT_EQ(1, gatt_write_descriptor_attempts_);
77 std::vector<uint8_t> written_vector(
78 &expected_config_descriptor_value,
Jeffrey Yasskin 2016/01/14 00:13:42 You mean to pull the bytes out of here, right? Ins
scheib 2016/01/14 01:12:26 Thanks - double check this version.
79 &expected_config_descriptor_value +
80 sizeof(expected_config_descriptor_value));
81 EXPECT_EQ(written_vector, last_write_value_);
82 }
83
48 BluetoothDevice* device_ = nullptr; 84 BluetoothDevice* device_ = nullptr;
49 BluetoothGattService* service_ = nullptr; 85 BluetoothGattService* service_ = nullptr;
50 BluetoothGattCharacteristic* characteristic1_ = nullptr; 86 BluetoothGattCharacteristic* characteristic1_ = nullptr;
51 BluetoothGattCharacteristic* characteristic2_ = nullptr; 87 BluetoothGattCharacteristic* characteristic2_ = nullptr;
52 }; 88 };
53 #endif 89 #endif
54 90
55 #if defined(OS_ANDROID) 91 #if defined(OS_ANDROID)
56 TEST_F(BluetoothGattCharacteristicTest, GetIdentifier) { 92 TEST_F(BluetoothGattCharacteristicTest, GetIdentifier) {
57 InitWithFakeAdapter(); 93 InitWithFakeAdapter();
(...skipping 573 matching lines...) Expand 10 before | Expand all | Expand 10 after
631 667
632 // Initial read should still succeed: 668 // Initial read should still succeed:
633 ResetEventCounts(); 669 ResetEventCounts();
634 SimulateGattCharacteristicRead(characteristic1_, empty_vector); 670 SimulateGattCharacteristicRead(characteristic1_, empty_vector);
635 EXPECT_EQ(1, callback_count_); 671 EXPECT_EQ(1, callback_count_);
636 EXPECT_EQ(0, error_callback_count_); 672 EXPECT_EQ(0, error_callback_count_);
637 } 673 }
638 #endif // defined(OS_ANDROID) 674 #endif // defined(OS_ANDROID)
639 675
640 #if defined(OS_ANDROID) 676 #if defined(OS_ANDROID)
641 // Tests StartNotifySession success. 677 // StartNotifySession fails if characteristic doesn't have Notify or Indicate
642 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession) { 678 // property.
679 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession_NoNotifyOrIndicate) {
643 ASSERT_NO_FATAL_FAILURE(FakeCharacteristicBoilerplate()); 680 ASSERT_NO_FATAL_FAILURE(FakeCharacteristicBoilerplate());
644 681
645 characteristic1_->StartNotifySession( 682 characteristic1_->StartNotifySession(GetNotifyCallback(Call::NOT_EXPECTED),
646 GetNotifyCallback(Call::EXPECTED), 683 GetGattErrorCallback(Call::EXPECTED));
647 GetGattErrorCallback(Call::NOT_EXPECTED)); 684 EXPECT_EQ(0, gatt_notify_characteristic_attempts_);
648 EXPECT_EQ(1, gatt_notify_characteristic_attempts_); 685
649 EXPECT_EQ(0, callback_count_); 686 // The expected error callback is asynchronous:
650 SimulateGattNotifySessionStarted(characteristic1_);
651 EXPECT_EQ(1, callback_count_);
652 EXPECT_EQ(0, error_callback_count_); 687 EXPECT_EQ(0, error_callback_count_);
653 ASSERT_EQ(1u, notify_sessions_.size()); 688 base::RunLoop().RunUntilIdle();
654 ASSERT_TRUE(notify_sessions_[0]); 689 EXPECT_EQ(1, error_callback_count_);
655 EXPECT_EQ(characteristic1_->GetIdentifier(), 690 }
656 notify_sessions_[0]->GetCharacteristicIdentifier()); 691 #endif // defined(OS_ANDROID)
657 EXPECT_TRUE(notify_sessions_[0]->IsActive()); 692
693 #if defined(OS_ANDROID)
694 // StartNotifySession fails if the characteristic is missing the Client
695 // Characteristic Configuration descriptor.
696 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession_NoConfigDescriptor) {
697 ASSERT_NO_FATAL_FAILURE(
698 FakeCharacteristicBoilerplate(/* properties: NOTIFY */ 0x10));
699
700 characteristic1_->StartNotifySession(GetNotifyCallback(Call::NOT_EXPECTED),
701 GetGattErrorCallback(Call::EXPECTED));
702 EXPECT_EQ(0, gatt_notify_characteristic_attempts_);
703
704 // The expected error callback is asynchronous:
705 EXPECT_EQ(0, error_callback_count_);
706 base::RunLoop().RunUntilIdle();
707 EXPECT_EQ(1, error_callback_count_);
658 } 708 }
659 #endif // defined(OS_ANDROID) 709 #endif // defined(OS_ANDROID)
660 710
661 #if defined(OS_ANDROID) 711 #if defined(OS_ANDROID)
662 // Tests StartNotifySession synchronous failure. 712 // Tests StartNotifySession synchronous failure.
663 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession_SynchronousError) { 713 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession_SynchronousError) {
Jeffrey Yasskin 2016/01/14 00:13:43 Is "SynchronousError" the most descriptive name fo
scheib 2016/01/14 01:12:26 Done. Naming was intentionally abstracting platfor
664 ASSERT_NO_FATAL_FAILURE(FakeCharacteristicBoilerplate()); 714 ASSERT_NO_FATAL_FAILURE(
715 FakeCharacteristicBoilerplate(/* properties: NOTIFY */ 0x10));
665 716
666 SimulateGattCharacteristicSetNotifyWillFailSynchronouslyOnce( 717 SimulateGattCharacteristicSetNotifyWillFailSynchronouslyOnce(
Jeffrey Yasskin 2016/01/14 00:13:42 If you remove this line, does the test fail? I sus
scheib 2016/01/14 01:12:26 It needed the descriptor. Code coverage here is br
Jeffrey Yasskin 2016/01/14 18:43:31 One way to do it would be to have StartNotifyBoile
scheib 2016/01/14 21:02:14 Nice idea - I'll refactor to use it in a follow up
667 characteristic1_); 718 characteristic1_);
668 characteristic1_->StartNotifySession(GetNotifyCallback(Call::NOT_EXPECTED), 719 characteristic1_->StartNotifySession(GetNotifyCallback(Call::NOT_EXPECTED),
669 GetGattErrorCallback(Call::EXPECTED)); 720 GetGattErrorCallback(Call::EXPECTED));
670 EXPECT_EQ(0, error_callback_count_); 721 EXPECT_EQ(0, error_callback_count_);
671 base::RunLoop().RunUntilIdle(); 722 base::RunLoop().RunUntilIdle();
723 EXPECT_EQ(1, error_callback_count_);
672 EXPECT_EQ(0, gatt_notify_characteristic_attempts_); 724 EXPECT_EQ(0, gatt_notify_characteristic_attempts_);
673 EXPECT_EQ(0, callback_count_); 725 ASSERT_EQ(0u, notify_sessions_.size());
726 }
727 #endif // defined(OS_ANDROID)
728
729 #if defined(OS_ANDROID)
730 // Tests StartNotifySession descriptor write synchronous failure.
731 TEST_F(BluetoothGattCharacteristicTest,
732 StartNotifySession_WriteDescriptorSynchronousError) {
733 ASSERT_NO_FATAL_FAILURE(
734 FakeCharacteristicBoilerplate(/* properties: NOTIFY */ 0x10));
735 SimulateGattDescriptor(
736 characteristic1_,
737 /* Client Characteristic Configuration descriptor's standard UUID: */
738 "00002902-0000-1000-8000-00805F9B34FB");
739 ASSERT_EQ(1u, characteristic1_->GetDescriptors().size());
740
741 // Fail to write to config descriptor synchronously.
742 SimulateGattDescriptorWriteWillFailSynchronouslyOnce(
743 characteristic1_->GetDescriptors()[0]);
744
745 characteristic1_->StartNotifySession(GetNotifyCallback(Call::NOT_EXPECTED),
746 GetGattErrorCallback(Call::EXPECTED));
747 EXPECT_EQ(0, error_callback_count_);
748 base::RunLoop().RunUntilIdle();
674 EXPECT_EQ(1, error_callback_count_); 749 EXPECT_EQ(1, error_callback_count_);
750 EXPECT_EQ(1, gatt_notify_characteristic_attempts_);
675 ASSERT_EQ(0u, notify_sessions_.size()); 751 ASSERT_EQ(0u, notify_sessions_.size());
676 } 752 }
677 #endif // defined(OS_ANDROID) 753 #endif // defined(OS_ANDROID)
678 754
679 #if defined(OS_ANDROID) 755 #if defined(OS_ANDROID)
756 // Tests StartNotifySession success.
757 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession) {
758 ASSERT_NO_FATAL_FAILURE(StartNotifyBoilerplate(
759 /* properties: NOTIFY */ 0x10,
760 /* expected_config_descriptor_value: NOTIFY */ 1));
761 }
762 #endif // defined(OS_ANDROID)
763
764 #if defined(OS_ANDROID)
765 // Tests StartNotifySession success.
766 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession_OnIndicate) {
767 ASSERT_NO_FATAL_FAILURE(StartNotifyBoilerplate(
768 /* properties: INDICATE */ 0x20,
Jeffrey Yasskin 2016/01/14 00:13:42 Please also check when both NOTIFY and INDICATE pr
scheib 2016/01/14 01:12:26 Done.
769 /* expected_config_descriptor_value: INDICATE */ 2));
770 }
771 #endif // defined(OS_ANDROID)
772
773 #if defined(OS_ANDROID)
774 // Tests Characteristic Value changes during a Notify Session.
775 TEST_F(BluetoothGattCharacteristicTest, GattCharacteristicValueChanged) {
776 ASSERT_NO_FATAL_FAILURE(StartNotifyBoilerplate(
777 /* properties: NOTIFY */ 0x10,
778 /* expected_config_descriptor_value: NOTIFY */ 1));
779
780 TestBluetoothAdapterObserver observer(adapter_);
781
782 std::vector<uint8_t> test_vector1;
783 test_vector1.push_back(111);
784 std::vector<uint8_t> test_vector2;
785 test_vector2.push_back(222);
786
787 SimulateGattCharacteristicChanged(characteristic1_, test_vector1);
788 EXPECT_EQ(1, observer.gatt_characteristic_value_changed_count());
789 EXPECT_EQ(test_vector1, characteristic1_->GetValue());
790
791 SimulateGattCharacteristicChanged(characteristic1_, test_vector2);
792 EXPECT_EQ(2, observer.gatt_characteristic_value_changed_count());
793 EXPECT_EQ(test_vector2, characteristic1_->GetValue());
794 }
795 #endif // defined(OS_ANDROID)
796
797 #if defined(OS_ANDROID)
798 // Tests Characteristic Value changing after a Notify Session and objects being
799 // destroyed.
800 TEST_F(BluetoothGattCharacteristicTest,
801 GattCharacteristicValueChanged_AfterDeleted) {
802 ASSERT_NO_FATAL_FAILURE(StartNotifyBoilerplate(
803 /* properties: NOTIFY */ 0x10,
804 /* expected_config_descriptor_value: NOTIFY */ 1));
805
806 RememberCharacteristicForSubsequentAction(characteristic1_);
807 DeleteDevice(device_);
808
809 std::vector<uint8_t> empty_vector;
810 SimulateGattCharacteristicChanged(/* use remembered characteristic */ nullptr,
Jeffrey Yasskin 2016/01/14 00:13:42 Please comment that the test here is that nothing
scheib 2016/01/14 01:12:26 Done.
811 empty_vector);
812 }
813 #endif // defined(OS_ANDROID)
814
815 #if defined(OS_ANDROID)
680 // Tests multiple StartNotifySession success. 816 // Tests multiple StartNotifySession success.
681 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession_Multiple) { 817 TEST_F(BluetoothGattCharacteristicTest, StartNotifySession_Multiple) {
682 ASSERT_NO_FATAL_FAILURE(FakeCharacteristicBoilerplate()); 818 ASSERT_NO_FATAL_FAILURE(
819 FakeCharacteristicBoilerplate(/* properties: NOTIFY */ 0x10));
820 SimulateGattDescriptor(
821 characteristic1_,
822 /* Client Characteristic Configuration descriptor's standard UUID: */
823 "00002902-0000-1000-8000-00805F9B34FB");
824 ASSERT_EQ(1u, characteristic1_->GetDescriptors().size());
683 825
684 characteristic1_->StartNotifySession( 826 characteristic1_->StartNotifySession(
685 GetNotifyCallback(Call::EXPECTED), 827 GetNotifyCallback(Call::EXPECTED),
686 GetGattErrorCallback(Call::NOT_EXPECTED)); 828 GetGattErrorCallback(Call::NOT_EXPECTED));
687 characteristic1_->StartNotifySession( 829 characteristic1_->StartNotifySession(
688 GetNotifyCallback(Call::EXPECTED), 830 GetNotifyCallback(Call::EXPECTED),
689 GetGattErrorCallback(Call::NOT_EXPECTED)); 831 GetGattErrorCallback(Call::NOT_EXPECTED));
690 #if defined(OS_ANDROID) 832 #if defined(OS_ANDROID)
691 // TODO(crbug.com/551634): Decide when implementing IsNotifying if Android 833 // TODO(crbug.com/551634): Decide when implementing IsNotifying if Android
692 // should trust the notification request always worked, or if we should always 834 // should trust the notification request always worked, or if we should always
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after
758 900
759 // Characteristic 1 has descriptor uuids 1 and 2 (we don't know the order). 901 // Characteristic 1 has descriptor uuids 1 and 2 (we don't know the order).
760 EXPECT_TRUE(c1_uuid1 == uuid1 || c1_uuid2 == uuid1); 902 EXPECT_TRUE(c1_uuid1 == uuid1 || c1_uuid2 == uuid1);
761 EXPECT_TRUE(c1_uuid1 == uuid2 || c1_uuid2 == uuid2); 903 EXPECT_TRUE(c1_uuid1 == uuid2 || c1_uuid2 == uuid2);
762 // ... but not uuid 3 904 // ... but not uuid 3
763 EXPECT_FALSE(c1_uuid1 == uuid3 || c1_uuid2 == uuid3); 905 EXPECT_FALSE(c1_uuid1 == uuid3 || c1_uuid2 == uuid3);
764 } 906 }
765 #endif // defined(OS_ANDROID) 907 #endif // defined(OS_ANDROID)
766 908
767 } // namespace device 909 } // namespace device
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698