#!/usr/bin/python2 # # Copyright 2010 Google Inc. All Rights Reserved. """Script to compare ChromeOS benchmarks Inputs: <perflab-output directory 1 - baseline> <perflab-output directory 2 - results> --csv - comma separated results This script doesn't really know much about benchmarks. It simply looks for similarly names directories and a results.txt file, and compares the results and presents it, along with a geometric mean. """ from __future__ import print_function __author__ = 'bjanakiraman@google.com (Bhaskar Janakiraman)' import glob import math import argparse import re import sys from cros_utils import command_executer BENCHDIRS = ('%s/default/default/*/gcc-4.4.3-glibc-2.11.1-grte-k8-opt/ref/*' '/results.txt') # Common initializations cmd_executer = command_executer.GetCommandExecuter() def Usage(parser, message): print('ERROR: %s' % message) parser.print_help() sys.exit(0) def GetStats(in_file): """Return stats from file""" f = open(in_file, 'r') pairs = [] for l in f: line = l.strip() # Look for match lines like the following: # METRIC isolated TotalTime_ms (down, scalar) trial_run_0: ['1524.4'] # METRIC isolated isolated_walltime (down, scalar) trial_run_0: \ # ['167.407445192'] m = re.match(r"METRIC\s+isolated\s+(\S+).*\['(\d+(?:\.\d+)?)'\]", line) if not m: continue metric = m.group(1) if re.match(r'isolated_walltime', metric): continue value = float(m.group(2)) pairs.append((metric, value)) return dict(pairs) def PrintDash(n): tmpstr = '' for _ in range(n): tmpstr += '-' print(tmpstr) def PrintHeaderCSV(hdr): tmpstr = '' for i in range(len(hdr)): if tmpstr != '': tmpstr += ',' tmpstr += hdr[i] print(tmpstr) def PrintHeader(hdr): tot_len = len(hdr) PrintDash(tot_len * 15) tmpstr = '' for i in range(len(hdr)): tmpstr += '%15.15s' % hdr[i] print(tmpstr) PrintDash(tot_len * 15) def Main(argv): """Compare Benchmarks.""" # Common initializations parser = argparse.ArgumentParser() parser.add_argument('-c', '--csv', dest='csv_output', action='store_true', default=False, help='Output in csv form.') parser.add_argument('args', nargs='+', help='positional arguments: ' '<baseline-output-dir> <results-output-dir>') options = parser.parse_args(argv[1:]) # validate args if len(options.args) != 2: Usage(parser, 'Needs <baseline output dir> <results output dir>') base_dir = options.args[0] res_dir = options.args[1] # find res benchmarks that have results resbenches_glob = BENCHDIRS % res_dir resbenches = glob.glob(resbenches_glob) basebenches_glob = BENCHDIRS % base_dir basebenches = glob.glob(basebenches_glob) to_compare = [] for resbench in resbenches: tmp = resbench.replace(res_dir, base_dir, 1) if tmp in basebenches: to_compare.append((resbench, tmp)) for (resfile, basefile) in to_compare: stats = GetStats(resfile) basestats = GetStats(basefile) # Print a header # benchname (remove results.txt), basetime, restime, %speed-up hdr = [] benchname = re.split('/', resfile)[-2:-1][0] benchname = benchname.replace('chromeos__', '', 1) hdr.append(benchname) hdr.append('basetime') hdr.append('restime') hdr.append('%speed up') if options.csv_output: PrintHeaderCSV(hdr) else: PrintHeader(hdr) # For geomean computations prod = 1.0 count = 0 for key in stats.keys(): if key in basestats.keys(): # ignore very small values. if stats[key] < 0.01: continue count = count + 1 prod = prod * (stats[key] / basestats[key]) speedup = (basestats[key] - stats[key]) / basestats[key] speedup = speedup * 100.0 if options.csv_output: print('%s,%f,%f,%f' % (key, basestats[key], stats[key], speedup)) else: print('%15.15s%15.2f%15.2f%14.2f%%' % (key, basestats[key], stats[key], speedup)) prod = math.exp(1.0 / count * math.log(prod)) prod = (1.0 - prod) * 100 if options.csv_output: print('%s,,,%f' % ('Geomean', prod)) else: print('%15.15s%15.15s%15.15s%14.2f%%' % ('Geomean', '', '', prod)) print('') return 0 if __name__ == '__main__': retval = Main(sys.argv) sys.exit(retval)