| Index: tools/llvm_coverage_run.py
|
| diff --git a/tools/llvm_coverage_run.py b/tools/llvm_coverage_run.py
|
| index e0d0ff6f5a6cc00bc78f2844cb9f46d3b3e49d1d..8b497506e64d3dfb59911f98d28a66bb3c2fe84c 100755
|
| --- a/tools/llvm_coverage_run.py
|
| +++ b/tools/llvm_coverage_run.py
|
| @@ -8,12 +8,8 @@
|
|
|
|
|
| import argparse
|
| -import json
|
| import os
|
| -import re
|
| -import shlex
|
| import subprocess
|
| -import sys
|
|
|
|
|
| BUILDTYPE = 'Coverage'
|
| @@ -22,51 +18,6 @@ PROFILE_DATA_MERGED = 'prof_merged'
|
| SKIA_OUT = 'SKIA_OUT'
|
|
|
|
|
| -def _fix_filename(filename):
|
| - """Return a filename which we can use to identify the file.
|
| -
|
| - The file paths printed by llvm-cov take the form:
|
| -
|
| - /path/to/repo/out/dir/../../src/filename.cpp
|
| -
|
| - And then they're truncated to 22 characters with leading ellipses:
|
| -
|
| - ...../../src/filename.cpp
|
| -
|
| - This makes it really tough to determine whether the file actually belongs in
|
| - the Skia repo. This function strips out the leading junk so that, if the file
|
| - exists in the repo, the returned string matches the end of some relative path
|
| - in the repo. This doesn't guarantee correctness, but it's about as close as
|
| - we can get.
|
| - """
|
| - return filename.split('..')[-1].lstrip('./')
|
| -
|
| -
|
| -def _filter_results(results):
|
| - """Filter out any results for files not in the Skia repo.
|
| -
|
| - We run through the list of checked-in files and determine whether each file
|
| - belongs in the repo. Unfortunately, llvm-cov leaves us with fragments of the
|
| - file paths, so we can't guarantee accuracy. See the docstring for
|
| - _fix_filename for more details.
|
| - """
|
| - all_files = subprocess.check_output(['git', 'ls-files']).splitlines()
|
| - filtered = []
|
| - for percent, filename in results:
|
| - new_file = _fix_filename(filename)
|
| - matched = []
|
| - for f in all_files:
|
| - if f.endswith(new_file):
|
| - matched.append(f)
|
| - if len(matched) == 1:
|
| - filtered.append((percent, matched[0]))
|
| - elif len(matched) > 1:
|
| - print >> sys.stderr, ('WARNING: multiple matches for %s; skipping:\n\t%s'
|
| - % (new_file, '\n\t'.join(matched)))
|
| - print 'Filtered out %d files.' % (len(results) - len(filtered))
|
| - return filtered
|
| -
|
| -
|
| def _get_out_dir():
|
| """Determine the location for compiled binaries."""
|
| return os.path.join(os.environ.get(SKIA_OUT, os.path.realpath('out')),
|
| @@ -88,66 +39,11 @@ def run_coverage(cmd):
|
| finally:
|
| os.remove(PROFILE_DATA)
|
| try:
|
| - report = subprocess.check_output(
|
| - ['llvm-cov', 'report', '-instr-profile', PROFILE_DATA_MERGED,
|
| - binary_path])
|
| + return subprocess.check_output(['llvm-cov', 'show', '-no-colors',
|
| + '-instr-profile', PROFILE_DATA_MERGED,
|
| + binary_path])
|
| finally:
|
| os.remove(PROFILE_DATA_MERGED)
|
| - results = []
|
| - for line in report.splitlines()[2:-2]:
|
| - filename, _, _, cover, _, _ = shlex.split(line)
|
| - percent = float(cover.split('%')[0])
|
| - results.append((percent, filename))
|
| - results = _filter_results(results)
|
| - results.sort()
|
| - return results
|
| -
|
| -
|
| -def _testname(filename):
|
| - """Transform the file name into an ingestible test name."""
|
| - return re.sub(r'[^a-zA-Z0-9]', '_', filename)
|
| -
|
| -
|
| -def _nanobench_json(results, properties, key):
|
| - """Return the results in JSON format like that produced by nanobench."""
|
| - rv = {}
|
| - # Copy over the properties first, then set the 'key' and 'results' keys,
|
| - # in order to avoid bad formatting in case the user passes in a properties
|
| - # dict containing those keys.
|
| - rv.update(properties)
|
| - rv['key'] = key
|
| - rv['results'] = {
|
| - _testname(f): {
|
| - 'coverage': {
|
| - 'percent': percent,
|
| - 'options': {
|
| - 'fullname': f,
|
| - 'dir': os.path.dirname(f),
|
| - },
|
| - },
|
| - } for percent, f in results
|
| - }
|
| - return rv
|
| -
|
| -
|
| -def _parse_key_value(kv_list):
|
| - """Return a dict whose key/value pairs are derived from the given list.
|
| -
|
| - For example:
|
| -
|
| - ['k1', 'v1', 'k2', 'v2']
|
| - becomes:
|
| -
|
| - {'k1': 'v1',
|
| - 'k2': 'v2'}
|
| - """
|
| - if len(kv_list) % 2 != 0:
|
| - raise Exception('Invalid key/value pairs: %s' % kv_list)
|
| -
|
| - rv = {}
|
| - for i in xrange(len(kv_list) / 2):
|
| - rv[kv_list[i*2]] = kv_list[i*2+1]
|
| - return rv
|
|
|
|
|
| def main():
|
| @@ -155,34 +51,12 @@ def main():
|
| # Parse args.
|
| parser = argparse.ArgumentParser()
|
| parser.add_argument('--outResultsFile')
|
| - parser.add_argument(
|
| - '--key', metavar='key_or_value', nargs='+',
|
| - help='key/value pairs identifying this bot.')
|
| - parser.add_argument(
|
| - '--properties', metavar='key_or_value', nargs='+',
|
| - help='key/value pairs representing properties of this build.')
|
| args, cmd = parser.parse_known_args()
|
|
|
| - # We still need to pass the args we stripped out to DM.
|
| - cmd.append('--key')
|
| - cmd.extend(args.key)
|
| - cmd.append('--properties')
|
| - cmd.extend(args.properties)
|
| -
|
| - # Parse the key and properties for use in the nanobench JSON output.
|
| - key = _parse_key_value(args.key)
|
| - properties = _parse_key_value(args.properties)
|
| -
|
| # Run coverage.
|
| - results = run_coverage(cmd)
|
| -
|
| - # Write results.
|
| - format_results = _nanobench_json(results, properties, key)
|
| - if args.outResultsFile:
|
| - with open(args.outResultsFile, 'w') as f:
|
| - json.dump(format_results, f)
|
| - else:
|
| - print json.dumps(format_results, indent=4, sort_keys=True)
|
| + report = run_coverage(cmd)
|
| + with open(args.outResultsFile, 'w') as f:
|
| + f.write(report)
|
|
|
|
|
| if __name__ == '__main__':
|
|
|