| OLD | NEW |
| 1 # Copyright 2016 The Chromium Authors. All rights reserved. | 1 # Copyright 2016 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 import collections | 5 import collections |
| 6 import contextlib |
| 6 import io | 7 import io |
| 7 import json | 8 import json |
| 8 import logging | 9 import logging |
| 9 import os | 10 import os |
| 10 import pickle | 11 import pickle |
| 11 import shutil | 12 import shutil |
| 12 import tempfile | 13 import tempfile |
| 13 import threading | 14 import threading |
| 14 import time | 15 import time |
| 15 import zipfile | 16 import zipfile |
| 16 | 17 |
| 17 from devil.android import battery_utils | 18 from devil.android import battery_utils |
| 18 from devil.android import device_errors | 19 from devil.android import device_errors |
| 19 from devil.android import device_list | 20 from devil.android import device_list |
| 20 from devil.android import device_utils | 21 from devil.android import device_utils |
| 21 from devil.android import forwarder | 22 from devil.android import forwarder |
| 22 from devil.android.tools import device_recovery | 23 from devil.android.tools import device_recovery |
| 23 from devil.android.tools import device_status | 24 from devil.android.tools import device_status |
| 24 from devil.utils import cmd_helper | 25 from devil.utils import cmd_helper |
| 25 from devil.utils import parallelizer | 26 from devil.utils import parallelizer |
| 26 from devil.utils import reraiser_thread | 27 from devil.utils import reraiser_thread |
| 27 from pylib import constants | 28 from pylib import constants |
| 28 from pylib.base import base_test_result | 29 from pylib.base import base_test_result |
| 29 from pylib.constants import host_paths | 30 from pylib.constants import host_paths |
| 30 from pylib.local.device import local_device_environment | 31 from pylib.local.device import local_device_environment |
| 31 from pylib.local.device import local_device_test_run | 32 from pylib.local.device import local_device_test_run |
| 33 from py_trace_event import trace_event |
| 32 | 34 |
| 33 | 35 |
| 34 class HeartBeat(object): | 36 class HeartBeat(object): |
| 35 | 37 |
| 36 def __init__(self, shard, wait_time=60*10): | 38 def __init__(self, shard, wait_time=60*10): |
| 37 """ HeartBeat Logger constructor. | 39 """ HeartBeat Logger constructor. |
| 38 | 40 |
| 39 Args: | 41 Args: |
| 40 shard: A perf test runner device shard. | 42 shard: A perf test runner device shard. |
| 41 wait_time: time to wait between heartbeat messages. | 43 wait_time: time to wait between heartbeat messages. |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 87 | 89 |
| 88 def _RunSingleTest(self, test): | 90 def _RunSingleTest(self, test): |
| 89 self._test_instance.WriteBuildBotJson(self._output_dir) | 91 self._test_instance.WriteBuildBotJson(self._output_dir) |
| 90 | 92 |
| 91 timeout = self._tests[test].get('timeout', self._timeout) | 93 timeout = self._tests[test].get('timeout', self._timeout) |
| 92 cmd = self._CreateCmd(test) | 94 cmd = self._CreateCmd(test) |
| 93 cwd = os.path.abspath(host_paths.DIR_SOURCE_ROOT) | 95 cwd = os.path.abspath(host_paths.DIR_SOURCE_ROOT) |
| 94 | 96 |
| 95 self._LogTest(test, cmd, timeout) | 97 self._LogTest(test, cmd, timeout) |
| 96 | 98 |
| 99 @contextlib.contextmanager |
| 100 def trace_if_enabled(test): |
| 101 try: |
| 102 if self._test_instance.trace_output: |
| 103 trace_event.trace_begin(test) |
| 104 yield |
| 105 finally: |
| 106 if self._test_instance.trace_output: |
| 107 trace_event.trace_end(test) |
| 108 |
| 97 try: | 109 try: |
| 98 start_time = time.time() | 110 start_time = time.time() |
| 99 exit_code, output = cmd_helper.GetCmdStatusAndOutputWithTimeout( | 111 |
| 100 cmd, timeout, cwd=cwd, shell=True) | 112 with trace_if_enabled(test): |
| 113 exit_code, output = cmd_helper.GetCmdStatusAndOutputWithTimeout( |
| 114 cmd, timeout, cwd=cwd, shell=True) |
| 101 end_time = time.time() | 115 end_time = time.time() |
| 102 json_output = self._test_instance.ReadChartjsonOutput(self._output_dir) | 116 json_output = self._test_instance.ReadChartjsonOutput(self._output_dir) |
| 103 if exit_code == 0: | 117 if exit_code == 0: |
| 104 result_type = base_test_result.ResultType.PASS | 118 result_type = base_test_result.ResultType.PASS |
| 105 else: | 119 else: |
| 106 result_type = base_test_result.ResultType.FAIL | 120 result_type = base_test_result.ResultType.FAIL |
| 107 except cmd_helper.TimeoutError as e: | 121 except cmd_helper.TimeoutError as e: |
| 108 end_time = time.time() | 122 end_time = time.time() |
| 109 exit_code = -1 | 123 exit_code = -1 |
| 110 output = e.output | 124 output = e.output |
| 111 json_output = '' | 125 json_output = '' |
| 112 result_type = base_test_result.ResultType.TIMEOUT | 126 result_type = base_test_result.ResultType.TIMEOUT |
| 113 | |
| 114 return self._ProcessTestResult(test, cmd, start_time, end_time, exit_code, | 127 return self._ProcessTestResult(test, cmd, start_time, end_time, exit_code, |
| 115 output, json_output, result_type) | 128 output, json_output, result_type) |
| 116 | 129 |
| 117 def _CreateCmd(self, test): | 130 def _CreateCmd(self, test): |
| 118 cmd = [] | 131 cmd = [] |
| 119 if self._test_instance.dry_run: | 132 if self._test_instance.dry_run: |
| 120 cmd.append('echo') | 133 cmd.append('echo') |
| 121 cmd.append(self._tests[test]['cmd']) | 134 cmd.append(self._tests[test]['cmd']) |
| 122 if self._output_dir: | 135 if self._output_dir: |
| 123 cmd.append('--output-dir=%s' % self._output_dir) | 136 cmd.append('--output-dir=%s' % self._output_dir) |
| (...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 403 'affinity to work properly, it must be passed.') | 416 'affinity to work properly, it must be passed.') |
| 404 devices = active_devices | 417 devices = active_devices |
| 405 except IOError as e: | 418 except IOError as e: |
| 406 logging.error('Unable to find %s [%s]', devices_path, e) | 419 logging.error('Unable to find %s [%s]', devices_path, e) |
| 407 devices = active_devices | 420 devices = active_devices |
| 408 return sorted(devices) | 421 return sorted(devices) |
| 409 | 422 |
| 410 #override | 423 #override |
| 411 def RunTests(self): | 424 def RunTests(self): |
| 412 # Affinitize the tests. | 425 # Affinitize the tests. |
| 426 if self._test_instance.trace_output: |
| 427 assert not trace_event.trace_is_enabled(), 'Tracing already running.' |
| 428 trace_event.trace_enable(self._test_instance.trace_output) |
| 413 self._SplitTestsByAffinity() | 429 self._SplitTestsByAffinity() |
| 414 if not self._test_buckets and not self._no_device_tests: | 430 if not self._test_buckets and not self._no_device_tests: |
| 415 raise local_device_test_run.NoTestsError() | 431 raise local_device_test_run.NoTestsError() |
| 416 | 432 |
| 417 def run_no_devices_tests(): | 433 def run_no_devices_tests(): |
| 418 if not self._no_device_tests: | 434 if not self._no_device_tests: |
| 419 return [] | 435 return [] |
| 420 s = HostTestShard(self._env, self._test_instance, self._no_device_tests, | 436 s = HostTestShard(self._env, self._test_instance, self._no_device_tests, |
| 421 retries=3, timeout=self._timeout) | 437 retries=3, timeout=self._timeout) |
| 422 return [s.RunTestsOnShard()] | 438 return [s.RunTestsOnShard()] |
| (...skipping 17 matching lines...) Expand all Loading... |
| 440 self._devices = self._GetAllDevices( | 456 self._devices = self._GetAllDevices( |
| 441 self._env.devices, self._test_instance.known_devices_file) | 457 self._env.devices, self._test_instance.known_devices_file) |
| 442 | 458 |
| 443 device_indices = range(min(len(self._devices), len(self._test_buckets))) | 459 device_indices = range(min(len(self._devices), len(self._test_buckets))) |
| 444 shards = parallelizer.Parallelizer(device_indices).pMap( | 460 shards = parallelizer.Parallelizer(device_indices).pMap( |
| 445 device_shard_helper) | 461 device_shard_helper) |
| 446 return [x for x in shards.pGet(self._timeout) if x is not None] | 462 return [x for x in shards.pGet(self._timeout) if x is not None] |
| 447 | 463 |
| 448 host_test_results, device_test_results = reraiser_thread.RunAsync( | 464 host_test_results, device_test_results = reraiser_thread.RunAsync( |
| 449 [run_no_devices_tests, run_devices_tests]) | 465 [run_no_devices_tests, run_devices_tests]) |
| 466 if self._test_instance.trace_output: |
| 467 assert trace_event.trace_is_enabled(), 'Tracing not running.' |
| 468 trace_event.trace_disable() |
| 450 return host_test_results + device_test_results | 469 return host_test_results + device_test_results |
| 451 | 470 |
| 452 # override | 471 # override |
| 453 def TestPackage(self): | 472 def TestPackage(self): |
| 454 return 'perf' | 473 return 'perf' |
| 455 | 474 |
| 456 # override | 475 # override |
| 457 def _CreateShards(self, _tests): | 476 def _CreateShards(self, _tests): |
| 458 raise NotImplementedError | 477 raise NotImplementedError |
| 459 | 478 |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 512 # override | 531 # override |
| 513 def _RunTest(self, _device, _test): | 532 def _RunTest(self, _device, _test): |
| 514 raise NotImplementedError | 533 raise NotImplementedError |
| 515 | 534 |
| 516 | 535 |
| 517 class TestDictVersionError(Exception): | 536 class TestDictVersionError(Exception): |
| 518 pass | 537 pass |
| 519 | 538 |
| 520 class PerfTestRunGetStepsError(Exception): | 539 class PerfTestRunGetStepsError(Exception): |
| 521 pass | 540 pass |
| OLD | NEW |