зеркало из https://github.com/mozilla/pluotsorbet.git
219 строки
6.9 KiB
JavaScript
219 строки
6.9 KiB
JavaScript
var Benchmark = (function() {
|
|
|
|
function mean(array) {
|
|
function add(a, b) {
|
|
return a + b;
|
|
}
|
|
return array.reduce(add, 0) / array.length;
|
|
}
|
|
|
|
var defaultStorage = {
|
|
numRounds: 10,
|
|
roundDelay: 5000, // ms to delay starting next round of tests
|
|
baseline: [],
|
|
running: false,
|
|
round: 0,
|
|
times: [],
|
|
deleteFs: true,
|
|
deleteJitCache: true,
|
|
buildBaseline: false
|
|
};
|
|
|
|
function Storage(key, defaults) {
|
|
this.key = key;
|
|
if (!(key in localStorage)) {
|
|
this.storage = defaults;
|
|
this.save();
|
|
}
|
|
this.storage = JSON.parse(localStorage[key]);
|
|
Object.keys(defaultStorage).forEach(function(key) {
|
|
Object.defineProperty(this, key, {
|
|
get: function() { return this.storage[key]; },
|
|
set: function(newValue) { this.storage[key] = newValue; this.save() },
|
|
enumerable: true,
|
|
configurable: true
|
|
});
|
|
}, this);
|
|
}
|
|
|
|
Storage.prototype = {
|
|
save: function() {
|
|
localStorage[this.key] = JSON.stringify(this.storage);
|
|
}
|
|
};
|
|
|
|
var storage = new Storage("benchmark", defaultStorage);
|
|
|
|
var startup = {
|
|
run: function(settings) {
|
|
storage.round = 0;
|
|
storage.times = [];
|
|
storage.running = true;
|
|
storage.numRounds = "numRounds" in settings ? settings.numRounds : defaultStorage.numRounds;
|
|
storage.roundDelay = "roundDelay" in settings ? settings.roundDelay : defaultStorage.roundDelay;
|
|
storage.deleteFs = "deleteFs" in settings ? settings.deleteFs : defaultStorage.deleteFs;
|
|
storage.deleteJitCache = "deleteJitCache" in settings ? settings.deleteJitCache : defaultStorage.deleteJitCache;
|
|
storage.buildBaseline = "buildBaseline" in settings ? settings.buildBaseline : defaultStorage.buildBaseline;
|
|
if (storage.buildBaseline) {
|
|
storage.baseline = [];
|
|
}
|
|
this.runNextRound();
|
|
},
|
|
startTimer: function() {
|
|
if (!storage.running) {
|
|
console.log("startTimer called while benchmark not running");
|
|
return;
|
|
}
|
|
this.startTime = performance.now();
|
|
},
|
|
stopTimer: function() {
|
|
if (!storage.running) {
|
|
console.log("stopTimer called while benchmark not running");
|
|
return;
|
|
}
|
|
if (this.startTime === null) {
|
|
console.log("stopTimer called without previous call to startTimer");
|
|
return;
|
|
}
|
|
var took = performance.now() - this.startTime;
|
|
this.startTime = null;
|
|
var times = storage.times;
|
|
times.push(took);
|
|
storage.times = times;
|
|
storage.round++;
|
|
if (storage.round >= storage.numRounds) {
|
|
this.finish();
|
|
return;
|
|
}
|
|
this.runNextRound();
|
|
},
|
|
runNextRound: function() {
|
|
function run() {
|
|
DumbPipe.close(DumbPipe.open("reload", {}));
|
|
}
|
|
if (typeof netscape !== "undefined" && netscape.security.PrivilegeManager) {
|
|
// To enable GC use a seperate profile and enable the pref:
|
|
// security.turn_off_all_security_so_that_viruses_can_take_over_this_computer
|
|
netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");
|
|
console.log("Forcing CC/GC.");
|
|
for (var i = 0; i < 3; i++) {
|
|
Components.utils.forceCC();
|
|
Components.utils.forceGC();
|
|
}
|
|
}
|
|
if (storage.deleteFs) {
|
|
console.log("Deleting fs.");
|
|
indexedDB.deleteDatabase("asyncStorage");
|
|
}
|
|
if (storage.deleteJitCache) {
|
|
console.log("Deleting jit cache.");
|
|
indexedDB.deleteDatabase("CompiledMethodCache");
|
|
}
|
|
console.log("Scheduling round " + (storage.round + 1) + " of " + storage.numRounds + " to run in " + storage.roundDelay + "ms");
|
|
setTimeout(run, storage.roundDelay);
|
|
},
|
|
finish: function() {
|
|
storage.running = false;
|
|
var times = storage.times;
|
|
var message = "Current times: " + JSON.stringify(times) + "\n";
|
|
var baselineMean = mean(storage.baseline);
|
|
var currentMean = mean(times);
|
|
message += "Current mean : " + Math.round(currentMean) + "ms\n";
|
|
if (storage.baseline.length) {
|
|
message +=
|
|
"Baseline mean: " + Math.round(baselineMean) + "ms\n" +
|
|
"+/- : " + Math.round(currentMean - baselineMean) + "ms\n" +
|
|
"% : " + (100 * (currentMean - baselineMean) / baselineMean).toFixed(2) + "\n";
|
|
}
|
|
if (storage.baseline.length) {
|
|
var p = (storage.baseline.length < 2) ? 1 : ttest(storage.baseline, times).pValue();
|
|
if (p < 0.05) {
|
|
message += currentMean < baselineMean ? "FASTER" : "SLOWER";
|
|
} else {
|
|
message += "INSIGNIFICANT RESULT";
|
|
}
|
|
}
|
|
if (storage.buildBaseline) {
|
|
storage.baseline = times;
|
|
storage.buildBaseline = false;
|
|
message = "FINISHED BUILDING BASELINE\n" + message;
|
|
}
|
|
message = "-------------------------------------------------------------\n" +
|
|
message + "\n" +
|
|
"-------------------------------------------------------------\n";
|
|
console.log(message);
|
|
}
|
|
|
|
};
|
|
|
|
// Start right away instead of in init() so we can see any speedups in script loading.
|
|
if (storage.running) {
|
|
startup.startTimer();
|
|
}
|
|
|
|
var numRoundsEl;
|
|
var roundDelayEl;
|
|
var deleteFsEl;
|
|
var deleteJitCacheEl;
|
|
var startButton;
|
|
var baselineButton;
|
|
|
|
function getSettings() {
|
|
return {
|
|
numRounds: numRoundsEl.value | 0,
|
|
roundDelay: roundDelayEl.value | 0,
|
|
deleteFs: !!deleteFsEl.checked,
|
|
deleteJitCache: !!deleteJitCacheEl.checked,
|
|
};
|
|
}
|
|
|
|
function start() {
|
|
startup.run(getSettings());
|
|
};
|
|
|
|
function buildBaseline() {
|
|
var settings = getSettings();
|
|
settings["buildBaseline"] = true;
|
|
startup.run(settings);
|
|
}
|
|
|
|
return {
|
|
initUI: function() {
|
|
numRoundsEl = document.getElementById("benchmark-num-rounds");
|
|
roundDelayEl = document.getElementById("benchmark-round-delay");
|
|
deleteFsEl = document.getElementById("benchmark-delete-fs");
|
|
deleteJitCacheEl = document.getElementById("benchmark-delete-jit-cache");
|
|
startButton = document.getElementById("benchmark-startup-run");
|
|
baselineButton = document.getElementById("benchmark-startup-baseline");
|
|
|
|
numRoundsEl.value = storage.numRounds;
|
|
roundDelayEl.value = storage.roundDelay;
|
|
deleteFsEl.checked = storage.deleteFs;
|
|
deleteJitCacheEl.checked = storage.deleteJitCache;
|
|
|
|
if (storage.baseline.length === 0) {
|
|
startButton.disabled = true;
|
|
}
|
|
|
|
startButton.onclick = start;
|
|
baselineButton.onclick = buildBaseline;
|
|
},
|
|
start: start,
|
|
buildBaseline: buildBaseline,
|
|
startup: {
|
|
init: function() {
|
|
if (!storage.running) {
|
|
return;
|
|
}
|
|
var implKey = "com/sun/midp/lcdui/DisplayDevice.gainedForeground0.(II)V";
|
|
var originalFn = Native[implKey];
|
|
Native[implKey] = function() {
|
|
startup.stopTimer();
|
|
originalFn.apply(null, arguments);
|
|
};
|
|
},
|
|
run: startup.run.bind(startup),
|
|
}
|
|
};
|
|
})();
|