1#/usr/bin/env python3.4 2# 3# Copyright (C) 2016 The Android Open Source Project 4# 5# Licensed under the Apache License, Version 2.0 (the "License"); you may not 6# use this file except in compliance with the License. You may obtain a copy of 7# the License at 8# 9# http://www.apache.org/licenses/LICENSE-2.0 10# 11# Unless required by applicable law or agreed to in writing, software 12# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 13# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 14# License for the specific language governing permissions and limitations under 15# the License. 16""" 17Test script to execute Bluetooth basic functionality test cases. 18This test was designed to be run in a shield box. 19""" 20 21from contextlib import suppress 22import threading 23import time 24 25from queue import Empty 26from acts.test_utils.bt.BluetoothBaseTest import BluetoothBaseTest 27from acts.test_utils.bt.bt_test_utils import log_energy_info 28from acts.test_utils.bt.bt_test_utils import kill_bluetooth_process 29from acts.test_utils.bt.bt_test_utils import reset_bluetooth 30from acts.test_utils.bt.bt_test_utils import rfcomm_accept 31from acts.test_utils.bt.bt_test_utils import rfcomm_connect 32from acts.test_utils.bt.bt_test_utils import setup_multiple_devices_for_bt_test 33from acts.test_utils.bt.bt_test_utils import take_btsnoop_logs 34from acts.test_utils.bt.bt_test_utils import write_read_verify_data 35 36 37class RfcommTest(BluetoothBaseTest): 38 default_timeout = 10 39 rf_client_th = 0 40 scan_discovery_time = 5 41 thread_list = [] 42 message = ( 43 "Space: the final frontier. These are the voyages of " 44 "the starship Enterprise. Its continuing mission: to explore " 45 "strange new worlds, to seek out new life and new civilizations," 46 " to boldly go where no man has gone before.") 47 48 def __init__(self, controllers): 49 BluetoothBaseTest.__init__(self, controllers) 50 self.client_ad = self.android_devices[0] 51 self.server_ad = self.android_devices[1] 52 53 def _clear_bonded_devices(self): 54 for a in self.android_devices: 55 bonded_device_list = a.droid.bluetoothGetBondedDevices() 56 for device in bonded_device_list: 57 a.droid.bluetoothUnbond(device['address']) 58 59 def setup_class(self): 60 return setup_multiple_devices_for_bt_test(self.android_devices) 61 62 def setup_test(self): 63 self._clear_bonded_devices() 64 self.log.debug(log_energy_info(self.android_devices, "Start")) 65 for a in self.android_devices: 66 a.ed.clear_all_events() 67 return True 68 69 def teardown_test(self): 70 self.log.debug(log_energy_info(self.android_devices, "End")) 71 return True 72 73 def on_fail(self, test_name, begin_time): 74 take_btsnoop_logs(self.android_devices, self, test_name) 75 reset_bluetooth(self.android_devices) 76 77 def teardown_test(self): 78 with suppress(Exception): 79 self.client_ad.droid.bluetoothRfcommStop() 80 self.server_ad.droid.bluetoothRfcommStop() 81 self.client_ad.droid.bluetoothRfcommCloseSocket() 82 self.server_ad.droid.bluetoothRfcommCloseSocket() 83 for thread in self.thread_list: 84 thread.join() 85 self.thread_list.clear() 86 87 def orchestrate_rfcomm_connect(self, server_mac): 88 accept_thread = threading.Thread(target=rfcomm_accept, 89 args=(self.server_ad, )) 90 self.thread_list.append(accept_thread) 91 accept_thread.start() 92 connect_thread = threading.Thread(target=rfcomm_connect, 93 args=(self.client_ad, server_mac)) 94 self.rf_client_th = connect_thread 95 self.thread_list.append(connect_thread) 96 connect_thread.start() 97 for thread in self.thread_list: 98 thread.join() 99 end_time = time.time() + self.default_timeout 100 result = False 101 while time.time() < end_time: 102 if len(self.client_ad.droid.bluetoothRfcommActiveConnections( 103 )) > 0: 104 self.log.info("RFCOMM Connection Active") 105 return True 106 self.log.error("Failed to establish an RFCOMM connection") 107 return False 108 109 @BluetoothBaseTest.bt_test_wrap 110 def test_rfcomm_connection(self): 111 """Test bluetooth RFCOMM connection 112 113 Test RFCOMM though establishing a basic connection. 114 115 Steps: 116 1. Get the mac address of the server device. 117 2. Establish an RFCOMM connection from the client to the server AD. 118 3. Verify that the RFCOMM connection is active from both the client and 119 server. 120 121 Expected Result: 122 RFCOMM connection is established then disconnected succcessfully. 123 124 Returns: 125 Pass if True 126 Fail if False 127 128 TAGS: Classic, RFCOMM 129 Priority: 1 130 """ 131 server_mac = self.server_ad.droid.bluetoothGetLocalAddress() 132 if not self.orchestrate_rfcomm_connect(server_mac): 133 return False 134 135 self.client_ad.droid.bluetoothRfcommStop() 136 self.server_ad.droid.bluetoothRfcommStop() 137 return True 138 139 140 @BluetoothBaseTest.bt_test_wrap 141 def test_rfcomm_connection_write_ascii(self): 142 """Test bluetooth RFCOMM writing and reading ascii data 143 144 Test RFCOMM though establishing a connection. 145 146 Steps: 147 1. Get the mac address of the server device. 148 2. Establish an RFCOMM connection from the client to the server AD. 149 3. Verify that the RFCOMM connection is active from both the client and 150 server. 151 4. Write data from the client and read received data from the server. 152 5. Verify data matches from client and server 153 6. Disconnect the RFCOMM connection. 154 155 Expected Result: 156 RFCOMM connection is established then disconnected succcessfully. 157 158 Returns: 159 Pass if True 160 Fail if False 161 162 TAGS: Classic, RFCOMM 163 Priority: 1 164 """ 165 server_mac = self.server_ad.droid.bluetoothGetLocalAddress() 166 if not self.orchestrate_rfcomm_connect(server_mac): 167 return False 168 if not write_read_verify_data(self.client_ad, self.server_ad, 169 self.message, False): 170 return False 171 if len(self.server_ad.droid.bluetoothRfcommActiveConnections()) == 0: 172 self.log.info("No rfcomm connections found on server.") 173 return False 174 if len(self.client_ad.droid.bluetoothRfcommActiveConnections()) == 0: 175 self.log.info("no rfcomm connections found on client.") 176 return False 177 178 self.client_ad.droid.bluetoothRfcommStop() 179 self.server_ad.droid.bluetoothRfcommStop() 180 return True 181 182 @BluetoothBaseTest.bt_test_wrap 183 def test_rfcomm_write_binary(self): 184 """Test bluetooth RFCOMM writing and reading binary data 185 186 Test profile though establishing an RFCOMM connection. 187 188 Steps: 189 1. Get the mac address of the server device. 190 2. Establish an RFCOMM connection from the client to the server AD. 191 3. Verify that the RFCOMM connection is active from both the client and 192 server. 193 4. Write data from the client and read received data from the server. 194 5. Verify data matches from client and server 195 6. Disconnect the RFCOMM connection. 196 197 Expected Result: 198 RFCOMM connection is established then disconnected succcessfully. 199 200 Returns: 201 Pass if True 202 Fail if False 203 204 TAGS: Classic, RFCOMM 205 Priority: 1 206 """ 207 server_mac = self.server_ad.droid.bluetoothGetLocalAddress() 208 if not self.orchestrate_rfcomm_connect(server_mac): 209 return False 210 binary_message = "11010101" 211 if not write_read_verify_data(self.client_ad, self.server_ad, 212 binary_message, True): 213 return False 214 if len(self.server_ad.droid.bluetoothRfcommActiveConnections()) == 0: 215 self.log.info("No rfcomm connections found on server.") 216 return False 217 if len(self.client_ad.droid.bluetoothRfcommActiveConnections()) == 0: 218 self.log.info("no rfcomm connections found on client.") 219 return False 220 221 self.client_ad.droid.bluetoothRfcommStop() 222 self.server_ad.droid.bluetoothRfcommStop() 223 return True 224