1a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond#!/usr/bin/env python 25bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond 35bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# Copyright (C) 2016 The Android Open Source Project 45bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# 55bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# Licensed under the Apache License, Version 2.0 (the "License"); 65bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# you may not use this file except in compliance with the License. 75bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# You may obtain a copy of the License at 85bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# 95bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# http://www.apache.org/licenses/LICENSE-2.0 105bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# 115bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# Unless required by applicable law or agreed to in writing, software 125bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# distributed under the License is distributed on an "AS IS" BASIS, 135bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 145bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# See the License for the specific language governing permissions and 155bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond# limitations under the License. 165bbcc3861c44435f89481f80946ef5c9c49968f2Luke Drummond 17dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo'''This script will run one specific test.''' 18a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummondfrom __future__ import print_function, absolute_import 19dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 20a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummondimport os 21dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leoimport sys 22dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leoimport atexit 23dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leoimport inspect 24dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leoimport logging 25a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummondimport argparse 26a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummondimport warnings 27dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 28dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leoimport harness 29dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leofrom harness import util_constants 30dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leofrom harness import util_log 31dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leofrom harness import util_warnings 32dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leofrom harness.util_functions import load_py_module 33dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leofrom harness.util_lldb import UtilLLDB 34dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leofrom harness.exception import DisconnectedException 35a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummondfrom harness.exception import TestSuiteException, TestIgnoredException 36dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leofrom harness.util_timer import Timer 37dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 38dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 39a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummondclass TestState(object): 40a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond '''Simple mutable mapping (like namedtuple)''' 41a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond def __init__(self, **kwargs): 42a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond for key, val in kwargs.items(): 43a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond setattr(self, key, val) 44a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 45a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 46dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef _test_pre_run(state): 47dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo '''This function is called before a test is executed (setup). 48dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 49dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Args: 50a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond state: Test suite state collection, instance of TestState. 51dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 52dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Returns: 53dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo True if the pre_run step completed without error. Currently the pre-run 54dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo will launch the target test binary on the device and attach an 55dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo lldb-server to it in platform mode. 56dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 57dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Raises: 58dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo AssertionError: If an assertion fails. 59dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo TestSuiteException: Previous processes of this apk required for this 60dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo test could not be killed. 61dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 62dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo assert state.test 63dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo assert state.bundle 64dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 65dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log = util_log.get_logger() 66dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.info('running: {0}'.format(state.name)) 67dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 68dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # Remove any cached NDK scripts between tests 69dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo state.bundle.delete_ndk_cache() 70dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 71dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # query our test case for the remote target app it needs 72a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond # First try the legacy behaviour 73a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond try: 74a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond target_name = state.test.get_bundle_target() 75a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond warnings.warn("get_bundle_target() is deprecated and will be removed soon" 76a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond " - use the `bundle_target` dictionary attribute instead") 77a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond except AttributeError: 78a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond try: 79a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond target_name = state.test.bundle_target[state.bundle_type] 80a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond except KeyError: 81a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond raise TestIgnoredException() 82a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 83a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond if target_name is None: 84dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # test case doesn't require a remote process to debug 85dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return True 86dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo else: 87dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # find the pid of our remote test process 88dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo state.pid = state.bundle.launch(target_name) 89dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if not state.pid: 90dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.error('unable to get pid of target') 91dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return False 92dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo state.android.kill_servers() 93dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # spawn lldb platform on the target device 94dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo state.android.launch_lldb_platform(state.device_port) 95dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return True 96dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 97dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 98dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef _test_post_run(state): 99dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo '''This function is called after a test is executed (cleanup). 100dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 101dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Args: 102a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond state: Test suite state collection, instance of TestState. 103dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 104dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Raises: 105dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo AssertionError: If an assertion fails. 106dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 107dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo assert state.test 108dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo assert state.bundle 109dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 110a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond try: 111a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond target_name = state.test.get_bundle_target() 112a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond warnings.warn("get_bundle_target() is deprecated and will be removed soon" 113a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond " - use the `bundle_target` dictionary attribute instead") 114a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond except AttributeError: 115a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond try: 116a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond target_name = state.test.bundle_target[state.bundle_type] 117a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond except KeyError: 118a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond raise TestIgnoredException() 119a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 120a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 121dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if target_name: 122dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if state.bundle.is_apk(target_name): 123dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo state.android.stop_app(state.bundle.get_package(target_name)) 124dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo else: 125dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo state.android.kill_process(target_name) 126dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 127dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 128dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef _test_run(state): 129a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond '''Execute a single test suite. 130dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 131dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Args: 132a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond state: test suite state collection, instance of TestState. 133dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 134dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Returns: 135dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo True: if the test case ran successfully and passed. 136dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo False: if the test case failed or suffered an error. 137dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 138dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Raises: 139dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo AssertionError: If an assertion fails. 140dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 141dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo assert state.lldb 142dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo assert state.lldb_module 143dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo assert state.test 144dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 145a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond test_failures = state.test.run(state.lldb, state.pid, state.lldb_module) 146a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 147a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond if test_failures: 148a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond log = util_log.get_logger() 149a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond for test, err in test_failures: 150a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond log.error('test %s:%s failed: %r' % (state.name, test, err)) 151a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 152dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return False 153dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 154dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return True 155dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 156dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 157dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef _initialise_timer(android, interval): 158dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo '''Start a 'timeout' timer, to catch stalled execution. 159dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 160dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo This function will start a timer that will act as a timeout killing this 161dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo test session if a test becomes un-responsive. 162dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 163dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Args: 164dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo android: current instance of harness.UtilAndroid 165dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo interval: the interval for the timeout, in seconds 166dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 167dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Returns: 168dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo The instance of the Timer class that was created. 169dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 170dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 171dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo def on_timeout(): 172dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo '''This is a callback function that will fire if a test takes longer 173dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo then a threshold time to complete.''' 174dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # Clean up the android properties 175dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo android.reset_all_props() 176dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # pylint: disable=protected-access 177dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo sys.stdout.flush() 178dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # hard exit to force kill all threads that may block our exit 179dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo os._exit(util_constants.RC_TEST_TIMEOUT) 180dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 181dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo timer = Timer(interval, on_timeout) 182dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo timer.start() 183dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo atexit.register(Timer.stop, timer) 184dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return timer 185dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 186dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 187dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef _quit_test(num, timer): 188dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo '''This function will exit making sure the timeout thread is killed. 189dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 190dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Args: 191dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo num: An integer specifying the exit status, 0 meaning "successful 192dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo termination". 193dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo timer: The current Timer instance. 194dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 195dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if timer: 196dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo timer.stop() 197dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo sys.stdout.flush() 198dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo sys.exit(num) 199dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 200dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 201dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef _execute_test(state): 202a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond '''Execute a test suite. 203dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 204dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Args: 205a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond state: The current TestState object. 206dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 207dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log = util_log.get_logger() 208dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 209a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond state.test.setup(state.android) 210dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo try: 211dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if not _test_pre_run(state): 212dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo raise TestSuiteException('test_pre_run() failed') 213dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if not _test_run(state): 214dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo raise TestSuiteException('test_run() failed') 215dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo _test_post_run(state) 216dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.info('Test passed') 217dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 218dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo finally: 219dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo state.test.post_run() 220a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond state.test.teardown(state.android) 221dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 222dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 223dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef _get_test_case_class(module): 224dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo '''Inspect a test case module and return the test case class. 225dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 226dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Args: 227dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo module: A loaded test case module. 228dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 229a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond # We consider only subclasses of TestCase that have `test_` methods` 230a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond log = util_log.get_logger() 231a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond log.debug("loading test suites from %r", module) 232a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond for name, klass in inspect.getmembers(module, inspect.isclass): 233a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond for attr in dir(klass): 234a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond if attr.startswith('test_'): 235a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond log.info("Found test class %r", name) 236a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond return klass 237a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond else: 238a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond log.debug("class %r has no test_ methods", name) 239dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return None 240dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 241dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 242dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef get_test_dir(test_name): 243dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' Get the directory that contains a test with a given name. 244dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 245dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Returns: 246dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo A string that is the directory containing the test. 247dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 248dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo Raises: 249dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo TestSuiteException: If a test with this name does not exist. 250dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ''' 251dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo tests_dir = os.path.dirname(os.path.realpath(__file__)) 252dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo for sub_dir in os.listdir(tests_dir): 253dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo current_test_dir = os.path.join(tests_dir, sub_dir) 254dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if (os.path.isdir(current_test_dir) and 255dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo test_name in os.listdir(current_test_dir)): 256dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo return current_test_dir 257dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 258dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo raise TestSuiteException( 259dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 'unable to find test: {0}'.format(test_name)) 260dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 261dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 262dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leodef main(): 263dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo '''Test runner entry point.''' 264dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 265dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # re-open stdout with no buffering 266dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo sys.stdout = os.fdopen(sys.stdout.fileno(), 'w', 0) 267dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 268dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo android = None 269dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo timer = None 270dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log = None 271dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 272a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond # parse the command line (positional arguments only) 273a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond truthy = lambda x: x.lower() in ('true', '1') 274a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond parser = argparse.ArgumentParser("Run a single RenderScript TestSuite against lldb") 275a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond for name, formatter in ( 276a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('test_name', str), 277a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('log_file_path', str), 278a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('adb_path', str), 279a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('lldb_server_path_device', str), 280a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('aosp_product_path', str), 281a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('device_port', int), 282a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('device', str), 283a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('print_to_stdout', truthy), 284a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('verbose', truthy), 285a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('wimpy', truthy), 286a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('timeout', int), 287a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ('bundle_type', str), 288a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ): 289a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond parser.add_argument(name, type=formatter) 290a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 291a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond args = parser.parse_args() 292dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 293a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond try: 294dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # create utility classes 295a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond harness.util_log.initialise( 296a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond '%s(%s)' % (args.test_name, args.bundle_type), 297a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond print_to_stdout=args.print_to_stdout, 298a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond level=logging.INFO if not args.verbose else logging.DEBUG, 299a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond file_path=args.log_file_path, 300dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo file_mode='a' 301dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo ) 302dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log = util_log.get_logger() 303dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.debug('Logger initialised') 304dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 305a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond android = harness.UtilAndroid(args.adb_path, 306a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond args.lldb_server_path_device, 307a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond args.device) 308dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 309dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # start the timeout counter 310a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond timer = _initialise_timer(android, args.timeout) 311dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 312dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # startup lldb and register teardown handler 313dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo atexit.register(UtilLLDB.stop) 314dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo UtilLLDB.start() 315dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 316a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond current_test_dir = get_test_dir(args.test_name) 317dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 318dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # load a test case module 319dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo test_module = load_py_module(os.path.join(current_test_dir, 320a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond args.test_name)) 321a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 322dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 323dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # inspect the test module and locate our test case class 324dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo test_class = _get_test_case_class(test_module) 325dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 326dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # if our test inherits from TestBaseRemote, check we have a valid device 327dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if (hasattr(test_module, "TestBaseRemote") and 328dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo issubclass(test_class, test_module.TestBaseRemote)): 329dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo android.validate_device() 330dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 331dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # create an instance of our test case 332a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond test_inst = test_class( 333a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond args.device_port, 334a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond args.device, 335a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond timer, 336a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond args.bundle_type, 337a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond wimpy=args.wimpy 338a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ) 339dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 340dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # instantiate a test target bundle 341a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond bundle = harness.UtilBundle(android, args.aosp_product_path) 342dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 343dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # execute the test case 344dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo try: 345dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo for _ in range(2): 346dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo try: 347dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # create an lldb instance 348dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo lldb = UtilLLDB.create_debugger() 349dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 350dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # create state object to encapsulate instances 351a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 352a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond state = TestState( 353a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond android=android, 354a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond bundle=bundle, 355a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond lldb=lldb, 356a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond lldb_module=UtilLLDB.get_module(), 357a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond test=test_inst, 358a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond pid=None, 359a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond name=args.test_name, 360a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond device_port=args.device_port, 361a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond bundle_type=args.bundle_type 362a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond ) 363dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 364dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo util_warnings.redirect_warnings() 365dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 366dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo _execute_test(state) 367dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 368dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # tear down the lldb instance 369dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo UtilLLDB.destroy_debugger(lldb) 370dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo break 371dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo except DisconnectedException as error: 372dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.warning(error) 373dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.warning('Trying again.') 374dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo else: 375dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.fatal('Not trying again, maximum retries exceeded.') 376dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo raise TestSuiteException('Lost connection to lldb-server') 377dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 378dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo finally: 379dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo util_warnings.restore_warnings() 380dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 381dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo _quit_test(util_constants.RC_TEST_OK, timer) 382dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 383dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo except AssertionError: 384dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if log: 385dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.critical('Internal test suite error', exc_info=1) 386dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo print('Internal test suite error', file=sys.stderr) 387dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo _quit_test(util_constants.RC_TEST_FATAL, timer) 388dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 389a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond except TestIgnoredException: 390a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond if log: 391a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond log.warn("test ignored") 392a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond _quit_test(util_constants.RC_TEST_IGNORED, timer) 393a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond 394dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo except TestSuiteException as error: 395dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if log: 396dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.exception(str(error)) 397dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo else: 398a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond print(error, file=sys.stderr) 39974de4db187fc370c9b6625134ae39df6655e7d72Luke Drummond _quit_test(util_constants.RC_TEST_FAIL, timer) 400dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 401dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # use a global exception handler to be sure that we will 402dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo # exit safely and correctly 403dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo except Exception: 404dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if log: 405dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo log.exception('INTERNAL ERROR') 406dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo else: 407dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo import traceback 408dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo print('Exception {0}'.format(traceback.format_exc()), 409dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo file=sys.stderr) 410dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo _quit_test(util_constants.RC_TEST_FATAL, timer) 411dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 412dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo finally: 413dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if android: 414dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo android.reset_all_props() 415dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo if timer: 416dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo timer.stop() 417dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 418dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo 419dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo# execution trampoline 420dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leoif __name__ == '__main__': 421a3c6f62775506c95afd556e617f14d7a28839f01Luke Drummond print(' '.join(sys.argv)) 422dcecc0c8d22e894525e25a122ce25129b51338f2Dean De Leo main() 423