Index: build/android/pylib/base/shard.py |
diff --git a/build/android/pylib/base/shard.py b/build/android/pylib/base/shard.py |
index 8c429f7d3d01a9df148d25089260e9f085f50724..d963be2edd933e06b3caa350b90ef267363ed290 100644 |
--- a/build/android/pylib/base/shard.py |
+++ b/build/android/pylib/base/shard.py |
@@ -184,28 +184,28 @@ def _SetUp(runner_factory, device, out_runners, threadsafe_counter): |
logging.warning('Failed to create shard for %s: [%s]', device, e) |
-def _RunAllTests(runners, tests, num_retries, timeout=None): |
+def _RunAllTests(runners, test_collection_factory, num_retries, timeout=None): |
"""Run all tests using the given TestRunners. |
Args: |
runners: a list of TestRunner objects. |
- tests: a list of Tests to run using the given TestRunners. |
+ test_collection_factory: a callable to generate a _TestCollection object for |
+ each test runner. |
num_retries: number of retries for a test. |
timeout: watchdog timeout in seconds, defaults to the default timeout. |
Returns: |
A tuple of (TestRunResults object, exit code) |
""" |
- logging.warning('Running %s tests with %s test runners.' % |
- (len(tests), len(runners))) |
- tests_collection = _TestCollection([_Test(t) for t in tests]) |
+ logging.warning('Running tests with %s test runners.' % (len(runners))) |
results = [] |
exit_code = 0 |
watcher = watchdog_timer.WatchdogTimer(timeout) |
+ |
workers = reraiser_thread.ReraiserThreadGroup( |
[reraiser_thread.ReraiserThread( |
_RunTestsFromQueue, |
- [r, tests_collection, results, watcher, num_retries], |
+ [r, test_collection_factory(), results, watcher, num_retries], |
name=r.device[-4:]) |
for r in runners]) |
run_results = base_test_result.TestRunResults() |
@@ -267,36 +267,82 @@ def _TearDownRunners(runners, timeout=None): |
threads.JoinAll(watchdog_timer.WatchdogTimer(timeout)) |
-def ShardAndRunTests(runner_factory, devices, tests, build_type='Debug', |
- test_timeout=DEFAULT_TIMEOUT, |
- setup_timeout=DEFAULT_TIMEOUT, |
- num_retries=2): |
+def ReplicateAndRunTests(tests, *args, **kwargs): |
+ """Replicates the tests for each device, so all devices run every test. |
+ |
+ Args: |
+ tests: A list of tests to run. |
+ *args, **kwargs: Args and kwargs to RunTests which we pass through. |
+ |
+ Returns: |
+ A tuple of (base_test_result.TestRunResults object, exit code). |
+ """ |
+ |
+ if not tests: |
+ logging.error('No tests to run.') |
+ return (base_test_result.TestRunResults(), constants.ERROR_EXIT_CODE) |
+ |
+ logging.info('Will run %d tests: %s', len(tests), str(tests)) |
+ |
+ # Genereate a unique _TestCollection object for each test runner, but use |
+ # the same set of tests. |
+ TestCollectionFactory = lambda: _TestCollection([_Test(t) for t in tests]) |
+ return RunTests(TestCollectionFactory, *args, **kwargs) |
+ |
+ |
+def ShardAndRunTests(tests, *args, **kwargs): |
+ """Distrbutes all tests over devices through a shared pool of tests. |
+ |
+ Args: |
+ tests: A list of tests to run. |
+ *args, **kwargs: Args and kwargs to RunTests which we pass through. |
+ |
+ Returns: |
+ A tuple of (base_test_result.TestRunResults object, exit code). |
+ """ |
+ |
+ if not tests: |
+ logging.error('No tests to run.') |
+ return (base_test_result.TestRunResults(), constants.ERROR_EXIT_CODE) |
+ |
+ logging.info('Will run %d tests: %s', len(tests), str(tests)) |
+ |
+ # Genereate a shared _TestCollection object for all test runners, so they draw |
+ # from a common pool of tests. |
+ shared_test_collection = _TestCollection([_Test(t) for t in tests]) |
+ TestCollectionFactory = lambda: shared_test_collection |
+ return RunTests(TestCollectionFactory, *args, **kwargs) |
+ |
+ |
+def RunTests(test_collection_factory, runner_factory, devices, |
+ build_type='Debug', |
+ test_timeout=DEFAULT_TIMEOUT, |
+ setup_timeout=DEFAULT_TIMEOUT, |
+ num_retries=2): |
"""Run all tests on attached devices, retrying tests that don't pass. |
Args: |
runner_factory: callable that takes a device and index and returns a |
- TestRunner object. |
+ TestRunner object. |
+ test_collection_factory: callable that is used to generate a _TestCollection |
+ object for each test runner. |
devices: list of attached device serial numbers as strings. |
tests: list of tests to run. |
build_type: either 'Debug' or 'Release'. |
test_timeout: watchdog timeout in seconds for running tests, defaults to the |
- default timeout. |
+ default timeout. |
setup_timeout: watchdog timeout in seconds for creating and cleaning up |
- test runners, defaults to the default timeout. |
+ test runners, defaults to the default timeout. |
num_retries: number of retries for a test. |
Returns: |
A tuple of (base_test_result.TestRunResults object, exit code). |
""" |
- if not tests: |
- logging.error('No tests to run.') |
- return (base_test_result.TestRunResults(), constants.ERROR_EXIT_CODE) |
- |
- logging.info('Will run %d tests: %s', len(tests), str(tests)) |
forwarder.Forwarder.KillHost(build_type) |
runners = _CreateRunners(runner_factory, devices, setup_timeout) |
try: |
- return _RunAllTests(runners, tests, num_retries, test_timeout) |
+ return _RunAllTests(runners, test_collection_factory, |
+ num_retries, test_timeout) |
finally: |
try: |
_TearDownRunners(runners, setup_timeout) |