• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Copyright 2016 The Chromium OS 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"""Server side bluetooth tests about sending bluetooth HID reports."""
6
7import logging
8import time
9
10from autotest_lib.client.common_lib import error
11from autotest_lib.server.cros.bluetooth import bluetooth_adapter_tests
12from autotest_lib.server.cros.multimedia import remote_facade_factory
13
14
15class bluetooth_AdapterHIDReports(
16        bluetooth_adapter_tests.BluetoothAdapterTests):
17    """Server side bluetooth tests about sending bluetooth HID reports.
18
19    This test tries to send HID reports to a DUT and verifies if the DUT
20    could receive the reports correctly. For the time being, only bluetooth
21    mouse events are tested. Bluetooth keyboard events will be supported
22    later.
23    """
24
25    TEST_SLEEP_SECS = 5
26
27    def _run_mouse_tests(self, device):
28        """Run all bluetooth mouse reports tests.
29
30        @param device: the bluetooth HID device.
31
32        """
33        self.test_mouse_left_click(device)
34        self.test_mouse_right_click(device)
35        self.test_mouse_move_in_x(device, 80)
36        self.test_mouse_move_in_y(device, -50)
37        self.test_mouse_move_in_xy(device, -60, 100)
38        self.test_mouse_scroll_down(device, 70)
39        self.test_mouse_scroll_up(device, 40)
40        self.test_mouse_click_and_drag(device, 90, 30)
41
42
43    def run_once(self, host, device_type, num_iterations=1, min_pass_count=1,
44                 suspend_resume=False, reboot=False):
45        """Running Bluetooth HID reports tests.
46
47        @param host: the DUT, usually a chromebook
48        @param device_type : the bluetooth HID device type, e.g., 'MOUSE'
49        @param num_iterations: the number of rounds to execute the test
50        @param min_pass_count: the minimal pass count to pass this test
51
52        """
53        self.host = host
54        factory = remote_facade_factory.RemoteFacadeFactory(host)
55        self.bluetooth_facade = factory.create_bluetooth_hid_facade()
56        self.input_facade = factory.create_input_facade()
57        self.check_chameleon()
58
59        pass_count = 0
60        self.total_fails = {}
61        for iteration in xrange(1, num_iterations + 1):
62            self.fails = []
63
64            # Get the bluetooth device object.
65            device = self.get_device(device_type)
66
67            # Reset the adapter and set it pairable.
68            self.test_reset_on_adapter()
69            self.test_pairable()
70
71            # Let the adapter pair, and connect to the target device.
72            time.sleep(self.TEST_SLEEP_SECS)
73            self.test_discover_device(device.address)
74            time.sleep(self.TEST_SLEEP_SECS)
75            self.test_pairing(device.address, device.pin, trusted=True)
76            time.sleep(self.TEST_SLEEP_SECS)
77            self.test_connection_by_adapter(device.address)
78
79            if suspend_resume:
80                self.suspend_resume()
81
82                time.sleep(self.TEST_SLEEP_SECS)
83                self.test_device_is_paired(device.address)
84
85                # After a suspend/resume, we should check if the device is
86                # connected.
87                # NOTE: After a suspend/resume, the RN42 kit remains connected.
88                #       However, this is not expected behavior for all bluetooth
89                #       peripherals.
90                time.sleep(self.TEST_SLEEP_SECS)
91                self.test_device_is_connected(device.address)
92
93                time.sleep(self.TEST_SLEEP_SECS)
94                self.test_device_name(device.address, device.name)
95
96            if reboot:
97                self.host.reboot()
98
99                # NOTE: We need to recreate the bluetooth_facade after a reboot.
100                self.bluetooth_facade = factory.create_bluetooth_hid_facade()
101                self.input_facade = factory.create_input_facade()
102
103                time.sleep(self.TEST_SLEEP_SECS)
104                self.test_device_is_paired(device.address)
105
106                time.sleep(self.TEST_SLEEP_SECS)
107                self.test_connection_by_device(device)
108
109                time.sleep(self.TEST_SLEEP_SECS)
110                self.test_device_name(device.address, device.name)
111
112            # Run tests about mouse reports.
113            if device_type.endswith('MOUSE'):
114                self._run_mouse_tests(device)
115
116            # Disconnect the device, and remove the pairing.
117            self.test_disconnection_by_adapter(device.address)
118            self.test_remove_pairing(device.address)
119
120            if bool(self.fails):
121                self.total_fails['Round %d' % iteration] = self.fails
122            else:
123                pass_count += 1
124
125            fail_count = iteration - pass_count
126            logging.info('===  (pass = %d, fail = %d) / total %d  ===\n',
127                         pass_count, fail_count, num_iterations)
128
129        if pass_count < min_pass_count:
130            raise error.TestFail(self.total_fails)
131