Ejemplo n.º 1
0
    def GenerateCoverageReportIfNeeded(self):
        """Uses the Emma to generate a coverage report and a html page."""
        if not self.coverage:
            return
        cmd = [
            'java', '-classpath', TestRunner._EMMA_JAR, 'emma', 'report', '-r',
            'html', '-in', TestRunner._COVERAGE_MERGED_FILENAME, '-in',
            TestRunner._COVERAGE_META_INFO_PATH
        ]
        cmd_helper.RunCmd(cmd)
        new_dir = os.path.join(TestRunner._COVERAGE_WEB_ROOT_DIR,
                               time.strftime('Coverage_for_%Y_%m_%d_%a_%H:%M'))
        shutil.copytree('coverage', new_dir)

        latest_dir = os.path.join(TestRunner._COVERAGE_WEB_ROOT_DIR,
                                  'Latest_Coverage_Run')
        if os.path.exists(latest_dir):
            shutil.rmtree(latest_dir)
        os.mkdir(latest_dir)
        webserver_new_index = os.path.join(new_dir, 'index.html')
        webserver_new_files = os.path.join(new_dir, '_files')
        webserver_latest_index = os.path.join(latest_dir, 'index.html')
        webserver_latest_files = os.path.join(latest_dir, '_files')
        # Setup new softlinks to last result.
        os.symlink(webserver_new_index, webserver_latest_index)
        os.symlink(webserver_new_files, webserver_latest_files)
        cmd_helper.RunCmd(['chmod', '755', '-R', latest_dir, new_dir])
Ejemplo n.º 2
0
    def ZipAndCleanResults(dest_dir, dump_file_name, debug_info_list):
        """A helper method to zip all debug information results into a dump file.

    Args:
      dest-dir: Dir path in where we put the dump file.
      dump_file_name: Desired name of the dump file. This method makes sure
                      '.zip' will be added as ext name.
      debug_info_list: List of all debug info objects.
    """
        if not dest_dir or not dump_file_name or not debug_info_list:
            return
        cmd_helper.RunCmd(['mkdir', '-p', dest_dir])
        log_basename = os.path.basename(dump_file_name)
        log_file = os.path.join(dest_dir,
                                os.path.splitext(log_basename)[0] + '.zip')
        logging.info('Zipping debug dumps into %s ...' % log_file)
        for d in debug_info_list:
            d.ArchiveNewCrashFiles()
        # Add new dumps into the zip file. The zip may exist already if previous
        # gtest also dumps the debug information. It's OK since we clean up the old
        # dumps in each build step.
        cmd_helper.RunCmd([
            'zip', '-q', '-r', log_file,
            ' '.join([d.GetStoragePath() for d in debug_info_list])
        ])
        assert os.path.exists(log_file)
        for debug_info in debug_info_list:
            debug_info.CleanupStorage()
Ejemplo n.º 3
0
  def _KillHostForwarderBlocking(self, host_pattern, timeout_sec):
    """Kills any existing host forwarders using the provided pattern.

    Note that this waits until the process terminates.
    """
    cmd_helper.RunCmd(['pkill', '-f', host_pattern])
    elapsed = 0
    wait_period = 0.1
    while not cmd_helper.RunCmd(['pgrep', '-f', host_pattern]) and (
        elapsed < timeout_sec):
      time.sleep(wait_period)
      elapsed += wait_period
    if elapsed >= timeout_sec:
        raise Exception('Timed out while killing ' + host_pattern)
Ejemplo n.º 4
0
    def SaveCoverageData(self, test):
        """Saves the Emma coverage data before it's overwritten by the next test.

    Args:
      test: the test whose coverage data is collected.
    """
        if not self.coverage:
            return
        if not self.adb.Adb().Pull(TestRunner._COVERAGE_RESULT_PATH,
                                   constants.CHROME_DIR):
            logging.error('ERROR: Unable to find file ' +
                          TestRunner._COVERAGE_RESULT_PATH +
                          ' on the device for test ' + test)
        pulled_coverage_file = os.path.join(constants.CHROME_DIR,
                                            TestRunner._COVERAGE_FILENAME)
        if os.path.exists(TestRunner._COVERAGE_MERGED_FILENAME):
            cmd = [
                'java', '-classpath', TestRunner._EMMA_JAR, 'emma', 'merge',
                '-in', pulled_coverage_file, '-in',
                TestRunner._COVERAGE_MERGED_FILENAME, '-out',
                TestRunner._COVERAGE_MERGED_FILENAME
            ]
            cmd_helper.RunCmd(cmd)
        else:
            shutil.copy(pulled_coverage_file,
                        TestRunner._COVERAGE_MERGED_FILENAME)
        os.remove(pulled_coverage_file)
Ejemplo n.º 5
0
    def CreateTestRunnerScript(self, gtest_filter, test_arguments):
        """Creates a test runner script and pushes to the device.

    Args:
      gtest_filter: A gtest_filter flag.
      test_arguments: Additional arguments to pass to the test binary.
    """
        tool_wrapper = self.tool.GetTestWrapper()
        sh_script_file = tempfile.NamedTemporaryFile()
        # We need to capture the exit status from the script since adb shell won't
        # propagate to us.
        sh_script_file.write(
            'cd /data/local\n'
            '%s'
            '%s /data/local/%s --gtest_filter=%s %s\n'
            'echo $? > %s' %
            (self._AddNativeCoverageExports(), tool_wrapper,
             self.test_suite_basename, gtest_filter, test_arguments,
             TestPackageExecutable._TEST_RUNNER_RET_VAL_FILE))
        sh_script_file.flush()
        cmd_helper.RunCmd(['chmod', '+x', sh_script_file.name])
        self.adb.PushIfNeeded(sh_script_file.name,
                              '/data/local/chrome_test_runner.sh')
        logging.info('Conents of the test runner script: ')
        for line in open(sh_script_file.name).readlines():
            logging.info('  ' + line.rstrip())
Ejemplo n.º 6
0
    def StripAndCopyExecutable(self):
        """Strips and copies the executable to the device."""
        if self.tool.NeedsDebugInfo():
            target_name = self.test_suite
        else:
            target_name = self.test_suite + '_' + self.device + '_stripped'
            should_strip = True
            if os.path.isfile(target_name):
                logging.info('Found target file %s' % target_name)
                target_mtime = os.stat(target_name).st_mtime
                source_mtime = os.stat(self.test_suite).st_mtime
                if target_mtime > source_mtime:
                    logging.info(
                        'Target mtime (%d) is newer than source (%d), assuming '
                        'no change.' % (target_mtime, source_mtime))
                    should_strip = False

            if should_strip:
                logging.info(
                    'Did not find up-to-date stripped binary. Generating a '
                    'new one (%s).' % target_name)
                # Whenever we generate a stripped binary, copy to the symbols dir. If we
                # aren't stripping a new binary, assume it's there.
                if self.symbols_dir:
                    if not os.path.exists(self.symbols_dir):
                        os.makedirs(self.symbols_dir)
                    shutil.copy(self.test_suite, self.symbols_dir)
                strip = os.environ['STRIP']
                cmd_helper.RunCmd([strip, self.test_suite, '-o', target_name])
        test_binary = constants.TEST_EXECUTABLE_DIR + '/' + self.test_suite_basename
        self.adb.PushIfNeeded(target_name, test_binary)
Ejemplo n.º 7
0
  def Run(self, port_pairs, tool, host_name):
    """Runs the forwarder.

    Args:
      port_pairs: A list of tuples (device_port, host_port) to forward. Note
                 that you can specify 0 as a device_port, in which case a
                 port will by dynamically assigned on the device. You can
                 get the number of the assigned port using the
                 DevicePortForHostPort method.
      tool: Tool class to use to get wrapper, if necessary, for executing the
            forwarder (see valgrind_tools.py).
      host_name: Address to forward to, must be addressable from the
                 host machine. Usually use loopback '127.0.0.1'.

    Raises:
      Exception on failure to forward the port.
    """
    host_adb_control_port = ports.AllocateTestServerPort()
    if not host_adb_control_port:
      raise Exception('Failed to allocate a TCP port in the host machine.')
    self._adb.PushIfNeeded(
        self._device_forwarder_path, Forwarder._DEVICE_FORWARDER_PATH)
    redirection_commands = [
        '%d:%d:%d:%s' % (host_adb_control_port, device, host,
                         host_name) for device, host in port_pairs]
    logging.info('Command format: <ADB port>:<Device port>' +
                 '[:<Forward to port>:<Forward to address>]')
    logging.info('Forwarding using commands: %s', redirection_commands)
    if cmd_helper.RunCmd(
        ['adb', '-s', self._adb._adb.GetSerialNumber(), 'forward',
         'tcp:%s' % host_adb_control_port,
         'localabstract:%s' % Forwarder._DEVICE_ADB_CONTROL_PORT]) != 0:
      raise Exception('Error while running adb forward.')

    (exit_code, output) = self._adb.GetShellCommandStatusAndOutput(
        '%s %s %s' % (tool.GetUtilWrapper(), Forwarder._DEVICE_FORWARDER_PATH,
                      Forwarder._DEVICE_ADB_CONTROL_PORT))
    if exit_code != 0:
      raise Exception(
          'Failed to start device forwarder:\n%s' % '\n'.join(output))

    for redirection_command in redirection_commands:
      (exit_code, output) = cmd_helper.GetCmdStatusAndOutput(
          [self._host_forwarder_path, redirection_command])
      if exit_code != 0:
        raise Exception('%s exited with %d:\n%s' % (
            self._host_forwarder_path, exit_code, '\n'.join(output)))
      tokens = output.split(':')
      if len(tokens) != 2:
        raise Exception('Unexpected host forwarder output "%s", ' +
                        'expected "device_port:host_port"' % output)
      device_port = int(tokens[0])
      host_port = int(tokens[1])
      self._host_to_device_port_map[host_port] = device_port
      logging.info('Forwarding device port: %d to host port: %d.', device_port,
                   host_port)
Ejemplo n.º 8
0
 def _TakeScreenshot(self, test):
     """Takes a screenshot from the device."""
     screenshot_tool = os.path.join(os.getenv('ANDROID_HOST_OUT'), 'bin',
                                    'screenshot2')
     screenshot_path = os.path.join(constants.CHROME_DIR, 'out_screenshots')
     if not os.path.exists(screenshot_path):
         os.mkdir(screenshot_path)
     screenshot_name = os.path.join(screenshot_path, test + '.png')
     logging.info('Taking screenshot named %s', screenshot_name)
     cmd_helper.RunCmd(
         [screenshot_tool, '-s', self.device, screenshot_name])
Ejemplo n.º 9
0
    def ZipAndCleanResults(dest_dir, dump_file_name):
        """A helper method to zip all debug information results into a dump file.

    Args:
      dest_dir: Dir path in where we put the dump file.
      dump_file_name: Desired name of the dump file. This method makes sure
                      '.zip' will be added as ext name.
    """
        if not dest_dir or not dump_file_name:
            return
        cmd_helper.RunCmd(['mkdir', '-p', dest_dir])
        log_basename = os.path.basename(dump_file_name)
        log_zip_file = os.path.join(dest_dir,
                                    os.path.splitext(log_basename)[0] + '.zip')
        logging.info('Zipping debug dumps into %s ...', log_zip_file)
        # Add new dumps into the zip file. The zip may exist already if previous
        # gtest also dumps the debug information. It's OK since we clean up the old
        # dumps in each build step.
        log_src_dir = os.path.join(tempfile.gettempdir(), 'gtest_debug_info')
        cmd_helper.RunCmd(['zip', '-q', '-r', log_zip_file, log_src_dir])
        assert os.path.exists(log_zip_file)
        assert os.path.exists(log_src_dir)
        shutil.rmtree(log_src_dir)
Ejemplo n.º 10
0
 def _TakeScreenshot(self, test):
   """Takes a screenshot from the device."""
   screenshot_tool = os.path.join(constants.CHROME_DIR,
       'third_party/android_tools/sdk/tools/monkeyrunner')
   screenshot_script = os.path.join(constants.CHROME_DIR,
       'build/android/monkeyrunner_screenshot.py')
   screenshot_path = os.path.join(constants.CHROME_DIR,
                                  'out_screenshots')
   if not os.path.exists(screenshot_path):
     os.mkdir(screenshot_path)
   screenshot_name = os.path.join(screenshot_path, test + '.png')
   logging.info('Taking screenshot named %s', screenshot_name)
   cmd_helper.RunCmd([screenshot_tool, screenshot_script,
                      '--serial', self.device,
                      '--file', screenshot_name])
 def _InitHostLocked(self):
     """Initializes the host forwarder process (only once)."""
     if self._host_adb_control_port:
         return
     self._host_adb_control_port = ports.AllocateTestServerPort()
     if not self._host_adb_control_port:
         raise Exception(
             'Failed to allocate a TCP port in the host machine.')
     if cmd_helper.RunCmd([
             'adb', '-s',
             self._adb._adb.GetSerialNumber(), 'forward',
             'tcp:%s' % self._host_adb_control_port,
             'localabstract:%s' % Forwarder._DEVICE_ADB_CONTROL_PORT
     ]) != 0:
         raise Exception('Error while running adb forward.')
Ejemplo n.º 12
0
    def StartRecordingLog(self, clear=True, filters=['*:v']):
        """Starts recording logcat output to a file.

    This call should come before running test, with calling StopRecordingLog
    following the tests.

    Args:
      clear: True if existing log output should be cleared.
      filters: A list of logcat filters to be used.
    """
        self.StopRecordingLog()
        if clear:
            cmd_helper.RunCmd(['adb', '-s', self.device, 'logcat', '-c'])
        logging.info('Start dumping log to %s ...', self.log_file_name)
        command = 'adb -s %s logcat -v threadtime %s > %s' % (
            self.device, ' '.join(filters), self.log_file_name)
        self.logcat_process = subprocess.Popen(command, shell=True)
Ejemplo n.º 13
0
 def _CopyLibraryAndJars(self):
   """Copy the shlib and jars into the apk source tree (if relevant)"""
   if self._native_library:
     destdir = os.path.join(self._output_directory, 'libs/' + self._target_abi)
     if not os.path.exists(destdir):
       os.makedirs(destdir)
     dest = os.path.join(destdir, os.path.basename(self._native_library))
     logging.warn('strip %s --> %s' % (self._native_library, dest))
     strip = os.environ['STRIP']
     cmd_helper.RunCmd(
         [strip, '--strip-unneeded', self._native_library, '-o', dest])
   if self._jars:
     destdir = os.path.join(self._output_directory, 'libs')
     if not os.path.exists(destdir):
       os.makedirs(destdir)
     for jar in self._jars:
       dest = os.path.join(destdir, os.path.basename(jar))
       logging.warn('%s --> %s' % (jar, dest))
       shutil.copyfile(jar, dest)
Ejemplo n.º 14
0
    def StripAndCopyExecutable(self):
        """Strips and copies the executable to the device."""
        if self.tool.NeedsDebugInfo():
            target_name = self.test_suite
        elif self.test_suite_basename == 'webkit_unit_tests':
            # webkit_unit_tests has been stripped in build step.
            target_name = self.test_suite
        else:
            target_name = self.test_suite + '_' + self.device + '_stripped'
            should_strip = True
            if os.path.isfile(target_name):
                logging.info('Found target file %s' % target_name)
                target_mtime = os.stat(target_name).st_mtime
                source_mtime = os.stat(self.test_suite).st_mtime
                if target_mtime > source_mtime:
                    logging.info(
                        'Target mtime (%d) is newer than source (%d), assuming '
                        'no change.' % (target_mtime, source_mtime))
                    should_strip = False

            if should_strip:
                logging.info(
                    'Did not find up-to-date stripped binary. Generating a '
                    'new one (%s).' % target_name)
                # Whenever we generate a stripped binary, copy to the symbols dir. If we
                # aren't stripping a new binary, assume it's there.
                if self.symbols_dir:
                    if not os.path.exists(self.symbols_dir):
                        os.makedirs(self.symbols_dir)
                    shutil.copy(self.test_suite, self.symbols_dir)
                strip = os.environ['STRIP']
                cmd_helper.RunCmd([strip, self.test_suite, '-o', target_name])
        test_binary = '/data/local/' + self.test_suite_basename
        self.adb.PushIfNeeded(target_name, test_binary)

        if self.test_suite_basename == 'ui_unittests':
            self.adb.PushIfNeeded(self.test_suite_dirname + '/chrome.pak',
                                  '/data/local/tmp/paks/chrome.pak')
            self.adb.PushIfNeeded(
                self.test_suite_dirname + '/locales/en-US.pak',
                '/data/local/tmp/paks/en-US.pak')
 def StartAdbServer(self):
     """Start adb server."""
     adb_cmd = ['adb', 'start-server']
     return cmd_helper.RunCmd(adb_cmd)
 def KillAdbServer(self):
     """Kill adb server."""
     adb_cmd = ['adb', 'kill-server']
     return cmd_helper.RunCmd(adb_cmd)