1*0e209d39SAndroid Build Coastguard Worker#!/usr/local/bin/perl 2*0e209d39SAndroid Build Coastguard Worker# *********************************************************************** 3*0e209d39SAndroid Build Coastguard Worker# * COPYRIGHT: 4*0e209d39SAndroid Build Coastguard Worker# * © 2016 and later: Unicode, Inc. and others. 5*0e209d39SAndroid Build Coastguard Worker# * License & terms of use: http://www.unicode.org/copyright.html 6*0e209d39SAndroid Build Coastguard Worker# * Copyright (c) 2002-2006, International Business Machines Corporation 7*0e209d39SAndroid Build Coastguard Worker# * and others. All Rights Reserved. 8*0e209d39SAndroid Build Coastguard Worker# *********************************************************************** 9*0e209d39SAndroid Build Coastguard Worker 10*0e209d39SAndroid Build Coastguard Workeruse strict; 11*0e209d39SAndroid Build Coastguard Worker 12*0e209d39SAndroid Build Coastguard Worker#use Dataset; 13*0e209d39SAndroid Build Coastguard Workeruse Format; 14*0e209d39SAndroid Build Coastguard Workeruse Output; 15*0e209d39SAndroid Build Coastguard Worker 16*0e209d39SAndroid Build Coastguard Workermy $VERBOSE = 0; 17*0e209d39SAndroid Build Coastguard Workermy $DEBUG = 1; 18*0e209d39SAndroid Build Coastguard Workermy $start_l = ""; #formatting help 19*0e209d39SAndroid Build Coastguard Workermy $end_l = ""; 20*0e209d39SAndroid Build Coastguard Workermy @testArgs; # different kinds of tests we want to do 21*0e209d39SAndroid Build Coastguard Workermy $datadir = "data"; 22*0e209d39SAndroid Build Coastguard Workermy $extraArgs; # stuff that always gets passed to the test program 23*0e209d39SAndroid Build Coastguard Worker 24*0e209d39SAndroid Build Coastguard Worker 25*0e209d39SAndroid Build Coastguard Workermy $iterCount = 0; 26*0e209d39SAndroid Build Coastguard Workermy $NUMPASSES = 4; 27*0e209d39SAndroid Build Coastguard Workermy $TIME = 2; 28*0e209d39SAndroid Build Coastguard Workermy $ITERATIONS; #Added by Doug 29*0e209d39SAndroid Build Coastguard Workermy $DATADIR; 30*0e209d39SAndroid Build Coastguard Worker 31*0e209d39SAndroid Build Coastguard Workersub setupOptions { 32*0e209d39SAndroid Build Coastguard Worker my %options = %{shift @_}; 33*0e209d39SAndroid Build Coastguard Worker 34*0e209d39SAndroid Build Coastguard Worker if($options{"time"}) { 35*0e209d39SAndroid Build Coastguard Worker $TIME = $options{"time"}; 36*0e209d39SAndroid Build Coastguard Worker } 37*0e209d39SAndroid Build Coastguard Worker 38*0e209d39SAndroid Build Coastguard Worker if($options{"passes"}) { 39*0e209d39SAndroid Build Coastguard Worker $NUMPASSES = $options{"passes"}; 40*0e209d39SAndroid Build Coastguard Worker } 41*0e209d39SAndroid Build Coastguard Worker 42*0e209d39SAndroid Build Coastguard Worker if($options{"dataDir"}) { 43*0e209d39SAndroid Build Coastguard Worker $DATADIR = $options{"dataDir"}; 44*0e209d39SAndroid Build Coastguard Worker } 45*0e209d39SAndroid Build Coastguard Worker 46*0e209d39SAndroid Build Coastguard Worker # Added by Doug 47*0e209d39SAndroid Build Coastguard Worker if ($options{"iterations"}) { 48*0e209d39SAndroid Build Coastguard Worker $ITERATIONS = $options{"iterations"}; 49*0e209d39SAndroid Build Coastguard Worker } 50*0e209d39SAndroid Build Coastguard Worker} 51*0e209d39SAndroid Build Coastguard Worker 52*0e209d39SAndroid Build Coastguard Workersub runTests { 53*0e209d39SAndroid Build Coastguard Worker debug("Enter runTest in PerfFramework4j\n"); 54*0e209d39SAndroid Build Coastguard Worker my $options = shift; 55*0e209d39SAndroid Build Coastguard Worker my @programs; 56*0e209d39SAndroid Build Coastguard Worker my $tests = shift; 57*0e209d39SAndroid Build Coastguard Worker my %datafiles; 58*0e209d39SAndroid Build Coastguard Worker if($#_ >= 0) { # maybe no files/locales 59*0e209d39SAndroid Build Coastguard Worker my $datafiles = shift; 60*0e209d39SAndroid Build Coastguard Worker if($datafiles) { 61*0e209d39SAndroid Build Coastguard Worker %datafiles = %{$datafiles}; 62*0e209d39SAndroid Build Coastguard Worker } 63*0e209d39SAndroid Build Coastguard Worker } 64*0e209d39SAndroid Build Coastguard Worker setupOutput($options); 65*0e209d39SAndroid Build Coastguard Worker setupOptions($options); 66*0e209d39SAndroid Build Coastguard Worker 67*0e209d39SAndroid Build Coastguard Worker my($locale, $iter, $data, $program, $args, $variable); 68*0e209d39SAndroid Build Coastguard Worker# 69*0e209d39SAndroid Build Coastguard Worker# Outer loop runs through the locales to test 70*0e209d39SAndroid Build Coastguard Worker# 71*0e209d39SAndroid Build Coastguard Worker if (%datafiles) { 72*0e209d39SAndroid Build Coastguard Worker foreach $locale (sort keys %datafiles ) { 73*0e209d39SAndroid Build Coastguard Worker foreach $data (@{ $datafiles{$locale} }) { 74*0e209d39SAndroid Build Coastguard Worker closeTable; 75*0e209d39SAndroid Build Coastguard Worker my $locdata = ""; 76*0e209d39SAndroid Build Coastguard Worker if(!($locale eq "")) { 77*0e209d39SAndroid Build Coastguard Worker $locdata = "<b>Locale:</b> $locale<br>"; 78*0e209d39SAndroid Build Coastguard Worker } 79*0e209d39SAndroid Build Coastguard Worker $locdata .= "<b>Datafile:</b> $data<br>"; 80*0e209d39SAndroid Build Coastguard Worker startTest($locdata); 81*0e209d39SAndroid Build Coastguard Worker 82*0e209d39SAndroid Build Coastguard Worker if($DATADIR) { 83*0e209d39SAndroid Build Coastguard Worker compareLoop ($tests, $locale, $DATADIR."/".$data); 84*0e209d39SAndroid Build Coastguard Worker } else { 85*0e209d39SAndroid Build Coastguard Worker compareLoop ($tests, $locale, $data); 86*0e209d39SAndroid Build Coastguard Worker } 87*0e209d39SAndroid Build Coastguard Worker } 88*0e209d39SAndroid Build Coastguard Worker } 89*0e209d39SAndroid Build Coastguard Worker } else { 90*0e209d39SAndroid Build Coastguard Worker compareLoop($tests); 91*0e209d39SAndroid Build Coastguard Worker } 92*0e209d39SAndroid Build Coastguard Worker closeOutput(); 93*0e209d39SAndroid Build Coastguard Worker} 94*0e209d39SAndroid Build Coastguard Worker 95*0e209d39SAndroid Build Coastguard Workersub compareLoop { 96*0e209d39SAndroid Build Coastguard Worker #debug("enter compareLoop\n"); 97*0e209d39SAndroid Build Coastguard Worker 98*0e209d39SAndroid Build Coastguard Worker my $tests = shift; 99*0e209d39SAndroid Build Coastguard Worker #debug("tests $tests"); 100*0e209d39SAndroid Build Coastguard Worker #my @tests = @{$tests}; 101*0e209d39SAndroid Build Coastguard Worker my %tests = %{$tests}; 102*0e209d39SAndroid Build Coastguard Worker #debug("tests $tests"); 103*0e209d39SAndroid Build Coastguard Worker my $locale = shift; 104*0e209d39SAndroid Build Coastguard Worker my $datafile = shift; 105*0e209d39SAndroid Build Coastguard Worker my $locAndData = ""; 106*0e209d39SAndroid Build Coastguard Worker if($locale) { 107*0e209d39SAndroid Build Coastguard Worker $locAndData .= " -L $locale"; 108*0e209d39SAndroid Build Coastguard Worker } 109*0e209d39SAndroid Build Coastguard Worker 110*0e209d39SAndroid Build Coastguard Worker if($datafile) { 111*0e209d39SAndroid Build Coastguard Worker $locAndData .= " -f $datafile"; 112*0e209d39SAndroid Build Coastguard Worker } 113*0e209d39SAndroid Build Coastguard Worker 114*0e209d39SAndroid Build Coastguard Worker my $args; 115*0e209d39SAndroid Build Coastguard Worker my ($i, $j, $aref); 116*0e209d39SAndroid Build Coastguard Worker foreach $i ( sort keys %tests ) { 117*0e209d39SAndroid Build Coastguard Worker #debug("Test: $i\n"); 118*0e209d39SAndroid Build Coastguard Worker $aref = $tests{$i}; 119*0e209d39SAndroid Build Coastguard Worker my @timedata; 120*0e209d39SAndroid Build Coastguard Worker my @iterPerPass; 121*0e209d39SAndroid Build Coastguard Worker my @noopers; 122*0e209d39SAndroid Build Coastguard Worker my @noevents; 123*0e209d39SAndroid Build Coastguard Worker 124*0e209d39SAndroid Build Coastguard Worker my $program; 125*0e209d39SAndroid Build Coastguard Worker my @argsAndTest; 126*0e209d39SAndroid Build Coastguard Worker for $j ( 0 .. $#{$aref} ) { 127*0e209d39SAndroid Build Coastguard Worker # first we calibrate. Use time from somewhere 128*0e209d39SAndroid Build Coastguard Worker # first test is used for calibration 129*0e209d39SAndroid Build Coastguard Worker ################## 130*0e209d39SAndroid Build Coastguard Worker # ($program, @argsAndTest) = split(/\ /, @{ $tests{$i} }[$j]); 131*0e209d39SAndroid Build Coastguard Worker # #Modified by Doug 132*0e209d39SAndroid Build Coastguard Worker # my $commandLine; 133*0e209d39SAndroid Build Coastguard Worker # if ($ITERATIONS) { 134*0e209d39SAndroid Build Coastguard Worker # $commandLine = "$program -i $ITERATIONS -p $NUMPASSES $locAndData @argsAndTest"; 135*0e209d39SAndroid Build Coastguard Worker # } else { 136*0e209d39SAndroid Build Coastguard Worker # $commandLine = "$program -t $TIME -p $NUMPASSES $locAndData @argsAndTest"; 137*0e209d39SAndroid Build Coastguard Worker # } 138*0e209d39SAndroid Build Coastguard Worker ###################### 139*0e209d39SAndroid Build Coastguard Worker ###################### 140*0e209d39SAndroid Build Coastguard Worker my $custArgs; 141*0e209d39SAndroid Build Coastguard Worker my $testCommand = @{ $tests{$i} }[$j]; 142*0e209d39SAndroid Build Coastguard Worker if ($testCommand =~/--/) { 143*0e209d39SAndroid Build Coastguard Worker $custArgs = $& . $'; #The matched part and the right part 144*0e209d39SAndroid Build Coastguard Worker $testCommand = $`; #The left part for further processing 145*0e209d39SAndroid Build Coastguard Worker } else { $custArgs = ''; } 146*0e209d39SAndroid Build Coastguard Worker ($program, @argsAndTest) = split(/\ /, $testCommand); 147*0e209d39SAndroid Build Coastguard Worker my $commandLine; 148*0e209d39SAndroid Build Coastguard Worker if ($ITERATIONS) { 149*0e209d39SAndroid Build Coastguard Worker $commandLine = "$program @argsAndTest -i $ITERATIONS -p $NUMPASSES $locAndData $custArgs"; 150*0e209d39SAndroid Build Coastguard Worker } else { 151*0e209d39SAndroid Build Coastguard Worker $commandLine = "$program @argsAndTest -t $TIME -p $NUMPASSES $locAndData $custArgs"; 152*0e209d39SAndroid Build Coastguard Worker } 153*0e209d39SAndroid Build Coastguard Worker #debug("custArgs:$custArgs\n"); 154*0e209d39SAndroid Build Coastguard Worker #################### 155*0e209d39SAndroid Build Coastguard Worker 156*0e209d39SAndroid Build Coastguard Worker my @res = measure1($commandLine); 157*0e209d39SAndroid Build Coastguard Worker store("$i, $program @argsAndTest", @res); 158*0e209d39SAndroid Build Coastguard Worker 159*0e209d39SAndroid Build Coastguard Worker push(@iterPerPass, shift(@res)); 160*0e209d39SAndroid Build Coastguard Worker push(@noopers, shift(@res)); 161*0e209d39SAndroid Build Coastguard Worker my @data = @{ shift(@res) }; 162*0e209d39SAndroid Build Coastguard Worker if($#res >= 0) { 163*0e209d39SAndroid Build Coastguard Worker push(@noevents, shift(@res)); 164*0e209d39SAndroid Build Coastguard Worker } 165*0e209d39SAndroid Build Coastguard Worker 166*0e209d39SAndroid Build Coastguard Worker 167*0e209d39SAndroid Build Coastguard Worker shift(@data) if (@data > 1); # discard first run 168*0e209d39SAndroid Build Coastguard Worker 169*0e209d39SAndroid Build Coastguard Worker #debug("data is @data\n"); 170*0e209d39SAndroid Build Coastguard Worker my $ds = Dataset->new(@data); 171*0e209d39SAndroid Build Coastguard Worker 172*0e209d39SAndroid Build Coastguard Worker push(@timedata, $ds); 173*0e209d39SAndroid Build Coastguard Worker } 174*0e209d39SAndroid Build Coastguard Worker 175*0e209d39SAndroid Build Coastguard Worker outputRow($i, \@iterPerPass, \@noopers, \@timedata, \@noevents); 176*0e209d39SAndroid Build Coastguard Worker } 177*0e209d39SAndroid Build Coastguard Worker 178*0e209d39SAndroid Build Coastguard Worker} 179*0e209d39SAndroid Build Coastguard Worker 180*0e209d39SAndroid Build Coastguard Worker#--------------------------------------------------------------------- 181*0e209d39SAndroid Build Coastguard Worker# Measure a given test method with a give test pattern using the 182*0e209d39SAndroid Build Coastguard Worker# global run parameters. 183*0e209d39SAndroid Build Coastguard Worker# 184*0e209d39SAndroid Build Coastguard Worker# @param the method to run 185*0e209d39SAndroid Build Coastguard Worker# @param the pattern defining characters to test 186*0e209d39SAndroid Build Coastguard Worker# @param if >0 then the number of iterations per pass. If <0 then 187*0e209d39SAndroid Build Coastguard Worker# (negative of) the number of seconds per pass. 188*0e209d39SAndroid Build Coastguard Worker# 189*0e209d39SAndroid Build Coastguard Worker# @return array of: 190*0e209d39SAndroid Build Coastguard Worker# [0] iterations per pass 191*0e209d39SAndroid Build Coastguard Worker# [1] events per iteration 192*0e209d39SAndroid Build Coastguard Worker# [2..] ms reported for each pass, in order 193*0e209d39SAndroid Build Coastguard Worker# 194*0e209d39SAndroid Build Coastguard Workersub measure1 { 195*0e209d39SAndroid Build Coastguard Worker # run passes 196*0e209d39SAndroid Build Coastguard Worker my @t = callProg(shift); #"$program $args $argsAndTest"); 197*0e209d39SAndroid Build Coastguard Worker my @ms = (); 198*0e209d39SAndroid Build Coastguard Worker my @b; # scratch 199*0e209d39SAndroid Build Coastguard Worker for my $a (@t) { 200*0e209d39SAndroid Build Coastguard Worker # $a->[0]: method name, corresponds to $method 201*0e209d39SAndroid Build Coastguard Worker # $a->[1]: 'begin' data, == $iterCount 202*0e209d39SAndroid Build Coastguard Worker # $a->[2]: 'end' data, of the form <ms> <eventsPerIter> 203*0e209d39SAndroid Build Coastguard Worker # $a->[3...]: gc messages from JVM during pass 204*0e209d39SAndroid Build Coastguard Worker @b = split(/\s+/, $a->[2]); 205*0e209d39SAndroid Build Coastguard Worker #push(@ms, $b[0]); 206*0e209d39SAndroid Build Coastguard Worker push(@ms, shift(@b)); 207*0e209d39SAndroid Build Coastguard Worker } 208*0e209d39SAndroid Build Coastguard Worker my $iterCount = shift(@b); 209*0e209d39SAndroid Build Coastguard Worker my $operationsPerIter = shift(@b); 210*0e209d39SAndroid Build Coastguard Worker my $eventsPerIter; 211*0e209d39SAndroid Build Coastguard Worker if($#b >= 0) { 212*0e209d39SAndroid Build Coastguard Worker $eventsPerIter = shift(@b); 213*0e209d39SAndroid Build Coastguard Worker } 214*0e209d39SAndroid Build Coastguard Worker 215*0e209d39SAndroid Build Coastguard Worker# out("Iterations per pass: $iterCount<BR>\n"); 216*0e209d39SAndroid Build Coastguard Worker# out("Events per iteration: $eventsPerIter<BR>\n"); 217*0e209d39SAndroid Build Coastguard Worker# debug("Iterations per pass: $iterCount<BR>\n"); 218*0e209d39SAndroid Build Coastguard Worker# if($eventsPerIter) { 219*0e209d39SAndroid Build Coastguard Worker# debug("Events per iteration: $eventsPerIter<BR>\n"); 220*0e209d39SAndroid Build Coastguard Worker# } 221*0e209d39SAndroid Build Coastguard Worker 222*0e209d39SAndroid Build Coastguard Worker my @ms_str = @ms; 223*0e209d39SAndroid Build Coastguard Worker $ms_str[0] .= " (discarded)" if (@ms_str > 1); 224*0e209d39SAndroid Build Coastguard Worker# out("Raw times (ms/pass): ", join(", ", @ms_str), "<BR>\n"); 225*0e209d39SAndroid Build Coastguard Worker debug("Raw times (ms/pass): ", join(", ", @ms_str), "<BR>\n"); 226*0e209d39SAndroid Build Coastguard Worker if($eventsPerIter) { 227*0e209d39SAndroid Build Coastguard Worker ($iterCount, $operationsPerIter, \@ms, $eventsPerIter); 228*0e209d39SAndroid Build Coastguard Worker } else { 229*0e209d39SAndroid Build Coastguard Worker ($iterCount, $operationsPerIter, \@ms); 230*0e209d39SAndroid Build Coastguard Worker } 231*0e209d39SAndroid Build Coastguard Worker} 232*0e209d39SAndroid Build Coastguard Worker 233*0e209d39SAndroid Build Coastguard Worker 234*0e209d39SAndroid Build Coastguard Worker 235*0e209d39SAndroid Build Coastguard Worker#--------------------------------------------------------------------- 236*0e209d39SAndroid Build Coastguard Worker# Measure a given test method with a give test pattern using the 237*0e209d39SAndroid Build Coastguard Worker# global run parameters. 238*0e209d39SAndroid Build Coastguard Worker# 239*0e209d39SAndroid Build Coastguard Worker# @param the method to run 240*0e209d39SAndroid Build Coastguard Worker# @param the pattern defining characters to test 241*0e209d39SAndroid Build Coastguard Worker# @param if >0 then the number of iterations per pass. If <0 then 242*0e209d39SAndroid Build Coastguard Worker# (negative of) the number of seconds per pass. 243*0e209d39SAndroid Build Coastguard Worker# 244*0e209d39SAndroid Build Coastguard Worker# @return a Dataset object, scaled by iterations per pass and 245*0e209d39SAndroid Build Coastguard Worker# events per iteration, to give time per event 246*0e209d39SAndroid Build Coastguard Worker# 247*0e209d39SAndroid Build Coastguard Workersub measure2 { 248*0e209d39SAndroid Build Coastguard Worker my @res = measure1(@_); 249*0e209d39SAndroid Build Coastguard Worker my $iterPerPass = shift(@res); 250*0e209d39SAndroid Build Coastguard Worker my $operationsPerIter = shift(@res); 251*0e209d39SAndroid Build Coastguard Worker my @data = @{ shift(@res) }; 252*0e209d39SAndroid Build Coastguard Worker my $eventsPerIter = shift(@res); 253*0e209d39SAndroid Build Coastguard Worker 254*0e209d39SAndroid Build Coastguard Worker 255*0e209d39SAndroid Build Coastguard Worker shift(@data) if (@data > 1); # discard first run 256*0e209d39SAndroid Build Coastguard Worker 257*0e209d39SAndroid Build Coastguard Worker my $ds = Dataset->new(@data); 258*0e209d39SAndroid Build Coastguard Worker #$ds->setScale(1.0e-3 / ($iterPerPass * $operationsPerIter)); 259*0e209d39SAndroid Build Coastguard Worker ($ds, $iterPerPass, $operationsPerIter, $eventsPerIter); 260*0e209d39SAndroid Build Coastguard Worker} 261*0e209d39SAndroid Build Coastguard Worker 262*0e209d39SAndroid Build Coastguard Worker 263*0e209d39SAndroid Build Coastguard Worker#--------------------------------------------------------------------- 264*0e209d39SAndroid Build Coastguard Worker# Invoke program and capture results, passing it the given parameters. 265*0e209d39SAndroid Build Coastguard Worker# 266*0e209d39SAndroid Build Coastguard Worker# @param the method to run 267*0e209d39SAndroid Build Coastguard Worker# @param the number of iterations, or if negative, the duration 268*0e209d39SAndroid Build Coastguard Worker# in seconds. If more than on pass is desired, pass in 269*0e209d39SAndroid Build Coastguard Worker# a string, e.g., "100 100 100". 270*0e209d39SAndroid Build Coastguard Worker# @param the pattern defining characters to test 271*0e209d39SAndroid Build Coastguard Worker# 272*0e209d39SAndroid Build Coastguard Worker# @return an array of results. Each result is an array REF 273*0e209d39SAndroid Build Coastguard Worker# describing one pass. The array REF contains: 274*0e209d39SAndroid Build Coastguard Worker# ->[0]: The method name as reported 275*0e209d39SAndroid Build Coastguard Worker# ->[1]: The params on the '= <meth> begin ...' line 276*0e209d39SAndroid Build Coastguard Worker# ->[2]: The params on the '= <meth> end ...' line 277*0e209d39SAndroid Build Coastguard Worker# ->[3..]: GC messages from the JVM, if any 278*0e209d39SAndroid Build Coastguard Worker# 279*0e209d39SAndroid Build Coastguard Workersub callProg { 280*0e209d39SAndroid Build Coastguard Worker my $cmd = shift; 281*0e209d39SAndroid Build Coastguard Worker #my $pat = shift; 282*0e209d39SAndroid Build Coastguard Worker #my $n = shift; 283*0e209d39SAndroid Build Coastguard Worker 284*0e209d39SAndroid Build Coastguard Worker #my $cmd = "java -cp c:\\dev\\myicu4j\\classes $TESTCLASS $method $n $pat"; 285*0e209d39SAndroid Build Coastguard Worker debug( "[$cmd]\n"); # for debugging 286*0e209d39SAndroid Build Coastguard Worker open(PIPE, "$cmd|") or die "Can't run \"$cmd\""; 287*0e209d39SAndroid Build Coastguard Worker my @out; 288*0e209d39SAndroid Build Coastguard Worker while (<PIPE>) { 289*0e209d39SAndroid Build Coastguard Worker push(@out, $_); 290*0e209d39SAndroid Build Coastguard Worker } 291*0e209d39SAndroid Build Coastguard Worker close(PIPE) or die "Program failed: \"$cmd\""; 292*0e209d39SAndroid Build Coastguard Worker 293*0e209d39SAndroid Build Coastguard Worker @out = grep(!/^\#/, @out); # filter out comments 294*0e209d39SAndroid Build Coastguard Worker 295*0e209d39SAndroid Build Coastguard Worker #debug( "[", join("\n", @out), "]\n"); 296*0e209d39SAndroid Build Coastguard Worker 297*0e209d39SAndroid Build Coastguard Worker my @results; 298*0e209d39SAndroid Build Coastguard Worker my $method = ''; 299*0e209d39SAndroid Build Coastguard Worker my $data = []; 300*0e209d39SAndroid Build Coastguard Worker foreach (@out) { 301*0e209d39SAndroid Build Coastguard Worker next unless (/\S/); 302*0e209d39SAndroid Build Coastguard Worker 303*0e209d39SAndroid Build Coastguard Worker if (/^=\s*(\w+)\s*(\w+)\s*(.*)/) { 304*0e209d39SAndroid Build Coastguard Worker my ($m, $state, $d) = ($1, $2, $3); 305*0e209d39SAndroid Build Coastguard Worker #debug ("$_ => [[$m $state !!!$d!!! $data ]]\n"); 306*0e209d39SAndroid Build Coastguard Worker if ($state eq 'begin') { 307*0e209d39SAndroid Build Coastguard Worker die "$method was begun but not finished" if ($method); 308*0e209d39SAndroid Build Coastguard Worker $method = $m; 309*0e209d39SAndroid Build Coastguard Worker push(@$data, $d); 310*0e209d39SAndroid Build Coastguard Worker push(@$data, ''); # placeholder for end data 311*0e209d39SAndroid Build Coastguard Worker } elsif ($state eq 'end') { 312*0e209d39SAndroid Build Coastguard Worker if ($m ne $method) { 313*0e209d39SAndroid Build Coastguard Worker die "$method end does not match: $_"; 314*0e209d39SAndroid Build Coastguard Worker } 315*0e209d39SAndroid Build Coastguard Worker $data->[1] = $d; # insert end data at [1] 316*0e209d39SAndroid Build Coastguard Worker #debug( "#$method:", join(";",@$data), "\n"); 317*0e209d39SAndroid Build Coastguard Worker unshift(@$data, $method); # add method to start 318*0e209d39SAndroid Build Coastguard Worker push(@results, $data); 319*0e209d39SAndroid Build Coastguard Worker $method = ''; 320*0e209d39SAndroid Build Coastguard Worker $data = []; 321*0e209d39SAndroid Build Coastguard Worker } else { 322*0e209d39SAndroid Build Coastguard Worker die "Can't parse: $_"; 323*0e209d39SAndroid Build Coastguard Worker } 324*0e209d39SAndroid Build Coastguard Worker } 325*0e209d39SAndroid Build Coastguard Worker 326*0e209d39SAndroid Build Coastguard Worker elsif (/^\[/) { 327*0e209d39SAndroid Build Coastguard Worker if ($method) { 328*0e209d39SAndroid Build Coastguard Worker push(@$data, $_); 329*0e209d39SAndroid Build Coastguard Worker } else { 330*0e209d39SAndroid Build Coastguard Worker # ignore extraneous GC notices 331*0e209d39SAndroid Build Coastguard Worker } 332*0e209d39SAndroid Build Coastguard Worker } 333*0e209d39SAndroid Build Coastguard Worker 334*0e209d39SAndroid Build Coastguard Worker else { 335*0e209d39SAndroid Build Coastguard Worker die "Can't parse: $_"; 336*0e209d39SAndroid Build Coastguard Worker } 337*0e209d39SAndroid Build Coastguard Worker } 338*0e209d39SAndroid Build Coastguard Worker 339*0e209d39SAndroid Build Coastguard Worker die "$method was begun but not finished" if ($method); 340*0e209d39SAndroid Build Coastguard Worker 341*0e209d39SAndroid Build Coastguard Worker @results; 342*0e209d39SAndroid Build Coastguard Worker} 343*0e209d39SAndroid Build Coastguard Worker 344*0e209d39SAndroid Build Coastguard Workersub debug { 345*0e209d39SAndroid Build Coastguard Worker my $message; 346*0e209d39SAndroid Build Coastguard Worker if($DEBUG != 0) { 347*0e209d39SAndroid Build Coastguard Worker foreach $message (@_) { 348*0e209d39SAndroid Build Coastguard Worker print STDERR "$message"; 349*0e209d39SAndroid Build Coastguard Worker } 350*0e209d39SAndroid Build Coastguard Worker } 351*0e209d39SAndroid Build Coastguard Worker} 352*0e209d39SAndroid Build Coastguard Worker 353*0e209d39SAndroid Build Coastguard Workersub measure1Alan { 354*0e209d39SAndroid Build Coastguard Worker #Added here, was global 355*0e209d39SAndroid Build Coastguard Worker my $CALIBRATE = 2; # duration in seconds for initial calibration 356*0e209d39SAndroid Build Coastguard Worker 357*0e209d39SAndroid Build Coastguard Worker my $method = shift; 358*0e209d39SAndroid Build Coastguard Worker my $pat = shift; 359*0e209d39SAndroid Build Coastguard Worker my $iterCount = shift; # actually might be -seconds/pass 360*0e209d39SAndroid Build Coastguard Worker 361*0e209d39SAndroid Build Coastguard Worker out("<P>Measuring $method using $pat, "); 362*0e209d39SAndroid Build Coastguard Worker if ($iterCount > 0) { 363*0e209d39SAndroid Build Coastguard Worker out("$iterCount iterations/pass, $NUMPASSES passes</P>\n"); 364*0e209d39SAndroid Build Coastguard Worker } else { 365*0e209d39SAndroid Build Coastguard Worker out(-$iterCount, " seconds/pass, $NUMPASSES passes</P>\n"); 366*0e209d39SAndroid Build Coastguard Worker } 367*0e209d39SAndroid Build Coastguard Worker 368*0e209d39SAndroid Build Coastguard Worker # is $iterCount actually -seconds? 369*0e209d39SAndroid Build Coastguard Worker if ($iterCount < 0) { 370*0e209d39SAndroid Build Coastguard Worker 371*0e209d39SAndroid Build Coastguard Worker # calibrate: estimate ms/iteration 372*0e209d39SAndroid Build Coastguard Worker print "Calibrating..."; 373*0e209d39SAndroid Build Coastguard Worker my @t = callJava($method, $pat, -$CALIBRATE); 374*0e209d39SAndroid Build Coastguard Worker print "done.\n"; 375*0e209d39SAndroid Build Coastguard Worker 376*0e209d39SAndroid Build Coastguard Worker my @data = split(/\s+/, $t[0]->[2]); 377*0e209d39SAndroid Build Coastguard Worker my $timePerIter = 1.0e-3 * $data[0] / $data[2]; 378*0e209d39SAndroid Build Coastguard Worker 379*0e209d39SAndroid Build Coastguard Worker # determine iterations/pass 380*0e209d39SAndroid Build Coastguard Worker $iterCount = int(-$iterCount / $timePerIter + 0.5); 381*0e209d39SAndroid Build Coastguard Worker 382*0e209d39SAndroid Build Coastguard Worker out("<P>Calibration pass ($CALIBRATE sec): "); 383*0e209d39SAndroid Build Coastguard Worker out("$data[0] ms, "); 384*0e209d39SAndroid Build Coastguard Worker out("$data[2] iterations = "); 385*0e209d39SAndroid Build Coastguard Worker out(formatSeconds(4, $timePerIter), "/iteration<BR>\n"); 386*0e209d39SAndroid Build Coastguard Worker } 387*0e209d39SAndroid Build Coastguard Worker 388*0e209d39SAndroid Build Coastguard Worker # run passes 389*0e209d39SAndroid Build Coastguard Worker print "Measuring $iterCount iterations x $NUMPASSES passes..."; 390*0e209d39SAndroid Build Coastguard Worker my @t = callJava($method, $pat, "$iterCount " x $NUMPASSES); 391*0e209d39SAndroid Build Coastguard Worker print "done.\n"; 392*0e209d39SAndroid Build Coastguard Worker my @ms = (); 393*0e209d39SAndroid Build Coastguard Worker my @b; # scratch 394*0e209d39SAndroid Build Coastguard Worker for my $a (@t) { 395*0e209d39SAndroid Build Coastguard Worker # $a->[0]: method name, corresponds to $method 396*0e209d39SAndroid Build Coastguard Worker # $a->[1]: 'begin' data, == $iterCount 397*0e209d39SAndroid Build Coastguard Worker # $a->[2]: 'end' data, of the form <ms> <eventsPerIter> 398*0e209d39SAndroid Build Coastguard Worker # $a->[3...]: gc messages from JVM during pass 399*0e209d39SAndroid Build Coastguard Worker @b = split(/\s+/, $a->[2]); 400*0e209d39SAndroid Build Coastguard Worker push(@ms, $b[0]); 401*0e209d39SAndroid Build Coastguard Worker } 402*0e209d39SAndroid Build Coastguard Worker my $eventsPerIter = $b[1]; 403*0e209d39SAndroid Build Coastguard Worker 404*0e209d39SAndroid Build Coastguard Worker out("Iterations per pass: $iterCount<BR>\n"); 405*0e209d39SAndroid Build Coastguard Worker out("Events per iteration: $eventsPerIter<BR>\n"); 406*0e209d39SAndroid Build Coastguard Worker 407*0e209d39SAndroid Build Coastguard Worker my @ms_str = @ms; 408*0e209d39SAndroid Build Coastguard Worker $ms_str[0] .= " (discarded)" if (@ms_str > 1); 409*0e209d39SAndroid Build Coastguard Worker out("Raw times (ms/pass): ", join(", ", @ms_str), "<BR>\n"); 410*0e209d39SAndroid Build Coastguard Worker 411*0e209d39SAndroid Build Coastguard Worker ($iterCount, $eventsPerIter, @ms); 412*0e209d39SAndroid Build Coastguard Worker} 413*0e209d39SAndroid Build Coastguard Worker 414*0e209d39SAndroid Build Coastguard Worker 415*0e209d39SAndroid Build Coastguard Worker1; 416*0e209d39SAndroid Build Coastguard Worker 417*0e209d39SAndroid Build Coastguard Worker#eof 418