165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// Copyright 2009 the V8 project authors. All rights reserved.
265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// Redistribution and use in source and binary forms, with or without
365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// modification, are permitted provided that the following conditions are
465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// met:
565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//
665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//     * Redistributions of source code must retain the above copyright
765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//       notice, this list of conditions and the following disclaimer.
865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//     * Redistributions in binary form must reproduce the above
965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//       copyright notice, this list of conditions and the following
1065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//       disclaimer in the documentation and/or other materials provided
1165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//       with the distribution.
1265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//     * Neither the name of Google Inc. nor the names of its
1365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//       contributors may be used to endorse or promote products derived
1465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//       from this software without specific prior written permission.
1565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org//
1665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
1765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
1865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
1965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
2065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
2165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
2265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
2365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
2465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
2565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
2665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
2865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// Load source code files from <project root>/tools.
295ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org// Files: tools/splaytree.js tools/codemap.js tools/consarray.js tools/profile.js
3065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
3165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
3265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgfunction stackToString(stack) {
3365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  return stack.join(' -> ');
3465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
3565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
3665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
3765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgfunction assertPathExists(root, path, opt_message) {
3865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var message = opt_message ? ' (' + opt_message + ')' : '';
3965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  assertNotNull(root.descendToChild(path, function(node, pos) {
4065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    assertNotNull(node,
4165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      stackToString(path.slice(0, pos)) + ' has no child ' +
4265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org                    path[pos] + message);
4365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  }), opt_message);
4465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
4565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
4665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
4765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgfunction assertNoPathExists(root, path, opt_message) {
4865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var message = opt_message ? ' (' + opt_message + ')' : '';
4965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  assertNull(root.descendToChild(path), opt_message);
5065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
5165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
5265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
5365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgfunction countNodes(profile, traverseFunc) {
5465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var count = 0;
5565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  traverseFunc.call(profile, function () { count++; });
5665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  return count;
5765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
5865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
5965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
6065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgfunction ProfileTestDriver() {
61496c03a64f12710e837204e261ef155601247895sgjesse@chromium.org  this.profile = new Profile();
6265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.stack_ = [];
6365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.addFunctions_();
6465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
6565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
6665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
6765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org// Addresses inside functions.
6865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgProfileTestDriver.prototype.funcAddrs_ = {
6965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    'lib1-f1': 0x11110, 'lib1-f2': 0x11210,
7065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    'lib2-f1': 0x21110, 'lib2-f2': 0x21210,
7165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    'T: F1': 0x50110, 'T: F2': 0x50210, 'T: F3': 0x50410 };
7265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
7365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
7465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgProfileTestDriver.prototype.addFunctions_ = function() {
75e959c18cf7193e2f021245584a3c8f1f32f82c92kasperl@chromium.org  this.profile.addLibrary('lib1', 0x11000, 0x12000);
7665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.addStaticCode('lib1-f1', 0x11100, 0x11900);
7765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.addStaticCode('lib1-f2', 0x11200, 0x11500);
78e959c18cf7193e2f021245584a3c8f1f32f82c92kasperl@chromium.org  this.profile.addLibrary('lib2', 0x21000, 0x22000);
7965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.addStaticCode('lib2-f1', 0x21100, 0x21900);
8065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.addStaticCode('lib2-f2', 0x21200, 0x21500);
8165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.addCode('T', 'F1', 0x50100, 0x100);
8265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.addCode('T', 'F2', 0x50200, 0x100);
8365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.addCode('T', 'F3', 0x50400, 0x100);
8465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
8565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
8665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
8765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgProfileTestDriver.prototype.enter = function(funcName) {
8865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  // Stack looks like this: [pc, caller, ..., main].
8965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  // Therefore, we are adding entries at the beginning.
9065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.stack_.unshift(this.funcAddrs_[funcName]);
9165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.recordTick(this.stack_);
9265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
9365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
9465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
9565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgProfileTestDriver.prototype.stay = function() {
9665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.profile.recordTick(this.stack_);
9765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
9865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
9965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
10065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgProfileTestDriver.prototype.leave = function() {
10165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.stack_.shift();
10265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
10365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
10465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
10565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgProfileTestDriver.prototype.execute = function() {
10665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.enter('lib1-f1');
10765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.enter('lib1-f2');
10865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      this.enter('T: F1');
10965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.enter('T: F2');
11065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.leave();
11165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      this.stay();
11265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.enter('lib2-f1');
11365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org          this.enter('lib2-f1');
11465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org          this.leave();
11565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.stay();
11665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.leave();
11765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.enter('T: F3');
11865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org          this.enter('T: F3');
11965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org            this.enter('T: F3');
12065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org            this.leave();
12165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org            this.enter('T: F2');
12265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org            this.stay();
12365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org            this.leave();
12465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org          this.leave();
12565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.leave();
12665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      this.leave();
1275ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org      this.enter('lib2-f1');
1285ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org        this.enter('lib1-f1');
1295ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org        this.leave();
1305ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org      this.leave();
13165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.stay();
13265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  this.leave();
13365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
13465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
13565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
13665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgfunction Inherits(childCtor, parentCtor) {
13765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  function tempCtor() {};
13865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  tempCtor.prototype = parentCtor.prototype;
13965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  childCtor.superClass_ = parentCtor.prototype;
14065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  childCtor.prototype = new tempCtor();
14165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  childCtor.prototype.constructor = childCtor;
14265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
14365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
14465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
14565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org(function testCallTreeBuilding() {
14665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  function Driver() {
14765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    ProfileTestDriver.call(this);
14865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesTopDown = [];
14965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesBottomUp = [];
15065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
15165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Inherits(Driver, ProfileTestDriver);
15265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
15365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.enter = function(func) {
15465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesTopDown.push(func);
15565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesBottomUp.unshift(func);
1565ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertNoPathExists(this.profile.getTopDownProfile().getRoot(), this.namesTopDown,
15765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        'pre enter/topDown');
1585ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertNoPathExists(this.profile.getBottomUpProfile().getRoot(), this.namesBottomUp,
15965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        'pre enter/bottomUp');
16065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    Driver.superClass_.enter.call(this, func);
1615ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertPathExists(this.profile.getTopDownProfile().getRoot(), this.namesTopDown,
16265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        'post enter/topDown');
1635ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertPathExists(this.profile.getBottomUpProfile().getRoot(), this.namesBottomUp,
16465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        'post enter/bottomUp');
16565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
16665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
16765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.stay = function() {
16865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var preTopDownNodes = countNodes(this.profile, this.profile.traverseTopDownTree);
16965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var preBottomUpNodes = countNodes(this.profile, this.profile.traverseBottomUpTree);
17065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    Driver.superClass_.stay.call(this);
17165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var postTopDownNodes = countNodes(this.profile, this.profile.traverseTopDownTree);
17265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var postBottomUpNodes = countNodes(this.profile, this.profile.traverseBottomUpTree);
17365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    // Must be no changes in tree layout.
17465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    assertEquals(preTopDownNodes, postTopDownNodes, 'stay/topDown');
17565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    assertEquals(preBottomUpNodes, postBottomUpNodes, 'stay/bottomUp');
17665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
17765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
17865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.leave = function() {
17965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    Driver.superClass_.leave.call(this);
18065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesTopDown.pop();
18165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesBottomUp.shift();
18265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
18365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
18465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var testDriver = new Driver();
18565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  testDriver.execute();
18665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org})();
18765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
18865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
18965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.orgfunction assertNodeWeights(root, path, selfTicks, totalTicks) {
19065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var node = root.descendToChild(path);
19165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var stack = stackToString(path);
19265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  assertNotNull(node, 'node not found: ' + stack);
19365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  assertEquals(selfTicks, node.selfWeight, 'self of ' + stack);
19465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  assertEquals(totalTicks, node.totalWeight, 'total of ' + stack);
19565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org};
19665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
19765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
19865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org(function testTopDownRootProfileTicks() {
19965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var testDriver = new ProfileTestDriver();
20065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  testDriver.execute();
20165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
20265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var pathWeights = [
2035ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib1-f1'], 1, 16],
2045ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib1-f1', 'lib1-f2'], 2, 15],
20565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1'], 2, 11],
20665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1', 'T: F2'], 1, 1],
20765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1', 'lib2-f1'], 2, 3],
20865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1', 'lib2-f1', 'lib2-f1'], 1, 1],
20965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1', 'T: F3'], 1, 5],
21065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1', 'T: F3', 'T: F3'], 1, 4],
21165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1', 'T: F3', 'T: F3', 'T: F3'], 1, 1],
2125ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib1-f1', 'lib1-f2', 'T: F1', 'T: F3', 'T: F3', 'T: F2'], 2, 2],
2135ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib1-f1', 'lib1-f2', 'lib2-f1'], 1, 2],
2145ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib1-f1', 'lib1-f2', 'lib2-f1', 'lib1-f1'], 1, 1]
21565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  ];
21665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
2175ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var root = testDriver.profile.getTopDownProfile().getRoot();
21865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  for (var i = 0; i < pathWeights.length; ++i) {
21965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var data = pathWeights[i];
22065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    assertNodeWeights(root, data[0], data[1], data[2]);
22165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  }
22265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org})();
22365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
22465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
22565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org(function testRootFlatProfileTicks() {
22665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  function Driver() {
22765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    ProfileTestDriver.call(this);
22865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesTopDown = [''];
22965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.counters = {};
2305ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    this.root = null;
23165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
23265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Inherits(Driver, ProfileTestDriver);
23365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
23465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.increment = function(func, self, total) {
23565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    if (!(func in this.counters)) {
23665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      this.counters[func] = { self: 0, total: 0 };
23765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    }
23865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.counters[func].self += self;
23965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.counters[func].total += total;
24065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
24165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
24265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.incrementTotals = function() {
24365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    // Only count each function in the stack once.
24465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var met = {};
24565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    for (var i = 0; i < this.namesTopDown.length; ++i) {
24665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      var name = this.namesTopDown[i];
24765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      if (!(name in met)) {
24865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org        this.increment(name, 0, 1);
24965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      }
25065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org      met[name] = true;
25165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    }
25265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
25365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
25465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.enter = function(func) {
25565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    Driver.superClass_.enter.call(this, func);
25665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesTopDown.push(func);
25765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.increment(func, 1, 0);
25865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.incrementTotals();
25965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
26065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
26165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.stay = function() {
26265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    Driver.superClass_.stay.call(this);
26365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.increment(this.namesTopDown[this.namesTopDown.length - 1], 1, 0);
26465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.incrementTotals();
26565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
26665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
26765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  Driver.prototype.leave = function() {
26865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    Driver.superClass_.leave.call(this);
26965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    this.namesTopDown.pop();
27065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  };
27165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
2725ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  Driver.prototype.extractRoot = function() {
2735ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertTrue('' in this.counters);
2745ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    this.root = this.counters[''];
2755ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    delete this.counters[''];
2765ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  };
2775ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
27865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var testDriver = new Driver();
27965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  testDriver.execute();
2805ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  testDriver.extractRoot();
28165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
28265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  var counted = 0;
28365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  for (var c in testDriver.counters) {
28465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    counted++;
28565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  }
28665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
2875ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var flatProfileRoot = testDriver.profile.getFlatProfile().getRoot();
2885ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  assertEquals(testDriver.root.self, flatProfileRoot.selfWeight);
2895ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  assertEquals(testDriver.root.total, flatProfileRoot.totalWeight);
2905ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
2915ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var flatProfile = flatProfileRoot.exportChildren();
29265dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  assertEquals(counted, flatProfile.length, 'counted vs. flatProfile');
29365dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  for (var i = 0; i < flatProfile.length; ++i) {
29465dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var rec = flatProfile[i];
29565dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    assertTrue(rec.label in testDriver.counters, 'uncounted: ' + rec.label);
29665dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    var reference = testDriver.counters[rec.label];
29765dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    assertEquals(reference.self, rec.selfWeight, 'self of ' + rec.label);
29865dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org    assertEquals(reference.total, rec.totalWeight, 'total of ' + rec.label);
29965dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org  }
30065dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org
30165dad4b091d2925543c6326db635d0f7cf9e1edcager@chromium.org})();
3025ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3035ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3045ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org(function testFunctionCalleesProfileTicks() {
3055ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var testDriver = new ProfileTestDriver();
3065ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  testDriver.execute();
3075ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3085ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var pathWeights = [
3095ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib2-f1'], 3, 5],
3105ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib2-f1', 'lib2-f1'], 1, 1],
3115ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    [['lib2-f1', 'lib1-f1'], 1, 1]
3125ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  ];
3135ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3145ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var profile = testDriver.profile.getTopDownProfile('lib2-f1');
3155ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var root = profile.getRoot();
3165ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  for (var i = 0; i < pathWeights.length; ++i) {
3175ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    var data = pathWeights[i];
3185ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertNodeWeights(root, data[0], data[1], data[2]);
3195ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  }
3205ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org})();
3215ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3225ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3235ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org(function testFunctionFlatProfileTicks() {
3245ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var testDriver = new ProfileTestDriver();
3255ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  testDriver.execute();
3265ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3275ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var flatWeights = {
3285ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    'lib2-f1': [1, 1],
3295ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    'lib1-f1': [1, 1]
3305ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  };
3315ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3325ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var flatProfileRoot =
3335ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org     testDriver.profile.getFlatProfile('lib2-f1').findOrAddChild('lib2-f1');
3345ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  assertEquals(3, flatProfileRoot.selfWeight);
3355ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  assertEquals(5, flatProfileRoot.totalWeight);
3365ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3375ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  var flatProfile = flatProfileRoot.exportChildren();
3385ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  assertEquals(2, flatProfile.length, 'counted vs. flatProfile');
3395ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  for (var i = 0; i < flatProfile.length; ++i) {
3405ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    var rec = flatProfile[i];
3415ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertTrue(rec.label in flatWeights, 'uncounted: ' + rec.label);
3425ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    var reference = flatWeights[rec.label];
3435ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertEquals(reference[0], rec.selfWeight, 'self of ' + rec.label);
3445ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org    assertEquals(reference[1], rec.totalWeight, 'total of ' + rec.label);
3455ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org  }
3465ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org
3475ec4892aef9cca42940d7d92302abf674365f6b7ager@chromium.org})();
348