2008-10-21 15:21:23 -07:00
|
|
|
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
2008-09-19 18:58:00 -07:00
|
|
|
/**
|
|
|
|
* A number of the tests in this file depend on the setting of
|
|
|
|
* HOTLOOP. Define some constants up front, so they're easy to grep
|
|
|
|
* for.
|
|
|
|
*/
|
2008-09-22 14:37:59 -07:00
|
|
|
// The HOTLOOP constant we depend on; only readable from our stats
|
|
|
|
// object in debug builds.
|
|
|
|
const haveTracemonkey = !!(this.tracemonkey)
|
|
|
|
const HOTLOOP = haveTracemonkey ? tracemonkey.HOTLOOP : 2;
|
2008-09-19 18:58:00 -07:00
|
|
|
// The loop count at which we trace
|
|
|
|
const RECORDLOOP = HOTLOOP;
|
|
|
|
// The loop count at which we run the trace
|
|
|
|
const RUNLOOP = HOTLOOP + 1;
|
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
var testName = null;
|
|
|
|
if ("arguments" in this && arguments.length > 0)
|
|
|
|
testName = arguments[0];
|
2008-07-17 01:58:34 -07:00
|
|
|
var fails = [], passes=[];
|
|
|
|
|
2008-09-22 14:37:59 -07:00
|
|
|
function jitstatHandler(f)
|
|
|
|
{
|
|
|
|
if (!haveTracemonkey) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
// XXXbz this is a nasty hack, but I can't figure out a way to
|
|
|
|
// just use jitstats.tbl here
|
|
|
|
f("recorderStarted");
|
|
|
|
f("recorderAborted");
|
|
|
|
f("traceCompleted");
|
|
|
|
f("sideExitIntoInterpreter");
|
|
|
|
f("typeMapMismatchAtEntry");
|
|
|
|
f("returnToDifferentLoopHeader");
|
|
|
|
f("traceTriggered");
|
|
|
|
f("globalShapeMismatchAtEntry");
|
|
|
|
f("treesTrashed");
|
|
|
|
f("slotPromoted");
|
|
|
|
f("unstableLoopVariable");
|
|
|
|
f("breakLoopExits");
|
|
|
|
f("returnLoopExits");
|
|
|
|
}
|
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function test(f)
|
|
|
|
{
|
2008-09-19 19:47:58 -07:00
|
|
|
if (!testName || testName == f.name) {
|
|
|
|
// Collect our jit stats
|
|
|
|
var localJITstats = {};
|
2008-09-22 14:37:59 -07:00
|
|
|
jitstatHandler(function(prop, local, global) {
|
|
|
|
localJITstats[prop] = tracemonkey[prop];
|
|
|
|
});
|
2008-09-19 19:47:58 -07:00
|
|
|
check(f.name, f(), f.expected, localJITstats, f.jitstats);
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
}
|
|
|
|
|
2008-09-19 19:47:58 -07:00
|
|
|
function check(desc, actual, expected, oldJITstats, expectedJITstats)
|
2008-07-01 19:21:11 -07:00
|
|
|
{
|
2008-07-17 01:58:34 -07:00
|
|
|
if (expected == actual) {
|
2008-09-19 19:47:58 -07:00
|
|
|
var pass = true;
|
2008-09-22 14:37:59 -07:00
|
|
|
jitstatHandler(function(prop) {
|
|
|
|
if (expectedJITstats && prop in expectedJITstats &&
|
|
|
|
expectedJITstats[prop] !=
|
|
|
|
tracemonkey[prop] - oldJITstats[prop]) {
|
|
|
|
pass = false;
|
|
|
|
}
|
|
|
|
});
|
2008-09-19 19:47:58 -07:00
|
|
|
if (pass) {
|
|
|
|
passes.push(desc);
|
|
|
|
return print(desc, ": passed");
|
|
|
|
}
|
2008-07-17 01:58:34 -07:00
|
|
|
}
|
|
|
|
fails.push(desc);
|
2008-09-19 19:47:58 -07:00
|
|
|
var expectedStats = "";
|
2008-09-22 14:37:59 -07:00
|
|
|
if (expectedJITstats) {
|
|
|
|
jitstatHandler(function(prop) {
|
|
|
|
if (prop in expectedJITstats) {
|
|
|
|
if (expectedStats)
|
|
|
|
expectedStats += " ";
|
|
|
|
expectedStats +=
|
|
|
|
prop + ": " + expectedJITstats[prop];
|
|
|
|
}
|
|
|
|
});
|
2008-09-19 19:47:58 -07:00
|
|
|
}
|
|
|
|
var actualStats = "";
|
2008-09-22 14:37:59 -07:00
|
|
|
if (expectedJITstats) {
|
|
|
|
jitstatHandler(function(prop) {
|
|
|
|
if (prop in expectedJITstats) {
|
|
|
|
if (actualStats)
|
|
|
|
actualStats += " ";
|
|
|
|
actualStats += prop + ": " + (tracemonkey[prop]-oldJITstats[prop]);
|
|
|
|
}
|
|
|
|
});
|
2008-09-19 19:47:58 -07:00
|
|
|
}
|
|
|
|
print(desc, ": FAILED: expected", typeof(expected), "(", expected, ")",
|
|
|
|
(expectedStats ? " [" + expectedStats + "] " : ""),
|
|
|
|
"!= actual",
|
|
|
|
typeof(actual), "(", actual, ")",
|
|
|
|
(actualStats ? " [" + actualStats + "] " : ""));
|
2008-07-01 19:21:11 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
function ifInsideLoop()
|
|
|
|
{
|
2008-07-18 08:01:51 -07:00
|
|
|
var cond = true, intCond = 5, count = 0;
|
|
|
|
for (var i = 0; i < 100; i++) {
|
2008-07-01 19:21:11 -07:00
|
|
|
if (cond)
|
|
|
|
count++;
|
2008-07-18 08:01:51 -07:00
|
|
|
if (intCond)
|
|
|
|
count++;
|
2008-07-01 19:21:11 -07:00
|
|
|
}
|
|
|
|
return count;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
ifInsideLoop.expected = 200;
|
|
|
|
test(ifInsideLoop);
|
2008-07-01 19:21:11 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function bitwiseAnd_inner(bitwiseAndValue) {
|
2008-07-07 21:18:10 -07:00
|
|
|
for (var i = 0; i < 60000; i++)
|
2008-07-01 19:21:11 -07:00
|
|
|
bitwiseAndValue = bitwiseAndValue & i;
|
|
|
|
return bitwiseAndValue;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
function bitwiseAnd()
|
|
|
|
{
|
|
|
|
return bitwiseAnd_inner(12341234);
|
|
|
|
}
|
|
|
|
bitwiseAnd.expected = 0;
|
|
|
|
test(bitwiseAnd);
|
|
|
|
|
|
|
|
if (!testName || testName == "bitwiseGlobal") {
|
|
|
|
bitwiseAndValue = Math.pow(2,32);
|
|
|
|
for (var i = 0; i < 60000; i++)
|
|
|
|
bitwiseAndValue = bitwiseAndValue & i;
|
|
|
|
check("bitwiseGlobal", bitwiseAndValue, 0);
|
|
|
|
}
|
2008-07-01 19:21:11 -07:00
|
|
|
|
2008-07-09 18:09:11 -07:00
|
|
|
|
2008-07-01 19:21:11 -07:00
|
|
|
function equalInt()
|
|
|
|
{
|
2008-08-11 22:05:33 -07:00
|
|
|
var i1 = 55, one = 1, zero = 0, undef;
|
2008-08-11 19:11:31 -07:00
|
|
|
var o1 = { }, o2 = { };
|
2008-08-11 22:05:33 -07:00
|
|
|
var s = "5";
|
|
|
|
var hits = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
|
2008-07-01 19:21:11 -07:00
|
|
|
for (var i = 0; i < 5000; i++) {
|
2008-07-13 19:33:08 -07:00
|
|
|
if (i1 == 55) hits[0]++;
|
|
|
|
if (i1 != 56) hits[1]++;
|
|
|
|
if (i1 < 56) hits[2]++;
|
|
|
|
if (i1 > 50) hits[3]++;
|
|
|
|
if (i1 <= 60) hits[4]++;
|
|
|
|
if (i1 >= 30) hits[5]++;
|
|
|
|
if (i1 == 7) hits[6]++;
|
|
|
|
if (i1 != 55) hits[7]++;
|
|
|
|
if (i1 < 30) hits[8]++;
|
|
|
|
if (i1 > 90) hits[9]++;
|
|
|
|
if (i1 <= 40) hits[10]++;
|
|
|
|
if (i1 >= 70) hits[11]++;
|
2008-08-11 19:11:31 -07:00
|
|
|
if (o1 == o2) hits[12]++;
|
|
|
|
if (o2 != null) hits[13]++;
|
2008-08-11 22:05:33 -07:00
|
|
|
if (s < 10) hits[14]++;
|
|
|
|
if (true < zero) hits[15]++;
|
|
|
|
if (undef > one) hits[16]++;
|
|
|
|
if (undef < zero) hits[17]++;
|
2008-07-01 19:21:11 -07:00
|
|
|
}
|
2008-07-13 19:33:08 -07:00
|
|
|
return hits.toString();
|
2008-07-01 19:21:11 -07:00
|
|
|
}
|
2008-08-11 22:05:33 -07:00
|
|
|
equalInt.expected = "5000,5000,5000,5000,5000,5000,0,0,0,0,0,0,0,5000,5000,0,0,0";
|
2008-07-31 12:15:22 -07:00
|
|
|
test(equalInt);
|
2008-07-13 19:33:08 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
var a;
|
|
|
|
function setelem()
|
2008-07-09 05:11:03 -07:00
|
|
|
{
|
2008-07-31 12:15:22 -07:00
|
|
|
a = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
|
|
|
|
a = a.concat(a, a, a);
|
2008-07-09 05:11:03 -07:00
|
|
|
var l = a.length;
|
|
|
|
for (var i = 0; i < l; i++) {
|
|
|
|
a[i] = i;
|
|
|
|
}
|
2008-07-13 19:33:08 -07:00
|
|
|
return a.toString();
|
2008-07-09 05:11:03 -07:00
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
setelem.expected = "0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83";
|
|
|
|
test(setelem);
|
2008-07-09 05:11:03 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function getelem_inner(a)
|
2008-07-09 05:11:03 -07:00
|
|
|
{
|
|
|
|
var accum = 0;
|
|
|
|
var l = a.length;
|
|
|
|
for (var i = 0; i < l; i++) {
|
|
|
|
accum += a[i];
|
|
|
|
}
|
|
|
|
return accum;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
function getelem()
|
|
|
|
{
|
|
|
|
return getelem_inner(a);
|
|
|
|
}
|
|
|
|
getelem.expected = 3486;
|
|
|
|
test(getelem);
|
2008-07-09 05:11:03 -07:00
|
|
|
|
|
|
|
globalName = 907;
|
|
|
|
function name()
|
|
|
|
{
|
|
|
|
var a = 0;
|
|
|
|
for (var i = 0; i < 100; i++)
|
|
|
|
a = globalName;
|
|
|
|
return a;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
name.expected = 907;
|
|
|
|
test(name);
|
2008-07-09 05:11:03 -07:00
|
|
|
|
2008-07-10 07:45:11 -07:00
|
|
|
var globalInt = 0;
|
2008-07-31 12:15:22 -07:00
|
|
|
if (!testName || testName == "globalGet") {
|
|
|
|
for (var i = 0; i < 500; i++)
|
|
|
|
globalInt = globalName + i;
|
|
|
|
check("globalGet", globalInt, globalName + 499);
|
|
|
|
}
|
2008-07-10 07:45:11 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
if (!testName || testName == "globalSet") {
|
|
|
|
for (var i = 0; i < 500; i++)
|
|
|
|
globalInt = i;
|
|
|
|
check("globalSet", globalInt, 499);
|
|
|
|
}
|
2008-07-10 07:45:11 -07:00
|
|
|
|
2008-07-09 05:11:03 -07:00
|
|
|
function arith()
|
|
|
|
{
|
|
|
|
var accum = 0;
|
|
|
|
for (var i = 0; i < 100; i++) {
|
|
|
|
accum += (i * 2) - 1;
|
|
|
|
}
|
|
|
|
return accum;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
arith.expected = 9800;
|
|
|
|
test(arith);
|
2008-07-09 05:11:03 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function lsh_inner(n)
|
2008-07-09 05:11:03 -07:00
|
|
|
{
|
|
|
|
var r;
|
|
|
|
for (var i = 0; i < 35; i++)
|
|
|
|
r = 0x1 << n;
|
|
|
|
return r;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
function lsh()
|
|
|
|
{
|
|
|
|
return [lsh_inner(15),lsh_inner(55),lsh_inner(1),lsh_inner(0)];
|
|
|
|
}
|
|
|
|
lsh.expected = "32768,8388608,2,1";
|
|
|
|
test(lsh);
|
2008-07-09 05:11:03 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function rsh_inner(n)
|
2008-07-09 05:11:03 -07:00
|
|
|
{
|
|
|
|
var r;
|
|
|
|
for (var i = 0; i < 35; i++)
|
|
|
|
r = 0x11010101 >> n;
|
|
|
|
return r;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
function rsh()
|
|
|
|
{
|
|
|
|
return [rsh_inner(8),rsh_inner(5),rsh_inner(35),rsh_inner(-1)];
|
|
|
|
}
|
|
|
|
rsh.expected = "1114369,8914952,35659808,0";
|
|
|
|
test(rsh);
|
2008-07-09 05:11:03 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function ursh_inner(n)
|
2008-07-09 05:11:03 -07:00
|
|
|
{
|
|
|
|
var r;
|
|
|
|
for (var i = 0; i < 35; i++)
|
|
|
|
r = -55 >>> n;
|
|
|
|
return r;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
function ursh() {
|
|
|
|
return [ursh_inner(8),ursh_inner(33),ursh_inner(0),ursh_inner(1)];
|
|
|
|
}
|
|
|
|
ursh.expected = "16777215,2147483620,4294967241,2147483620";
|
|
|
|
test(ursh);
|
2008-07-11 14:47:51 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function doMath_inner(cos)
|
2008-07-11 21:03:33 -07:00
|
|
|
{
|
|
|
|
var s = 0;
|
2008-07-15 20:37:57 -07:00
|
|
|
var sin = Math.sin;
|
2008-07-11 21:03:33 -07:00
|
|
|
for (var i = 0; i < 200; i++)
|
2008-07-15 20:37:57 -07:00
|
|
|
s = -Math.pow(sin(i) + cos(i * 0.75), 4);
|
2008-07-11 21:03:33 -07:00
|
|
|
return s;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
function doMath() {
|
|
|
|
return doMath_inner(Math.cos);
|
|
|
|
}
|
|
|
|
doMath.expected = -0.5405549555611059;
|
|
|
|
test(doMath);
|
2008-07-11 14:47:51 -07:00
|
|
|
|
2008-07-31 12:15:22 -07:00
|
|
|
function fannkuch() {
|
|
|
|
var count = Array(8);
|
|
|
|
var r = 8;
|
2008-07-11 14:47:51 -07:00
|
|
|
var done = 0;
|
|
|
|
while (done < 40) {
|
|
|
|
// write-out the first 30 permutations
|
|
|
|
done += r;
|
|
|
|
while (r != 1) { count[r - 1] = r; r--; }
|
|
|
|
while (true) {
|
|
|
|
count[r] = count[r] - 1;
|
|
|
|
if (count[r] > 0) break;
|
|
|
|
r++;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return done;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
fannkuch.expected = 41;
|
|
|
|
test(fannkuch);
|
2008-07-15 10:17:51 -07:00
|
|
|
|
|
|
|
function xprop()
|
|
|
|
{
|
|
|
|
a = 0;
|
|
|
|
for (var i = 0; i < 20; i++)
|
|
|
|
a += 7;
|
|
|
|
return a;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
xprop.expected = 140;
|
|
|
|
test(xprop);
|
2008-07-15 10:17:51 -07:00
|
|
|
|
2008-07-15 18:37:00 -07:00
|
|
|
var a = 2;
|
2008-07-31 12:15:22 -07:00
|
|
|
function getprop_inner(o2)
|
2008-07-15 10:17:51 -07:00
|
|
|
{
|
|
|
|
var o = {a:5};
|
2008-07-15 18:37:00 -07:00
|
|
|
var t = this;
|
2008-07-15 10:17:51 -07:00
|
|
|
var x = 0;
|
2008-07-15 18:37:00 -07:00
|
|
|
for (var i = 0; i < 20; i++) {
|
|
|
|
t = this;
|
|
|
|
x += o.a + o2.a + this.a + t.a;
|
|
|
|
}
|
2008-07-15 10:17:51 -07:00
|
|
|
return x;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
function getprop() {
|
|
|
|
return getprop_inner({a:9});
|
|
|
|
}
|
|
|
|
getprop.expected = 360;
|
|
|
|
test(getprop);
|
2008-07-15 20:19:29 -07:00
|
|
|
|
|
|
|
function mod()
|
|
|
|
{
|
|
|
|
var mods = [-1,-1,-1,-1];
|
|
|
|
var a = 9.5, b = -5, c = 42, d = (1/0);
|
|
|
|
for (var i = 0; i < 20; i++) {
|
|
|
|
mods[0] = a % b;
|
|
|
|
mods[1] = b % 1;
|
|
|
|
mods[2] = c % d;
|
|
|
|
mods[3] = c % a;
|
|
|
|
mods[4] = b % 0;
|
|
|
|
}
|
|
|
|
return mods.toString();
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
mod.expected = "4.5,0,42,4,NaN";
|
|
|
|
test(mod);
|
2008-07-16 15:26:51 -07:00
|
|
|
|
2008-07-16 18:08:58 -07:00
|
|
|
function glob_f1() {
|
2008-07-16 15:40:35 -07:00
|
|
|
return 1;
|
|
|
|
}
|
2008-07-16 18:08:58 -07:00
|
|
|
function glob_f2() {
|
|
|
|
return glob_f1();
|
|
|
|
}
|
2008-07-16 15:26:51 -07:00
|
|
|
function call()
|
|
|
|
{
|
2008-07-16 22:08:59 -07:00
|
|
|
var q1 = 0, q2 = 0, q3 = 0, q4 = 0, q5 = 0;
|
2008-07-16 15:53:04 -07:00
|
|
|
var o = {};
|
2008-07-16 15:26:51 -07:00
|
|
|
function f1() {
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
function f2(f) {
|
2008-07-16 22:08:59 -07:00
|
|
|
return f();
|
2008-07-16 18:08:58 -07:00
|
|
|
}
|
2008-07-16 15:53:04 -07:00
|
|
|
o.f = f1;
|
2008-07-16 15:26:51 -07:00
|
|
|
for (var i = 0; i < 100; ++i) {
|
|
|
|
q1 += f1();
|
|
|
|
q2 += f2(f1);
|
2008-07-16 18:08:58 -07:00
|
|
|
q3 += glob_f1();
|
2008-07-16 15:53:04 -07:00
|
|
|
q4 += o.f();
|
2008-07-16 22:08:59 -07:00
|
|
|
q5 += glob_f2();
|
2008-07-17 01:58:34 -07:00
|
|
|
}
|
2008-07-16 22:08:59 -07:00
|
|
|
var ret = [q1, q2, q3, q4, q5];
|
2008-07-16 15:26:51 -07:00
|
|
|
return ret;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
call.expected = "100,100,100,100,100";
|
|
|
|
test(call);
|
2008-07-17 02:00:23 -07:00
|
|
|
|
|
|
|
function setprop()
|
|
|
|
{
|
|
|
|
var obj = { a:-1 };
|
|
|
|
var obj2 = { b:-1, a:-1 };
|
|
|
|
for (var i = 0; i < 20; i++) {
|
|
|
|
obj2.b = obj.a = i;
|
|
|
|
}
|
|
|
|
return [obj.a, obj2.a, obj2.b].toString();
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
setprop.expected = "19,-1,19";
|
|
|
|
test(setprop);
|
2008-07-17 02:03:56 -07:00
|
|
|
|
2008-07-18 10:33:17 -07:00
|
|
|
function testif() {
|
|
|
|
var q = 0;
|
|
|
|
for (var i = 0; i < 100; i++) {
|
|
|
|
if ((i & 1) == 0)
|
|
|
|
q++;
|
|
|
|
else
|
|
|
|
q--;
|
|
|
|
}
|
|
|
|
return q;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
testif.expected = "0";
|
|
|
|
test(testif);
|
2008-07-18 10:33:17 -07:00
|
|
|
|
2008-08-12 08:33:40 -07:00
|
|
|
var globalinc = 0;
|
2008-07-19 10:24:28 -07:00
|
|
|
function testincops(n) {
|
2008-07-19 10:24:10 -07:00
|
|
|
var i = 0, o = {p:0}, a = [0];
|
2008-07-31 12:15:22 -07:00
|
|
|
n = 100;
|
2008-07-19 10:24:28 -07:00
|
|
|
|
2008-07-19 10:24:10 -07:00
|
|
|
for (i = 0; i < n; i++);
|
|
|
|
while (i-- > 0);
|
|
|
|
for (i = 0; i < n; ++i);
|
|
|
|
while (--i >= 0);
|
2008-07-19 10:24:28 -07:00
|
|
|
|
2008-08-12 08:33:40 -07:00
|
|
|
for (o.p = 0; o.p < n; o.p++) globalinc++;
|
|
|
|
while (o.p-- > 0) --globalinc;
|
|
|
|
for (o.p = 0; o.p < n; ++o.p) ++globalinc;
|
|
|
|
while (--o.p >= 0) globalinc--;
|
2008-07-19 10:24:28 -07:00
|
|
|
|
2008-07-19 10:24:10 -07:00
|
|
|
++i; // set to 0
|
|
|
|
for (a[i] = 0; a[i] < n; a[i]++);
|
|
|
|
while (a[i]-- > 0);
|
|
|
|
for (a[i] = 0; a[i] < n; ++a[i]);
|
|
|
|
while (--a[i] >= 0);
|
2008-07-19 10:24:28 -07:00
|
|
|
|
2008-08-12 08:33:40 -07:00
|
|
|
return [++o.p, ++a[i], globalinc].toString();
|
2008-07-19 10:24:28 -07:00
|
|
|
}
|
2008-08-12 08:33:40 -07:00
|
|
|
testincops.expected = "0,0,0";
|
2008-07-31 12:15:22 -07:00
|
|
|
test(testincops);
|
2008-07-20 13:17:58 -07:00
|
|
|
|
2008-07-25 19:10:23 -07:00
|
|
|
function trees() {
|
2008-07-29 07:32:18 -07:00
|
|
|
var i = 0, o = [0,0,0];
|
2008-07-25 19:10:23 -07:00
|
|
|
for (i = 0; i < 100; ++i) {
|
|
|
|
if ((i & 1) == 0) o[0]++;
|
|
|
|
else if ((i & 2) == 0) o[1]++;
|
|
|
|
else o[2]++;
|
|
|
|
}
|
|
|
|
return o;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
trees.expected = "50,25,25";
|
|
|
|
test(trees);
|
2008-07-25 19:10:23 -07:00
|
|
|
|
2008-07-27 14:55:26 -07:00
|
|
|
function unboxint() {
|
|
|
|
var q = 0;
|
|
|
|
var o = [4];
|
2008-07-29 07:32:18 -07:00
|
|
|
for (var i = 0; i < 100; ++i)
|
2008-07-27 14:55:26 -07:00
|
|
|
q = o[0] << 1;
|
|
|
|
return q;
|
|
|
|
}
|
2008-07-31 12:15:22 -07:00
|
|
|
unboxint.expected = "8";
|
|
|
|
test(unboxint);
|
2008-07-27 14:55:26 -07:00
|
|
|
|
2008-07-29 07:32:18 -07:00
|
|
|
function strings()
|
|
|
|
{
|
|
|
|
var a = [], b = -1;
|
2008-07-30 15:19:25 -07:00
|
|
|
var s = "abcdefghij", s2 = "a";
|
2008-07-30 17:28:59 -07:00
|
|
|
var f = "f";
|
2008-08-09 18:50:52 -07:00
|
|
|
var c = 0, d = 0, e = 0, g = 0;
|
2008-07-29 07:32:18 -07:00
|
|
|
for (var i = 0; i < 10; i++) {
|
2008-08-11 20:26:04 -07:00
|
|
|
a[i] = (s.substring(i, i+1) + s[i] + String.fromCharCode(s2.charCodeAt(0) + i)).concat(i) + i;
|
2008-07-30 17:28:59 -07:00
|
|
|
if (s[i] == f)
|
|
|
|
c++;
|
|
|
|
if (s[i] != 'b')
|
|
|
|
d++;
|
2008-08-09 18:50:52 -07:00
|
|
|
if ("B" > s2)
|
|
|
|
g++; // f already used
|
|
|
|
if (s2 < "b")
|
|
|
|
e++;
|
2008-07-29 07:32:18 -07:00
|
|
|
b = s.length;
|
|
|
|
}
|
2008-08-09 18:50:52 -07:00
|
|
|
return a.toString() + b + c + d + e + g;
|
2008-07-29 07:32:18 -07:00
|
|
|
}
|
2008-08-11 20:26:04 -07:00
|
|
|
strings.expected = "aaa00,bbb11,ccc22,ddd33,eee44,fff55,ggg66,hhh77,iii88,jjj991019100";
|
2008-07-31 12:15:22 -07:00
|
|
|
test(strings);
|
2008-07-29 07:32:18 -07:00
|
|
|
|
2008-08-11 20:26:04 -07:00
|
|
|
function dependentStrings()
|
|
|
|
{
|
|
|
|
var a = [];
|
|
|
|
var t = "abcdefghijklmnopqrst";
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
var s = t.substring(2*i, 2*i + 2);
|
|
|
|
a[i] = s + s.length;
|
|
|
|
}
|
|
|
|
return a.join("");
|
|
|
|
}
|
|
|
|
dependentStrings.expected = "ab2cd2ef2gh2ij2kl2mn2op2qr2st2";
|
|
|
|
test(dependentStrings);
|
|
|
|
|
2008-07-31 07:41:58 -07:00
|
|
|
function stringConvert()
|
|
|
|
{
|
|
|
|
var a = [];
|
|
|
|
var s1 = "F", s2 = "1.3", s3 = "5";
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
a[0] = 1 >> s1;
|
|
|
|
a[1] = 10 - s2;
|
|
|
|
a[2] = 15 * s3;
|
|
|
|
a[3] = s3 | 32;
|
2008-08-11 22:05:33 -07:00
|
|
|
a[4] = s2 + 60;
|
2008-07-31 07:41:58 -07:00
|
|
|
// a[5] = 9 + s3;
|
|
|
|
// a[6] = -s3;
|
|
|
|
a[7] = s3 & "7";
|
|
|
|
// a[8] = ~s3;
|
|
|
|
}
|
|
|
|
return a.toString();
|
|
|
|
}
|
2008-08-11 22:05:33 -07:00
|
|
|
stringConvert.expected = "1,8.7,75,37,1.360,,,5";
|
2008-07-31 12:15:22 -07:00
|
|
|
test(stringConvert);
|
2008-07-31 07:41:58 -07:00
|
|
|
|
2008-08-02 15:56:28 -07:00
|
|
|
function orTestHelper(a, b, n)
|
|
|
|
{
|
|
|
|
var k = 0;
|
|
|
|
for (var i = 0; i < n; i++) {
|
|
|
|
if (a || b)
|
|
|
|
k += i;
|
|
|
|
}
|
|
|
|
return k;
|
|
|
|
}
|
|
|
|
|
2008-08-12 15:45:06 -07:00
|
|
|
var orNaNTest1, orNaNTest2;
|
|
|
|
|
|
|
|
orNaNTest1 = new Function("return orTestHelper(NaN, NaN, 10);");
|
|
|
|
orNaNTest1.name = 'orNaNTest1';
|
|
|
|
orNaNTest1.expected = '0';
|
|
|
|
orNaNTest2 = new Function("return orTestHelper(NaN, 1, 10);");
|
|
|
|
orNaNTest2.name = 'orNaNTest2';
|
|
|
|
orNaNTest2.expected = '45';
|
|
|
|
test(orNaNTest1);
|
|
|
|
test(orNaNTest2);
|
|
|
|
|
2008-08-02 15:56:28 -07:00
|
|
|
function andTestHelper(a, b, n)
|
|
|
|
{
|
|
|
|
var k = 0;
|
|
|
|
for (var i = 0; i < n; i++) {
|
|
|
|
if (a && b)
|
|
|
|
k += i;
|
|
|
|
}
|
|
|
|
return k;
|
|
|
|
}
|
|
|
|
|
2008-08-09 18:50:52 -07:00
|
|
|
if (!testName || testName == "truthies") {
|
|
|
|
(function () {
|
|
|
|
var opsies = ["||", "&&"];
|
|
|
|
var falsies = [null, undefined, false, NaN, 0, ""];
|
|
|
|
var truthies = [{}, true, 1, 42, 1/0, -1/0, "blah"];
|
|
|
|
var boolies = [falsies, truthies];
|
|
|
|
|
|
|
|
// The for each here should abort tracing, so that this test framework
|
|
|
|
// relies only on the interpreter while the orTestHelper and andTestHelper
|
|
|
|
// functions get trace-JITed.
|
|
|
|
for each (var op in opsies) {
|
|
|
|
for (var i in boolies) {
|
|
|
|
for (var j in boolies[i]) {
|
|
|
|
var x = uneval(boolies[i][j]);
|
|
|
|
for (var k in boolies) {
|
|
|
|
for (var l in boolies[k]) {
|
|
|
|
var y = uneval(boolies[k][l]);
|
|
|
|
var prefix = (op == "||") ? "or" : "and";
|
|
|
|
var f = new Function("return " + prefix + "TestHelper(" + x + "," + y + ",10)");
|
|
|
|
f.name = prefix + "Test(" + x + "," + y + ")";
|
|
|
|
f.expected = eval(x + op + y) ? 45 : 0;
|
|
|
|
test(f);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
})();
|
|
|
|
}
|
2008-08-02 15:56:28 -07:00
|
|
|
|
2008-08-06 13:53:34 -07:00
|
|
|
function nonEmptyStack1Helper(o, farble) {
|
|
|
|
var a = [];
|
|
|
|
var j = 0;
|
|
|
|
for (var i in o)
|
|
|
|
a[j++] = i;
|
2008-08-06 17:44:39 -07:00
|
|
|
return a.join("");
|
2008-08-06 13:53:34 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
function nonEmptyStack1() {
|
2008-08-06 17:44:39 -07:00
|
|
|
return nonEmptyStack1Helper({a:1,b:2,c:3,d:4,e:5,f:6,g:7,h:8}, "hi");
|
2008-08-06 13:53:34 -07:00
|
|
|
}
|
|
|
|
|
2008-08-06 19:24:39 -07:00
|
|
|
nonEmptyStack1.expected = "abcdefgh";
|
2008-08-06 17:44:39 -07:00
|
|
|
test(nonEmptyStack1);
|
2008-08-06 13:53:34 -07:00
|
|
|
|
|
|
|
function nonEmptyStack2()
|
2008-08-06 13:12:49 -07:00
|
|
|
{
|
|
|
|
var a = 0;
|
|
|
|
for (var c in {a:1, b:2, c:3}) {
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
a += i;
|
|
|
|
}
|
|
|
|
return String(a);
|
|
|
|
}
|
2008-08-06 13:53:34 -07:00
|
|
|
nonEmptyStack2.expected = "135";
|
|
|
|
test(nonEmptyStack2);
|
2008-08-06 13:12:49 -07:00
|
|
|
|
2008-08-06 19:24:39 -07:00
|
|
|
function arityMismatchMissingArg(arg)
|
|
|
|
{
|
|
|
|
for (var a = 0, i = 1; i < 10000; i *= 2) {
|
|
|
|
a += i;
|
|
|
|
}
|
|
|
|
return a;
|
|
|
|
}
|
|
|
|
arityMismatchMissingArg.expected = 16383;
|
|
|
|
test(arityMismatchMissingArg);
|
|
|
|
|
|
|
|
function arityMismatchExtraArg()
|
|
|
|
{
|
|
|
|
return arityMismatchMissingArg(1, 2);
|
|
|
|
}
|
|
|
|
arityMismatchExtraArg.expected = 16383;
|
|
|
|
test(arityMismatchExtraArg);
|
|
|
|
|
2008-08-08 14:38:44 -07:00
|
|
|
function MyConstructor(i)
|
|
|
|
{
|
|
|
|
this.i = i;
|
|
|
|
}
|
|
|
|
MyConstructor.prototype.toString = function() {return this.i + ""};
|
|
|
|
|
2008-08-09 22:24:49 -07:00
|
|
|
function newTest()
|
2008-08-08 14:38:44 -07:00
|
|
|
{
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
a[i] = new MyConstructor(i);
|
|
|
|
return a.join("");
|
|
|
|
}
|
2008-08-09 22:24:49 -07:00
|
|
|
newTest.expected = "0123456789";
|
|
|
|
test(newTest);
|
2008-08-08 14:38:44 -07:00
|
|
|
|
2008-08-10 22:36:48 -07:00
|
|
|
// The following functions use a delay line of length 2 to change the value
|
|
|
|
// of the callee without exiting the traced loop. This is obviously tuned to
|
|
|
|
// match the current HOTLOOP setting of 2.
|
|
|
|
function shapelessArgCalleeLoop(f, g, h, a)
|
2008-08-08 16:37:01 -07:00
|
|
|
{
|
2008-08-10 22:36:48 -07:00
|
|
|
for (var i = 0; i < 10; i++) {
|
2008-08-08 16:37:01 -07:00
|
|
|
f(i, a);
|
2008-08-10 22:36:48 -07:00
|
|
|
f = g;
|
|
|
|
g = h;
|
|
|
|
}
|
2008-08-08 16:37:01 -07:00
|
|
|
}
|
|
|
|
|
2008-08-10 22:36:48 -07:00
|
|
|
function shapelessVarCalleeLoop(f0, g, h, a)
|
2008-08-08 16:37:01 -07:00
|
|
|
{
|
2008-08-10 22:36:48 -07:00
|
|
|
var f = f0;
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
f(i, a);
|
|
|
|
f = g;
|
|
|
|
g = h;
|
|
|
|
}
|
2008-08-08 16:37:01 -07:00
|
|
|
}
|
|
|
|
|
2008-08-10 22:36:48 -07:00
|
|
|
function shapelessLetCalleeLoop(f0, g, h, a)
|
2008-08-08 16:37:01 -07:00
|
|
|
{
|
|
|
|
for (var i = 0; i < 10; i++) {
|
2008-08-10 22:36:48 -07:00
|
|
|
let f = f0;
|
|
|
|
f(i, a);
|
|
|
|
f = g;
|
|
|
|
g = h;
|
2008-08-08 16:37:01 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-08-10 22:36:48 -07:00
|
|
|
function shapelessUnknownCalleeLoop(n, f, g, h, a)
|
2008-08-08 16:37:01 -07:00
|
|
|
{
|
|
|
|
for (var i = 0; i < 10; i++) {
|
2008-08-10 22:36:48 -07:00
|
|
|
(n || f)(i, a);
|
|
|
|
f = g;
|
|
|
|
g = h;
|
2008-08-08 16:37:01 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-08-09 22:24:49 -07:00
|
|
|
function shapelessCalleeTest()
|
2008-08-08 16:37:01 -07:00
|
|
|
{
|
|
|
|
var a = [];
|
2008-08-10 22:36:48 -07:00
|
|
|
|
|
|
|
var helper = function (i, a) a[i] = i;
|
|
|
|
shapelessArgCalleeLoop(helper, helper, function (i, a) a[i] = -i, a);
|
|
|
|
|
|
|
|
helper = function (i, a) a[10 + i] = i;
|
|
|
|
shapelessVarCalleeLoop(helper, helper, function (i, a) a[10 + i] = -i, a);
|
|
|
|
|
|
|
|
helper = function (i, a) a[20 + i] = i;
|
|
|
|
shapelessLetCalleeLoop(helper, helper, function (i, a) a[20 + i] = -i, a);
|
|
|
|
|
|
|
|
helper = function (i, a) a[30 + i] = i;
|
|
|
|
shapelessUnknownCalleeLoop(null, helper, helper, function (i, a) a[30 + i] = -i, a);
|
|
|
|
|
2008-08-08 16:37:01 -07:00
|
|
|
try {
|
2008-08-10 22:36:48 -07:00
|
|
|
helper = {hack: 42};
|
|
|
|
shapelessUnknownCalleeLoop(null, helper, helper, helper, a);
|
2008-08-08 16:37:01 -07:00
|
|
|
} catch (e) {
|
2008-08-12 16:36:32 -07:00
|
|
|
if (e + "" != "TypeError: f is not a function")
|
2008-08-09 22:24:49 -07:00
|
|
|
print("shapelessUnknownCalleeLoop: unexpected exception " + e);
|
2008-08-08 16:37:01 -07:00
|
|
|
}
|
|
|
|
return a.join("");
|
|
|
|
}
|
2008-08-10 22:36:48 -07:00
|
|
|
shapelessCalleeTest.expected = "01-2-3-4-5-6-7-8-901-2-3-4-5-6-7-8-9012345678901-2-3-4-5-6-7-8-9";
|
2008-08-09 22:24:49 -07:00
|
|
|
test(shapelessCalleeTest);
|
2008-08-08 16:37:01 -07:00
|
|
|
|
2008-08-09 19:54:01 -07:00
|
|
|
function typeofTest()
|
|
|
|
{
|
|
|
|
var values = ["hi", "hi", "hi", null, 5, 5.1, true, undefined, /foo/, typeofTest, [], {}], types = [];
|
|
|
|
for (var i = 0; i < values.length; i++)
|
|
|
|
types[i] = typeof values[i];
|
|
|
|
return types.toString();
|
|
|
|
}
|
|
|
|
typeofTest.expected = "string,string,string,object,number,number,boolean,undefined,object,function,object,object";
|
|
|
|
test(typeofTest);
|
|
|
|
|
2008-08-10 15:21:14 -07:00
|
|
|
function joinTest()
|
|
|
|
{
|
|
|
|
var s = "";
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 8; i++)
|
|
|
|
a[i] = [String.fromCharCode(97 + i)];
|
|
|
|
for (i = 0; i < 8; i++) {
|
|
|
|
for (var j = 0; j < 8; j++)
|
|
|
|
a[i][1 + j] = j;
|
|
|
|
}
|
|
|
|
for (i = 0; i < 8; i++)
|
|
|
|
s += a[i].join(",");
|
|
|
|
return s;
|
|
|
|
}
|
|
|
|
joinTest.expected = "a,0,1,2,3,4,5,6,7b,0,1,2,3,4,5,6,7c,0,1,2,3,4,5,6,7d,0,1,2,3,4,5,6,7e,0,1,2,3,4,5,6,7f,0,1,2,3,4,5,6,7g,0,1,2,3,4,5,6,7h,0,1,2,3,4,5,6,7";
|
|
|
|
test(joinTest);
|
|
|
|
|
2008-08-14 15:13:39 -07:00
|
|
|
function arity1(x)
|
2008-08-12 16:51:55 -07:00
|
|
|
{
|
2008-08-12 16:57:55 -07:00
|
|
|
return (x == undefined) ? 1 : 0;
|
2008-08-12 16:51:55 -07:00
|
|
|
}
|
|
|
|
function missingArgTest() {
|
|
|
|
var q;
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
q = arity1();
|
|
|
|
}
|
|
|
|
return q;
|
|
|
|
}
|
|
|
|
missingArgTest.expected = "1"
|
|
|
|
test(missingArgTest);
|
|
|
|
|
2008-08-12 23:58:50 -07:00
|
|
|
JSON = function () {
|
|
|
|
return {
|
|
|
|
stringify: function stringify(value, whitelist) {
|
|
|
|
switch (typeof(value)) {
|
|
|
|
case "object":
|
|
|
|
return value.constructor.name;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
}();
|
|
|
|
|
|
|
|
function missingArgTest2() {
|
|
|
|
var testPairs = [
|
|
|
|
["{}", {}],
|
|
|
|
["[]", []],
|
|
|
|
['{"foo":"bar"}', {"foo":"bar"}],
|
|
|
|
]
|
2008-08-14 15:13:39 -07:00
|
|
|
|
2008-08-12 23:58:50 -07:00
|
|
|
var a = [];
|
|
|
|
for (var i=0; i < testPairs.length; i++) {
|
|
|
|
var s = JSON.stringify(testPairs[i][1])
|
|
|
|
a[i] = s;
|
|
|
|
}
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
missingArgTest2.expected = "Object,Array,Object";
|
|
|
|
test(missingArgTest2);
|
|
|
|
|
2008-08-13 00:41:13 -07:00
|
|
|
function deepForInLoop() {
|
|
|
|
// NB: the number of props set in C is arefully tuned to match HOTLOOP = 2.
|
|
|
|
function C(){this.p = 1, this.q = 2}
|
|
|
|
C.prototype = {p:1, q:2, r:3, s:4, t:5};
|
|
|
|
var o = new C;
|
|
|
|
var j = 0;
|
|
|
|
var a = [];
|
|
|
|
for (var i in o)
|
|
|
|
a[j++] = i;
|
|
|
|
return a.join("");
|
|
|
|
}
|
|
|
|
deepForInLoop.expected = "pqrst";
|
|
|
|
test(deepForInLoop);
|
|
|
|
|
2008-08-13 18:13:22 -07:00
|
|
|
function nestedExit(x) {
|
|
|
|
var q = 0;
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
if (x)
|
|
|
|
++q;
|
|
|
|
}
|
|
|
|
function nestedExitLoop() {
|
|
|
|
for (var j = 0; j < 10; ++j)
|
|
|
|
nestedExit(j < 7);
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
nestedExitLoop.expected = "ok";
|
|
|
|
test(nestedExitLoop);
|
|
|
|
|
2008-08-13 21:44:01 -07:00
|
|
|
function bitsinbyte(b) {
|
|
|
|
var m = 1, c = 0;
|
|
|
|
while(m<0x100) {
|
|
|
|
if(b & m) c++;
|
|
|
|
m <<= 1;
|
|
|
|
}
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
function TimeFunc(func) {
|
|
|
|
var x,y;
|
|
|
|
for(var y=0; y<256; y++) func(y);
|
|
|
|
}
|
|
|
|
function nestedExit2() {
|
|
|
|
TimeFunc(bitsinbyte);
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
nestedExit2.expected = "ok";
|
|
|
|
test(nestedExit2);
|
|
|
|
|
2008-08-14 15:13:39 -07:00
|
|
|
function parsingNumbers() {
|
|
|
|
var s1 = "123";
|
|
|
|
var s1z = "123zzz";
|
|
|
|
var s2 = "123.456";
|
|
|
|
var s2z = "123.456zzz";
|
|
|
|
|
|
|
|
var e1 = 123;
|
|
|
|
var e2 = 123.456;
|
|
|
|
|
|
|
|
var r1, r1z, r2, r2z;
|
|
|
|
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
r1 = parseInt(s1);
|
|
|
|
r1z = parseInt(s1z);
|
|
|
|
r2 = parseFloat(s2);
|
|
|
|
r2z = parseFloat(s2z);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (r1 == e1 && r1z == e1 && r2 == e2 && r2z == e2)
|
|
|
|
return "ok";
|
|
|
|
return "fail";
|
|
|
|
}
|
|
|
|
parsingNumbers.expected = "ok";
|
|
|
|
test(parsingNumbers);
|
|
|
|
|
2008-08-15 09:29:03 -07:00
|
|
|
function matchInLoop() {
|
|
|
|
var k = "hi";
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
var result = k.match(/hi/) != null;
|
|
|
|
}
|
|
|
|
return result;
|
|
|
|
}
|
|
|
|
matchInLoop.expected = true;
|
|
|
|
test(matchInLoop);
|
|
|
|
|
2008-08-15 10:09:36 -07:00
|
|
|
function deep1(x) {
|
2008-08-21 00:50:20 -07:00
|
|
|
if (x > 90)
|
2008-08-15 10:09:36 -07:00
|
|
|
return 1;
|
|
|
|
return 2;
|
|
|
|
}
|
|
|
|
function deep2() {
|
|
|
|
for (var i = 0; i < 100; ++i)
|
|
|
|
deep1(i);
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
deep2.expected = "ok";
|
2008-08-19 23:31:33 -07:00
|
|
|
test(deep2);
|
2008-08-15 10:09:36 -07:00
|
|
|
|
2008-08-15 16:04:44 -07:00
|
|
|
var merge_type_maps_x = 0, merge_type_maps_y = 0;
|
|
|
|
function merge_type_maps() {
|
2008-08-21 00:50:20 -07:00
|
|
|
for (merge_type_maps_x = 0; merge_type_maps_x < 50; ++merge_type_maps_x)
|
2008-08-15 16:04:44 -07:00
|
|
|
if ((merge_type_maps_x & 1) == 1)
|
|
|
|
++merge_type_maps_y;
|
|
|
|
return [merge_type_maps_x,merge_type_maps_y].join(",");
|
|
|
|
}
|
|
|
|
merge_type_maps.expected = "50,25";
|
2008-08-19 23:28:13 -07:00
|
|
|
test(merge_type_maps)
|
2008-08-15 16:04:44 -07:00
|
|
|
|
2008-08-20 00:51:56 -07:00
|
|
|
function inner_double_outer_int() {
|
|
|
|
function f(i) {
|
|
|
|
for (var m = 0; m < 20; ++m)
|
|
|
|
for (var n = 0; n < 100; n += i)
|
|
|
|
;
|
|
|
|
return n;
|
|
|
|
}
|
|
|
|
return f(.5);
|
|
|
|
}
|
|
|
|
inner_double_outer_int.expected = "100";
|
|
|
|
test(inner_double_outer_int);
|
|
|
|
|
2008-08-21 00:50:20 -07:00
|
|
|
function newArrayTest()
|
|
|
|
{
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
a[i] = new Array();
|
|
|
|
return a.map(function(x) x.length).toString();
|
|
|
|
}
|
|
|
|
newArrayTest.expected="0,0,0,0,0,0,0,0,0,0";
|
|
|
|
test(newArrayTest);
|
|
|
|
|
2008-08-21 11:06:42 -07:00
|
|
|
function stringSplitTest()
|
|
|
|
{
|
|
|
|
var s = "a,b"
|
|
|
|
var a = null;
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
a = s.split(",");
|
|
|
|
return a.join();
|
|
|
|
}
|
|
|
|
stringSplitTest.expected="a,b";
|
|
|
|
test(stringSplitTest);
|
|
|
|
|
|
|
|
function stringSplitIntoArrayTest()
|
|
|
|
{
|
|
|
|
var s = "a,b"
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
a[i] = s.split(",");
|
|
|
|
return a.join();
|
|
|
|
}
|
|
|
|
stringSplitIntoArrayTest.expected="a,b,a,b,a,b,a,b,a,b,a,b,a,b,a,b,a,b,a,b";
|
|
|
|
test(stringSplitIntoArrayTest);
|
2008-08-21 00:50:20 -07:00
|
|
|
|
2008-08-26 12:50:01 -07:00
|
|
|
function forVarInWith() {
|
|
|
|
function foo() ({notk:42});
|
|
|
|
function bar() ({p:1, q:2, r:3, s:4, t:5});
|
|
|
|
var o = foo();
|
|
|
|
var a = [];
|
|
|
|
with (o) {
|
|
|
|
for (var k in bar())
|
|
|
|
a[a.length] = k;
|
|
|
|
}
|
|
|
|
return a.join("");
|
|
|
|
}
|
|
|
|
forVarInWith.expected = "pqrst";
|
|
|
|
test(forVarInWith);
|
|
|
|
|
2008-08-27 23:00:43 -07:00
|
|
|
function inObjectTest() {
|
|
|
|
var o = {p: 1, q: 2, r: 3, s: 4, t: 5};
|
|
|
|
var r = 0;
|
|
|
|
for (var i in o) {
|
|
|
|
if (!(i in o))
|
|
|
|
break;
|
|
|
|
if ((i + i) in o)
|
|
|
|
break;
|
|
|
|
++r;
|
|
|
|
}
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
inObjectTest.expected = 5;
|
|
|
|
test(inObjectTest);
|
|
|
|
|
|
|
|
function inArrayTest() {
|
|
|
|
var a = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
|
|
|
|
for (var i = 0; i < a.length; i++) {
|
|
|
|
if (!(i in a))
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
return i;
|
|
|
|
}
|
|
|
|
inArrayTest.expected = 10;
|
|
|
|
test(inArrayTest);
|
|
|
|
|
2008-08-22 17:31:23 -07:00
|
|
|
function innerLoopIntOuterDouble() {
|
|
|
|
var n = 10000, i=0, j=0, count=0, limit=0;
|
|
|
|
for (i = 1; i <= n; ++i) {
|
|
|
|
limit = i * 1;
|
|
|
|
for (j = 0; j < limit; ++j) {
|
|
|
|
++count;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return "" + count;
|
|
|
|
}
|
|
|
|
innerLoopIntOuterDouble.expected="50005000";
|
|
|
|
test(innerLoopIntOuterDouble);
|
|
|
|
|
2008-08-23 15:11:38 -07:00
|
|
|
function outerline(){
|
|
|
|
var i=0;
|
|
|
|
var j=0;
|
|
|
|
|
|
|
|
for (i = 3; i<= 100000; i+=2)
|
|
|
|
for (j = 3; j < 1000; j+=2)
|
|
|
|
if ((i & 1) == 1)
|
|
|
|
break;
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
outerline.expected="ok";
|
|
|
|
test(outerline);
|
|
|
|
|
2008-08-25 14:12:41 -07:00
|
|
|
function addAccumulations(f) {
|
|
|
|
var a = f();
|
|
|
|
var b = f();
|
|
|
|
return a() + b();
|
|
|
|
}
|
|
|
|
|
|
|
|
function loopingAccumulator() {
|
|
|
|
var x = 0;
|
|
|
|
return function () {
|
|
|
|
for (var i = 0; i < 10; ++i) {
|
|
|
|
++x;
|
|
|
|
}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
function testLoopingAccumulator() {
|
|
|
|
var x = addAccumulations(loopingAccumulator);
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testLoopingAccumulator.expected = 20;
|
|
|
|
test(testLoopingAccumulator);
|
|
|
|
|
2008-08-26 15:46:50 -07:00
|
|
|
function testBranchingLoop() {
|
|
|
|
var x = 0;
|
|
|
|
for (var i=0; i < 100; ++i) {
|
|
|
|
if (i == 51) {
|
|
|
|
x += 10;
|
|
|
|
}
|
|
|
|
x++;
|
|
|
|
}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testBranchingLoop.expected = 110;
|
|
|
|
test(testBranchingLoop);
|
|
|
|
|
|
|
|
function testBranchingUnstableLoop() {
|
|
|
|
var x = 0;
|
|
|
|
for (var i=0; i < 100; ++i) {
|
|
|
|
if (i == 51) {
|
|
|
|
x += 10.1;
|
|
|
|
}
|
|
|
|
x++;
|
|
|
|
}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testBranchingUnstableLoop.expected = 110.1;
|
|
|
|
test(testBranchingUnstableLoop);
|
|
|
|
|
|
|
|
function testBranchingUnstableLoopCounter() {
|
|
|
|
var x = 0;
|
|
|
|
for (var i=0; i < 100; ++i) {
|
|
|
|
if (i == 51) {
|
|
|
|
i += 1.1;
|
|
|
|
}
|
|
|
|
x++;
|
|
|
|
}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testBranchingUnstableLoopCounter.expected = 99;
|
|
|
|
test(testBranchingUnstableLoopCounter);
|
|
|
|
|
|
|
|
|
|
|
|
function testBranchingUnstableObject() {
|
|
|
|
var x = {s: "a"};
|
|
|
|
var t = "";
|
|
|
|
for (var i=0; i < 100; ++i) {
|
|
|
|
if (i == 51)
|
|
|
|
{
|
|
|
|
x.s = 5;
|
|
|
|
}
|
|
|
|
t += x.s;
|
|
|
|
}
|
|
|
|
return t.length;
|
|
|
|
}
|
|
|
|
testBranchingUnstableObject.expected = 100;
|
|
|
|
test(testBranchingUnstableObject);
|
|
|
|
|
|
|
|
function testArrayDensityChange() {
|
|
|
|
var x = [];
|
|
|
|
var count = 0;
|
|
|
|
for (var i=0; i < 100; ++i) {
|
|
|
|
x[i] = "asdf";
|
|
|
|
}
|
|
|
|
for (var i=0; i < x.length; ++i) {
|
|
|
|
if (i == 51)
|
|
|
|
{
|
|
|
|
x[199] = "asdf";
|
|
|
|
}
|
|
|
|
if (x[i])
|
|
|
|
count += x[i].length;
|
|
|
|
}
|
|
|
|
return count;
|
|
|
|
}
|
|
|
|
testArrayDensityChange.expected = 404;
|
|
|
|
test(testArrayDensityChange);
|
|
|
|
|
2008-08-26 20:02:59 -07:00
|
|
|
function testDoubleToStr() {
|
|
|
|
var x = 0.0;
|
|
|
|
var y = 5.5;
|
|
|
|
for (var i = 0; i < 200; i++) {
|
|
|
|
x += parseFloat(y.toString());
|
|
|
|
}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testDoubleToStr.expected = 5.5*200;
|
|
|
|
test(testDoubleToStr);
|
|
|
|
|
2008-10-08 15:19:15 -07:00
|
|
|
function testNumberToString() {
|
|
|
|
var x = new Number(0);
|
|
|
|
for (var i = 0; i < 4; i++)
|
|
|
|
x.toString();
|
|
|
|
}
|
|
|
|
test(testNumberToString);
|
|
|
|
|
2008-08-26 21:45:53 -07:00
|
|
|
function testDecayingInnerLoop() {
|
|
|
|
var i, j, k = 10;
|
|
|
|
for (i = 0; i < 5000; ++i) {
|
|
|
|
for (j = 0; j < k; ++j);
|
|
|
|
--k;
|
|
|
|
}
|
|
|
|
return i;
|
|
|
|
}
|
|
|
|
testDecayingInnerLoop.expected = 5000;
|
|
|
|
test(testDecayingInnerLoop);
|
|
|
|
|
2008-08-29 08:01:56 -07:00
|
|
|
function testContinue() {
|
|
|
|
var i;
|
|
|
|
var total = 0;
|
|
|
|
for (i = 0; i < 20; ++i) {
|
|
|
|
if (i == 11)
|
|
|
|
continue;
|
|
|
|
total++;
|
|
|
|
}
|
|
|
|
return total;
|
|
|
|
}
|
|
|
|
testContinue.expected = 19;
|
|
|
|
test(testContinue);
|
|
|
|
|
|
|
|
function testContinueWithLabel() {
|
|
|
|
var i = 0;
|
|
|
|
var j = 20;
|
|
|
|
checkiandj :
|
|
|
|
while (i<10) {
|
|
|
|
i+=1;
|
|
|
|
checkj :
|
|
|
|
while (j>10) {
|
|
|
|
j-=1;
|
|
|
|
if ((j%2)==0)
|
|
|
|
continue checkj;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return i + j;
|
|
|
|
}
|
|
|
|
testContinueWithLabel.expected = 20;
|
|
|
|
test(testContinueWithLabel);
|
|
|
|
|
2008-08-29 10:04:08 -07:00
|
|
|
function testDivision() {
|
|
|
|
var a = 32768;
|
|
|
|
var b;
|
|
|
|
while (b !== 1) {
|
|
|
|
b = a / 2;
|
|
|
|
a = b;
|
|
|
|
}
|
|
|
|
return a;
|
|
|
|
}
|
|
|
|
testDivision.expected = 1;
|
|
|
|
test(testDivision);
|
|
|
|
|
|
|
|
function testDivisionFloat() {
|
|
|
|
var a = 32768.0;
|
|
|
|
var b;
|
|
|
|
while (b !== 1) {
|
|
|
|
b = a / 2.0;
|
|
|
|
a = b;
|
|
|
|
}
|
|
|
|
return a === 1.0;
|
|
|
|
}
|
|
|
|
testDivisionFloat.expected = true;
|
|
|
|
test(testDivisionFloat);
|
|
|
|
|
2008-08-29 17:35:00 -07:00
|
|
|
function testToUpperToLower() {
|
|
|
|
var s = "Hello", s1, s2;
|
|
|
|
for (i = 0; i < 100; ++i) {
|
|
|
|
s1 = s.toLowerCase();
|
|
|
|
s2 = s.toUpperCase();
|
|
|
|
}
|
|
|
|
return s1 + s2;
|
|
|
|
}
|
|
|
|
testToUpperToLower.expected = "helloHELLO";
|
|
|
|
test(testToUpperToLower);
|
|
|
|
|
|
|
|
function testReplace2() {
|
|
|
|
var s = "H e l l o", s1;
|
|
|
|
for (i = 0; i < 100; ++i) {
|
|
|
|
s1 = s.replace(" ", "");
|
|
|
|
}
|
|
|
|
return s1;
|
|
|
|
}
|
|
|
|
testReplace2.expected = "He l l o";
|
|
|
|
test(testReplace2);
|
|
|
|
|
2008-08-30 16:20:54 -07:00
|
|
|
function testBitwise() {
|
|
|
|
var x = 10000;
|
|
|
|
var y = 123456;
|
|
|
|
var z = 987234;
|
|
|
|
for (var i = 0; i < 50; i++) {
|
|
|
|
x = x ^ y;
|
|
|
|
y = y | z;
|
|
|
|
z = ~x;
|
|
|
|
}
|
|
|
|
return x + y + z;
|
|
|
|
}
|
|
|
|
testBitwise.expected = -1298;
|
|
|
|
test(testBitwise);
|
|
|
|
|
2008-08-30 16:35:38 -07:00
|
|
|
function testSwitch() {
|
|
|
|
var x = 0;
|
|
|
|
var ret = 0;
|
|
|
|
for (var i = 0; i < 100; ++i) {
|
|
|
|
switch (x) {
|
|
|
|
case 0:
|
|
|
|
ret += 1;
|
|
|
|
break;
|
|
|
|
case 1:
|
|
|
|
ret += 2;
|
|
|
|
break;
|
|
|
|
case 2:
|
|
|
|
ret += 3;
|
|
|
|
break;
|
|
|
|
case 3:
|
|
|
|
ret += 4;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
x = 0;
|
|
|
|
}
|
|
|
|
x++;
|
|
|
|
}
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
testSwitch.expected = 226;
|
|
|
|
test(testSwitch);
|
|
|
|
|
|
|
|
function testSwitchString() {
|
|
|
|
var x = "asdf";
|
|
|
|
var ret = 0;
|
|
|
|
for (var i = 0; i < 100; ++i) {
|
|
|
|
switch (x) {
|
|
|
|
case "asdf":
|
|
|
|
x = "asd";
|
|
|
|
ret += 1;
|
|
|
|
break;
|
|
|
|
case "asd":
|
|
|
|
x = "as";
|
|
|
|
ret += 2;
|
|
|
|
break;
|
|
|
|
case "as":
|
|
|
|
x = "a";
|
|
|
|
ret += 3;
|
|
|
|
break;
|
|
|
|
case "a":
|
|
|
|
x = "foo";
|
|
|
|
ret += 4;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
x = "asdf";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
testSwitchString.expected = 200;
|
|
|
|
test(testSwitchString);
|
|
|
|
|
2008-09-03 23:27:58 -07:00
|
|
|
function testNegZero1Helper(z) {
|
|
|
|
for (let j = 0; j < 5; ++j) { z = -z; }
|
|
|
|
return Math.atan2(0, -0) == Math.atan2(0, z);
|
|
|
|
}
|
|
|
|
|
|
|
|
var testNegZero1 = function() { return testNegZero1Helper(0); }
|
|
|
|
testNegZero1.expected = true;
|
|
|
|
testNegZero1.name = 'testNegZero1';
|
|
|
|
testNegZero1Helper(1);
|
|
|
|
test(testNegZero1);
|
|
|
|
|
2008-09-04 11:53:49 -07:00
|
|
|
// No test case, just make sure this doesn't assert.
|
2008-09-03 23:27:58 -07:00
|
|
|
function testNegZero2() {
|
|
|
|
var z = 0;
|
|
|
|
for (let j = 0; j < 5; ++j) { ({p: (-z)}); }
|
|
|
|
}
|
|
|
|
testNegZero2();
|
2008-08-30 16:35:38 -07:00
|
|
|
|
2008-09-04 14:44:59 -07:00
|
|
|
function testConstSwitch() {
|
|
|
|
var x;
|
|
|
|
for (var j=0;j<5;++j) { switch(1.1) { case NaN: case 2: } x = 2; }
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testConstSwitch.expected = 2;
|
|
|
|
test(testConstSwitch);
|
|
|
|
|
2008-09-22 17:58:25 -07:00
|
|
|
function testConstSwitch2() {
|
|
|
|
var x;
|
|
|
|
for (var j = 0; j < 4; ++j) { switch(0/0) { } }
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testConstSwitch2.expected = "ok";
|
|
|
|
test(testConstSwitch2);
|
|
|
|
|
2008-09-04 14:44:59 -07:00
|
|
|
function testConstIf() {
|
|
|
|
var x;
|
|
|
|
for (var j=0;j<5;++j) { if (1.1 || 5) { } x = 2;}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testConstIf.expected = 2;
|
|
|
|
test(testConstIf);
|
|
|
|
|
2008-09-04 22:14:27 -07:00
|
|
|
function testTypeofHole() {
|
|
|
|
var a = new Array(6);
|
|
|
|
a[5] = 3;
|
|
|
|
for (var i = 0; i < 6; ++i)
|
|
|
|
a[i] = typeof a[i];
|
2008-09-08 20:06:58 -07:00
|
|
|
return a.join(",");
|
2008-09-04 22:14:27 -07:00
|
|
|
}
|
|
|
|
testTypeofHole.expected = "undefined,undefined,undefined,undefined,undefined,number"
|
|
|
|
test(testTypeofHole);
|
|
|
|
|
2008-09-05 14:25:01 -07:00
|
|
|
function testNativeLog() {
|
|
|
|
var a = new Array(5);
|
|
|
|
for (var i = 0; i < 5; i++) {
|
|
|
|
a[i] = Math.log(Math.pow(Math.E, 10));
|
|
|
|
}
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
testNativeLog.expected = "10,10,10,10,10";
|
|
|
|
test(testNativeLog);
|
|
|
|
|
2008-09-05 18:29:08 -07:00
|
|
|
function test_JSOP_ARGSUB() {
|
|
|
|
function f0() { return arguments[0]; }
|
|
|
|
function f1() { return arguments[1]; }
|
|
|
|
function f2() { return arguments[2]; }
|
|
|
|
function f3() { return arguments[3]; }
|
|
|
|
function f4() { return arguments[4]; }
|
|
|
|
function f5() { return arguments[5]; }
|
|
|
|
function f6() { return arguments[6]; }
|
|
|
|
function f7() { return arguments[7]; }
|
|
|
|
function f8() { return arguments[8]; }
|
|
|
|
function f9() { return arguments[9]; }
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
a[0] = f0('a');
|
|
|
|
a[1] = f1('a','b');
|
|
|
|
a[2] = f2('a','b','c');
|
|
|
|
a[3] = f3('a','b','c','d');
|
|
|
|
a[4] = f4('a','b','c','d','e');
|
|
|
|
a[5] = f5('a','b','c','d','e','f');
|
|
|
|
a[6] = f6('a','b','c','d','e','f','g');
|
|
|
|
a[7] = f7('a','b','c','d','e','f','g','h');
|
|
|
|
a[8] = f8('a','b','c','d','e','f','g','h','i');
|
|
|
|
a[9] = f9('a','b','c','d','e','f','g','h','i','j');
|
|
|
|
}
|
|
|
|
return a.join("");
|
|
|
|
}
|
|
|
|
test_JSOP_ARGSUB.expected = "abcdefghij";
|
|
|
|
test(test_JSOP_ARGSUB);
|
|
|
|
|
|
|
|
function test_JSOP_ARGCNT() {
|
|
|
|
function f0() { return arguments.length; }
|
|
|
|
function f1() { return arguments.length; }
|
|
|
|
function f2() { return arguments.length; }
|
|
|
|
function f3() { return arguments.length; }
|
|
|
|
function f4() { return arguments.length; }
|
|
|
|
function f5() { return arguments.length; }
|
|
|
|
function f6() { return arguments.length; }
|
|
|
|
function f7() { return arguments.length; }
|
|
|
|
function f8() { return arguments.length; }
|
|
|
|
function f9() { return arguments.length; }
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
a[0] = f0('a');
|
|
|
|
a[1] = f1('a','b');
|
|
|
|
a[2] = f2('a','b','c');
|
|
|
|
a[3] = f3('a','b','c','d');
|
|
|
|
a[4] = f4('a','b','c','d','e');
|
|
|
|
a[5] = f5('a','b','c','d','e','f');
|
|
|
|
a[6] = f6('a','b','c','d','e','f','g');
|
|
|
|
a[7] = f7('a','b','c','d','e','f','g','h');
|
|
|
|
a[8] = f8('a','b','c','d','e','f','g','h','i');
|
|
|
|
a[9] = f9('a','b','c','d','e','f','g','h','i','j');
|
|
|
|
}
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
test_JSOP_ARGCNT.expected = "1,2,3,4,5,6,7,8,9,10";
|
|
|
|
test(test_JSOP_ARGCNT);
|
|
|
|
|
2008-09-08 20:06:58 -07:00
|
|
|
function testNativeMax() {
|
|
|
|
var out = [], k;
|
|
|
|
for (var i = 0; i < 5; ++i) {
|
|
|
|
k = Math.max(k, i);
|
|
|
|
}
|
|
|
|
out.push(k);
|
|
|
|
|
|
|
|
k = 0;
|
|
|
|
for (var i = 0; i < 5; ++i) {
|
|
|
|
k = Math.max(k, i);
|
|
|
|
}
|
|
|
|
out.push(k);
|
|
|
|
|
|
|
|
for (var i = 0; i < 5; ++i) {
|
|
|
|
k = Math.max(0, -0);
|
|
|
|
}
|
|
|
|
out.push((1 / k) < 0);
|
|
|
|
return out.join(",");
|
|
|
|
}
|
|
|
|
testNativeMax.expected = "NaN,4,false";
|
|
|
|
test(testNativeMax);
|
|
|
|
|
2008-09-15 15:00:40 -07:00
|
|
|
function testFloatArrayIndex() {
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 10; ++i) {
|
|
|
|
a[3] = 5;
|
|
|
|
a[3.5] = 7;
|
|
|
|
}
|
|
|
|
return a[3] + "," + a[3.5];
|
|
|
|
}
|
|
|
|
testFloatArrayIndex.expected = "5,7";
|
|
|
|
test(testFloatArrayIndex);
|
|
|
|
|
2008-09-15 15:30:06 -07:00
|
|
|
function testStrict() {
|
|
|
|
var n = 10, a = [];
|
|
|
|
for (var i = 0; i < 10; ++i) {
|
|
|
|
a[0] = (n === 10);
|
|
|
|
a[1] = (n !== 10);
|
|
|
|
a[2] = (n === null);
|
|
|
|
a[3] = (n == null);
|
|
|
|
}
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
testStrict.expected = "true,false,false,false";
|
|
|
|
test(testStrict);
|
|
|
|
|
2008-09-16 08:07:01 -07:00
|
|
|
function testSetPropNeitherMissNorHit() {
|
|
|
|
for (var j = 0; j < 5; ++j) { if (({}).__proto__ = 1) { } }
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testSetPropNeitherMissNorHit.expected = "ok";
|
|
|
|
test(testSetPropNeitherMissNorHit);
|
|
|
|
|
2008-09-16 18:49:27 -07:00
|
|
|
function testPrimitiveConstructorPrototype() {
|
|
|
|
var f = function(){};
|
|
|
|
f.prototype = false;
|
|
|
|
for (let j=0;j<5;++j) { new f; }
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testPrimitiveConstructorPrototype.expected = "ok";
|
|
|
|
test(testPrimitiveConstructorPrototype);
|
|
|
|
|
2008-09-18 14:13:37 -07:00
|
|
|
function testSideExitInConstructor() {
|
|
|
|
var FCKConfig = {};
|
|
|
|
FCKConfig.CoreStyles =
|
|
|
|
{
|
|
|
|
'Bold': { },
|
|
|
|
'Italic': { },
|
|
|
|
'FontFace': { },
|
|
|
|
'Size' :
|
|
|
|
{
|
|
|
|
Overrides: [ ]
|
|
|
|
},
|
|
|
|
|
|
|
|
'Color' :
|
|
|
|
{
|
|
|
|
Element: '',
|
|
|
|
Styles: { },
|
|
|
|
Overrides: [ ]
|
|
|
|
},
|
|
|
|
'BackColor': {
|
|
|
|
Element : '',
|
|
|
|
Styles : { 'background-color' : '' }
|
|
|
|
},
|
|
|
|
|
|
|
|
};
|
|
|
|
var FCKStyle = function(A) {
|
|
|
|
A.Element;
|
|
|
|
};
|
|
|
|
|
|
|
|
var pass = true;
|
|
|
|
for (var s in FCKConfig.CoreStyles) {
|
|
|
|
var x = new FCKStyle(FCKConfig.CoreStyles[s]);
|
|
|
|
if (!x) pass = false;
|
|
|
|
}
|
|
|
|
return pass;
|
|
|
|
}
|
|
|
|
testSideExitInConstructor.expected = true;
|
|
|
|
test(testSideExitInConstructor);
|
|
|
|
|
2008-09-18 16:04:54 -07:00
|
|
|
function testNot() {
|
|
|
|
var a = new Object(), b = null, c = "foo", d = "", e = 5, f = 0, g = 5.5, h = -0, i = true, j = false, k = undefined;
|
|
|
|
var r;
|
|
|
|
for (var i = 0; i < 10; ++i) {
|
|
|
|
r = [!a, !b, !c, !d, !e, !f, !g, !h, !i, !j, !k];
|
|
|
|
}
|
|
|
|
return r.join(",");
|
|
|
|
}
|
|
|
|
testNot.expected = "false,true,false,true,false,true,false,true,false,true,true";
|
|
|
|
test(testNot);
|
|
|
|
|
2008-09-18 15:23:22 -07:00
|
|
|
function doTestDifferingArgc(a, b)
|
|
|
|
{
|
|
|
|
var k = 0;
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
{
|
|
|
|
k += i;
|
|
|
|
}
|
|
|
|
return k;
|
|
|
|
}
|
|
|
|
function testDifferingArgc()
|
|
|
|
{
|
|
|
|
var x = 0;
|
|
|
|
x += doTestDifferingArgc(1, 2);
|
|
|
|
x += doTestDifferingArgc(1);
|
|
|
|
x += doTestDifferingArgc(1, 2, 3);
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testDifferingArgc.expected = 45*3;
|
|
|
|
test(testDifferingArgc);
|
|
|
|
|
|
|
|
function doTestMoreArgcThanNargs()
|
|
|
|
{
|
|
|
|
var x = 0;
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
{
|
|
|
|
x = x + arguments[3];
|
|
|
|
}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
function testMoreArgcThanNargs()
|
|
|
|
{
|
|
|
|
return doTestMoreArgcThanNargs(1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
|
|
|
|
}
|
|
|
|
testMoreArgcThanNargs.expected = 4*10;
|
|
|
|
test(testMoreArgcThanNargs);
|
|
|
|
|
2008-09-19 18:58:00 -07:00
|
|
|
// Test stack reconstruction after a nested exit
|
2008-09-21 06:02:09 -07:00
|
|
|
function testNestedExitStackInner(j, counter) {
|
2008-09-19 18:58:00 -07:00
|
|
|
++counter;
|
|
|
|
var b = 0;
|
|
|
|
for (var i = 1; i <= RUNLOOP; i++) {
|
|
|
|
++b;
|
|
|
|
var a;
|
|
|
|
// Make sure that once everything has been traced we suddenly switch to
|
|
|
|
// a different control flow the first time we run the outermost tree,
|
|
|
|
// triggering a side exit.
|
|
|
|
if (j < RUNLOOP)
|
|
|
|
a = 1;
|
|
|
|
else
|
|
|
|
a = 0;
|
|
|
|
++b;
|
|
|
|
b += a;
|
|
|
|
}
|
|
|
|
return counter + b;
|
|
|
|
}
|
2008-09-21 06:02:09 -07:00
|
|
|
function testNestedExitStackOuter() {
|
2008-09-19 18:58:00 -07:00
|
|
|
var counter = 0;
|
|
|
|
for (var j = 1; j <= RUNLOOP; ++j) {
|
|
|
|
for (var k = 1; k <= RUNLOOP; ++k) {
|
|
|
|
counter = testNestedExitStackInner(j, counter);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return counter;
|
|
|
|
}
|
|
|
|
testNestedExitStackOuter.expected = 81;
|
2008-09-22 14:37:59 -07:00
|
|
|
testNestedExitStackOuter.jitstats = {
|
2008-10-27 20:42:49 -07:00
|
|
|
recorderStarted: 5,
|
|
|
|
recorderAborted: 2,
|
|
|
|
traceTriggered: 9
|
2008-09-22 14:37:59 -07:00
|
|
|
};
|
2008-09-19 18:58:00 -07:00
|
|
|
test(testNestedExitStackOuter);
|
|
|
|
|
2008-09-21 06:02:09 -07:00
|
|
|
function testHOTLOOPSize() {
|
2008-09-19 19:47:58 -07:00
|
|
|
return HOTLOOP > 1;
|
|
|
|
}
|
|
|
|
testHOTLOOPSize.expected = true;
|
|
|
|
test(testHOTLOOPSize);
|
|
|
|
|
2008-09-23 17:18:40 -07:00
|
|
|
function testMatchStringObject() {
|
|
|
|
var a = new String("foo");
|
|
|
|
var b;
|
|
|
|
for (i = 0; i < 300; i++) {
|
|
|
|
b = a.match(/bar/);
|
|
|
|
}
|
|
|
|
return b;
|
|
|
|
}
|
|
|
|
testMatchStringObject.expected = null;
|
|
|
|
test(testMatchStringObject);
|
|
|
|
|
2008-09-24 13:12:25 -07:00
|
|
|
function innerSwitch(k)
|
|
|
|
{
|
|
|
|
var m = 0;
|
|
|
|
|
|
|
|
switch (k)
|
|
|
|
{
|
|
|
|
case 0:
|
|
|
|
m = 1;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
return m;
|
|
|
|
}
|
|
|
|
function testInnerSwitchBreak()
|
|
|
|
{
|
|
|
|
var r = new Array(5);
|
|
|
|
for (var i = 0; i < 5; i++)
|
|
|
|
{
|
|
|
|
r[i] = innerSwitch(0);
|
|
|
|
}
|
|
|
|
|
|
|
|
return r.join(",");
|
|
|
|
}
|
|
|
|
testInnerSwitchBreak.expected = "1,1,1,1,1";
|
|
|
|
test(testInnerSwitchBreak);
|
|
|
|
|
2008-09-25 11:31:40 -07:00
|
|
|
function testArrayNaNIndex()
|
|
|
|
{
|
|
|
|
for (var j = 0; j < 4; ++j) { [this[NaN]]; }
|
|
|
|
for (var j = 0; j < 5; ++j) { if([1][-0]) { } }
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testArrayNaNIndex.expected = "ok";
|
|
|
|
test(testArrayNaNIndex);
|
|
|
|
|
2008-09-25 14:16:24 -07:00
|
|
|
function innerTestInnerMissingArgs(a,b,c,d)
|
|
|
|
{
|
|
|
|
if (a) {
|
|
|
|
} else {
|
|
|
|
}
|
|
|
|
}
|
|
|
|
function doTestInnerMissingArgs(k)
|
|
|
|
{
|
|
|
|
for (i = 0; i < 10; i++) {
|
|
|
|
innerTestInnerMissingArgs(k);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
function testInnerMissingArgs()
|
|
|
|
{
|
|
|
|
doTestInnerMissingArgs(1);
|
|
|
|
doTestInnerMissingArgs(0);
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
testInnerMissingArgs.expected = 1; //Expected: that we don't crash.
|
|
|
|
test(testInnerMissingArgs);
|
|
|
|
|
2008-09-25 17:45:14 -07:00
|
|
|
function regexpLastIndex()
|
|
|
|
{
|
|
|
|
var n = 0;
|
|
|
|
var re = /hi/g;
|
|
|
|
var ss = " hi hi hi hi hi hi hi hi hi hi";
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
// re.exec(ss);
|
|
|
|
n += (re.lastIndex > 0) ? 3 : 0;
|
|
|
|
re.lastIndex = 0;
|
|
|
|
}
|
|
|
|
return n;
|
|
|
|
}
|
|
|
|
regexpLastIndex.expected = 0; // 30;
|
|
|
|
test(regexpLastIndex);
|
|
|
|
|
2008-09-26 11:37:49 -07:00
|
|
|
function testHOTLOOPCorrectness() {
|
|
|
|
var b = 0;
|
|
|
|
for (var i = 0; i < HOTLOOP; ++i) {
|
|
|
|
++b;
|
|
|
|
}
|
|
|
|
return b;
|
|
|
|
}
|
|
|
|
testHOTLOOPCorrectness.expected = HOTLOOP;
|
|
|
|
testHOTLOOPCorrectness.jitstats = {
|
|
|
|
recorderStarted: 1,
|
|
|
|
recorderAborted: 0,
|
|
|
|
traceTriggered: 0
|
|
|
|
};
|
|
|
|
// Change the global shape right before doing the test
|
|
|
|
this.testHOTLOOPCorrectnessVar = 1;
|
|
|
|
test(testHOTLOOPCorrectness);
|
|
|
|
|
|
|
|
function testRUNLOOPCorrectness() {
|
|
|
|
var b = 0;
|
|
|
|
for (var i = 0; i < RUNLOOP; ++i) {
|
|
|
|
++b;
|
|
|
|
}
|
|
|
|
return b;
|
|
|
|
}
|
|
|
|
testRUNLOOPCorrectness.expected = RUNLOOP;
|
|
|
|
testRUNLOOPCorrectness.jitstats = {
|
|
|
|
recorderStarted: 1,
|
|
|
|
recorderAborted: 0,
|
|
|
|
traceTriggered: 1
|
|
|
|
};
|
|
|
|
// Change the global shape right before doing the test
|
|
|
|
this.testRUNLOOPCorrectnessVar = 1;
|
|
|
|
test(testRUNLOOPCorrectness);
|
|
|
|
|
2008-09-26 17:33:40 -07:00
|
|
|
function testDateNow() {
|
2008-09-26 11:37:50 -07:00
|
|
|
// Accessing global.Date for the first time will change the global shape,
|
|
|
|
// so do it before the loop starts; otherwise we have to loop an extra time
|
|
|
|
// to pick things up.
|
|
|
|
var time = Date.now();
|
|
|
|
for (var j = 0; j < RUNLOOP; ++j) {
|
|
|
|
time = Date.now();
|
|
|
|
}
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testDateNow.expected = "ok";
|
|
|
|
testDateNow.jitstats = {
|
|
|
|
recorderStarted: 1,
|
|
|
|
recorderAborted: 0,
|
|
|
|
traceTriggered: 1
|
|
|
|
};
|
|
|
|
test(testDateNow);
|
|
|
|
|
2008-09-26 17:33:40 -07:00
|
|
|
function testINITELEM()
|
|
|
|
{
|
|
|
|
var x;
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
x = { 0: 5, 1: 5 };
|
|
|
|
return x[0] + x[1];
|
|
|
|
}
|
|
|
|
testINITELEM.expected = 10;
|
|
|
|
test(testINITELEM);
|
|
|
|
|
2008-09-26 19:20:52 -07:00
|
|
|
function testUndefinedBooleanCmp()
|
|
|
|
{
|
|
|
|
var t = true, f = false, x = [];
|
|
|
|
for (var i = 0; i < 10; ++i) {
|
|
|
|
x[0] = t == undefined;
|
|
|
|
x[1] = t != undefined;
|
|
|
|
x[2] = t === undefined;
|
|
|
|
x[3] = t !== undefined;
|
|
|
|
x[4] = t < undefined;
|
|
|
|
x[5] = t > undefined;
|
|
|
|
x[6] = t <= undefined;
|
|
|
|
x[7] = t >= undefined;
|
|
|
|
x[8] = f == undefined;
|
|
|
|
x[9] = f != undefined;
|
|
|
|
x[10] = f === undefined;
|
|
|
|
x[11] = f !== undefined;
|
|
|
|
x[12] = f < undefined;
|
|
|
|
x[13] = f > undefined;
|
|
|
|
x[14] = f <= undefined;
|
|
|
|
x[15] = f >= undefined;
|
|
|
|
}
|
|
|
|
return x.join(",");
|
|
|
|
}
|
|
|
|
testUndefinedBooleanCmp.expected = "false,true,false,true,false,false,false,false,false,true,false,true,false,false,false,false";
|
|
|
|
test(testUndefinedBooleanCmp);
|
|
|
|
|
2008-09-27 13:13:42 -07:00
|
|
|
function testConstantBooleanExpr()
|
|
|
|
{
|
|
|
|
for (var j = 0; j < 3; ++j) { if(true <= true) { } }
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testConstantBooleanExpr.expected = "ok";
|
|
|
|
test(testConstantBooleanExpr);
|
|
|
|
|
2008-09-28 17:11:47 -07:00
|
|
|
function testNegativeGETELEMIndex()
|
|
|
|
{
|
|
|
|
for (let i=0;i<3;++i) /x/[-4];
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testNegativeGETELEMIndex.expected = "ok";
|
|
|
|
test(testNegativeGETELEMIndex);
|
|
|
|
|
2008-09-29 21:20:34 -07:00
|
|
|
function doTestInvalidCharCodeAt(input)
|
|
|
|
{
|
|
|
|
var q = "";
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
q += input.charCodeAt(i);
|
|
|
|
return q;
|
|
|
|
}
|
|
|
|
function testInvalidCharCodeAt()
|
|
|
|
{
|
|
|
|
return doTestInvalidCharCodeAt("");
|
|
|
|
}
|
|
|
|
testInvalidCharCodeAt.expected = "NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN";
|
|
|
|
test(testInvalidCharCodeAt);
|
|
|
|
|
2008-10-01 16:04:39 -07:00
|
|
|
function FPQuadCmp()
|
|
|
|
{
|
|
|
|
for (let j = 0; j < 3; ++j) { true == 0; }
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
FPQuadCmp.expected = "ok";
|
|
|
|
test(FPQuadCmp);
|
|
|
|
|
2008-10-02 15:39:25 -07:00
|
|
|
function testDestructuring() {
|
|
|
|
var t = 0;
|
|
|
|
for (var i = 0; i < HOTLOOP + 1; ++i) {
|
|
|
|
var [r, g, b] = [1, 1, 1];
|
|
|
|
t += r + g + b;
|
|
|
|
}
|
|
|
|
return t
|
|
|
|
}
|
|
|
|
testDestructuring.expected = (HOTLOOP + 1) * 3;
|
|
|
|
test(testDestructuring);
|
|
|
|
|
2008-10-30 11:42:12 -07:00
|
|
|
function loopWithUndefined1(t, val) {
|
|
|
|
var a = new Array(6);
|
|
|
|
for (var i = 0; i < 6; i++)
|
|
|
|
a[i] = (t > val);
|
|
|
|
return a;
|
|
|
|
}
|
|
|
|
loopWithUndefined1(5.0, 2); //compile version with val=int
|
|
|
|
|
|
|
|
function testLoopWithUndefined1() {
|
|
|
|
return loopWithUndefined1(5.0).join(","); //val=undefined
|
|
|
|
};
|
|
|
|
testLoopWithUndefined1.expected = "false,false,false,false,false,false";
|
|
|
|
test(testLoopWithUndefined1);
|
|
|
|
|
2008-10-30 11:52:48 -07:00
|
|
|
function loopWithUndefined2(t, dostuff, val) {
|
|
|
|
var a = new Array(6);
|
|
|
|
for (var i = 0; i < 6; i++) {
|
|
|
|
if (dostuff) {
|
|
|
|
val = 1;
|
|
|
|
a[i] = (t > val);
|
|
|
|
} else {
|
|
|
|
a[i] = (val == undefined);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return a;
|
|
|
|
}
|
|
|
|
function testLoopWithUndefined2() {
|
|
|
|
var a = loopWithUndefined2(5.0, true, 2);
|
|
|
|
var b = loopWithUndefined2(5.0, true);
|
|
|
|
var c = loopWithUndefined2(5.0, false, 8);
|
|
|
|
var d = loopWithUndefined2(5.0, false);
|
|
|
|
return [a[0], b[0], c[0], d[0]].join(",");
|
|
|
|
}
|
|
|
|
testLoopWithUndefined2.expected = "true,true,false,true";
|
|
|
|
test(testLoopWithUndefined2);
|
|
|
|
|
2008-10-30 15:54:22 -07:00
|
|
|
//test no multitrees assert
|
2008-10-30 13:48:22 -07:00
|
|
|
function testBug462388() {
|
|
|
|
var c = 0, v; for each (let x in ["",v,v,v]) { for (c=0;c<4;++c) { } }
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
testBug462388.expected = true;
|
|
|
|
test(testBug462388);
|
|
|
|
|
2008-10-30 15:54:22 -07:00
|
|
|
//test no multitrees assert
|
|
|
|
function testBug462407() {
|
|
|
|
for each (let i in [0, {}, 0, 1.5, {}, 0, 1.5, 0, 0]) { }
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
testBug462407.expected = true;
|
|
|
|
test(testBug462407);
|
|
|
|
|
2008-11-07 13:22:05 -08:00
|
|
|
//test no multitrees assert
|
|
|
|
function testBug463490() {
|
|
|
|
function f(a, b, d) {
|
|
|
|
for (var i = 0; i < 10; i++) {
|
|
|
|
if (d)
|
|
|
|
b /= 2;
|
|
|
|
}
|
|
|
|
return a + b;
|
|
|
|
}
|
|
|
|
//integer stable loop
|
|
|
|
f(2, 2, false);
|
|
|
|
//double stable loop
|
|
|
|
f(3, 4.5, false);
|
|
|
|
//integer unstable branch
|
|
|
|
f(2, 2, true);
|
|
|
|
return true;
|
|
|
|
};
|
|
|
|
testBug463490.expected = true;
|
|
|
|
test(testBug463490);
|
|
|
|
|
2008-11-12 19:00:15 -08:00
|
|
|
// Test no assert (bug 464089)
|
|
|
|
function shortRecursiveLoop(b, c) {
|
|
|
|
for (var i = 0; i < c; i++) {
|
|
|
|
if (b)
|
|
|
|
shortRecursiveLoop(c - 1);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
function testClosingRecursion() {
|
|
|
|
shortRecursiveLoop(false, 1);
|
|
|
|
shortRecursiveLoop(true, 3);
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
testClosingRecursion.expected = true;
|
|
|
|
test(testClosingRecursion);
|
|
|
|
|
2008-10-02 16:30:46 -07:00
|
|
|
// BEGIN MANDELBROT STUFF
|
|
|
|
// XXXbz I would dearly like to wrap it up into a function to avoid polluting
|
|
|
|
// the global scope, but the function ends up heavyweight, and then we lose on
|
|
|
|
// the jit.
|
|
|
|
load("mandelbrot-results.js");
|
|
|
|
//function testMandelbrotAll() {
|
|
|
|
// Configuration options that affect which codepaths we follow.
|
|
|
|
var doImageData = true;
|
|
|
|
var avoidSparseArray = true;
|
|
|
|
|
|
|
|
// Control of iteration numbers and sizing. We'll do
|
|
|
|
// scaler * colorNames.length iterations or so before deciding that we
|
|
|
|
// don't escape.
|
|
|
|
const scaler = 5;
|
|
|
|
const numRows = 600;
|
|
|
|
const numCols = 600;
|
|
|
|
|
|
|
|
// For now, avoid hitting memory pressure
|
|
|
|
gcparam("maxBytes", 1300000000);
|
|
|
|
gcparam("maxMallocBytes", 1300000000);
|
|
|
|
|
|
|
|
const colorNames = [
|
|
|
|
"black",
|
|
|
|
"green",
|
|
|
|
"blue",
|
|
|
|
"red",
|
|
|
|
"purple",
|
|
|
|
"orange",
|
|
|
|
"cyan",
|
|
|
|
"yellow",
|
|
|
|
"magenta",
|
|
|
|
"brown",
|
|
|
|
"pink",
|
|
|
|
"chartreuse",
|
|
|
|
"darkorange",
|
|
|
|
"crimson",
|
|
|
|
"gray",
|
|
|
|
"deeppink",
|
|
|
|
"firebrick",
|
|
|
|
"lavender",
|
|
|
|
"lawngreen",
|
|
|
|
"lightsalmon",
|
|
|
|
"lime",
|
|
|
|
"goldenrod"
|
|
|
|
];
|
|
|
|
const threshold = (colorNames.length - 1) * scaler;
|
|
|
|
|
|
|
|
// Now set up our colors
|
|
|
|
var colors = [];
|
2008-10-07 11:00:16 -07:00
|
|
|
// 3-part for loop (iterators buggy, we will add a separate test for them)
|
|
|
|
for (var colorNameIdx = 0; colorNameIdx < colorNames.length; ++colorNameIdx) {
|
|
|
|
//for (var colorNameIdx in colorNames) {
|
2008-10-02 16:30:46 -07:00
|
|
|
colorNameIdx = parseInt(colorNameIdx);
|
|
|
|
colors.push([colorNameIdx, colorNameIdx, colorNameIdx, 0]);
|
|
|
|
}
|
|
|
|
|
|
|
|
// Storage for our point data
|
|
|
|
var points;
|
|
|
|
|
|
|
|
var scratch = {};
|
|
|
|
var scratchZ = {};
|
|
|
|
function complexMult(a, b) {
|
|
|
|
var newr = a.r * b.r - a.i * b.i;
|
|
|
|
var newi = a.r * b.i + a.i * b.r;
|
|
|
|
scratch.r = newr;
|
|
|
|
scratch.i = newi;
|
|
|
|
return scratch;
|
|
|
|
}
|
|
|
|
function complexAdd(a, b) {
|
|
|
|
scratch.r = a.r + b.r;
|
|
|
|
scratch.i = a.i + b.i;
|
|
|
|
return scratch;
|
|
|
|
}
|
|
|
|
function abs(a) {
|
|
|
|
return Math.sqrt(a.r * a.r + a.i * a.i);
|
|
|
|
}
|
|
|
|
|
|
|
|
function escapeAbsDiff(normZ, absC) {
|
|
|
|
var absZ = Math.sqrt(normZ);
|
|
|
|
return normZ > absZ + absC;
|
|
|
|
}
|
|
|
|
|
|
|
|
function escapeNorm2(normZ) {
|
|
|
|
return normZ > 4;
|
|
|
|
}
|
|
|
|
|
|
|
|
function fuzzyColors(i) {
|
|
|
|
return Math.floor(i / scaler) + 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
function moddedColors(i) {
|
|
|
|
return (i % (colorNames.length - 1)) + 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
function computeEscapeSpeedObjects(real, imag) {
|
|
|
|
var c = { r: real, i: imag }
|
|
|
|
scratchZ.r = scratchZ.i = 0;
|
|
|
|
var absC = abs(c);
|
|
|
|
for (var i = 0; i < threshold; ++i) {
|
|
|
|
scratchZ = complexAdd(c, complexMult(scratchZ, scratchZ));
|
|
|
|
if (escape(scratchZ.r * scratchZ.r + scratchZ.i * scratchZ.i,
|
|
|
|
absC)) {
|
|
|
|
return colorMap(i);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
function computeEscapeSpeedOneObject(real, imag) {
|
|
|
|
// fold in the fact that we start with 0
|
|
|
|
var r = real;
|
|
|
|
var i = imag;
|
|
|
|
var absC = abs({r: real, i: imag});
|
|
|
|
for (var j = 0; j < threshold; ++j) {
|
|
|
|
var r2 = r * r;
|
|
|
|
var i2 = i * i;
|
|
|
|
if (escape(r2 + i2, absC)) {
|
|
|
|
return colorMap(j);
|
|
|
|
}
|
|
|
|
i = 2 * r * i + imag;
|
|
|
|
r = r2 - i2 + real;
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
function computeEscapeSpeedDoubles(real, imag) {
|
|
|
|
// fold in the fact that we start with 0
|
|
|
|
var r = real;
|
|
|
|
var i = imag;
|
|
|
|
var absC = Math.sqrt(real * real + imag * imag);
|
|
|
|
for (var j = 0; j < threshold; ++j) {
|
|
|
|
var r2 = r * r;
|
|
|
|
var i2 = i * i;
|
|
|
|
if (escape(r2 + i2, absC)) {
|
|
|
|
return colorMap(j);
|
|
|
|
}
|
|
|
|
i = 2 * r * i + imag;
|
|
|
|
r = r2 - i2 + real;
|
|
|
|
}
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
var computeEscapeSpeed = computeEscapeSpeedDoubles;
|
|
|
|
var escape = escapeNorm2;
|
|
|
|
var colorMap = fuzzyColors;
|
|
|
|
|
|
|
|
function addPointOrig(pointArray, n, i, j) {
|
|
|
|
if (!points[n]) {
|
|
|
|
points[n] = [];
|
|
|
|
points[n].push([i, j, 1, 1]);
|
|
|
|
} else {
|
|
|
|
var point = points[n][points[n].length-1];
|
|
|
|
if (point[0] == i && point[1] == j - point[3]) {
|
|
|
|
++point[3];
|
|
|
|
} else {
|
|
|
|
points[n].push([i, j, 1, 1]);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
function addPointImagedata(pointArray, n, col, row) {
|
|
|
|
var slotIdx = ((row * numCols) + col) * 4;
|
|
|
|
pointArray[slotIdx] = colors[n][0];
|
|
|
|
pointArray[slotIdx+1] = colors[n][1];
|
|
|
|
pointArray[slotIdx+2] = colors[n][2];
|
|
|
|
pointArray[slotIdx+3] = colors[n][3];
|
|
|
|
}
|
|
|
|
|
|
|
|
function createMandelSet() {
|
|
|
|
var realRange = { min: -2.1, max: 1 };
|
|
|
|
var imagRange = { min: -1.5, max: 1.5 };
|
|
|
|
|
|
|
|
var addPoint;
|
|
|
|
if (doImageData) {
|
|
|
|
addPoint = addPointImagedata;
|
|
|
|
points = new Array(4*numCols*numRows);
|
|
|
|
if (avoidSparseArray) {
|
|
|
|
for (var idx = 0; idx < 4*numCols*numRows; ++idx) {
|
|
|
|
points[idx] = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
addPoint = addPointOrig;
|
|
|
|
points = [];
|
|
|
|
}
|
|
|
|
var realStep = (realRange.max - realRange.min)/numCols;
|
|
|
|
var imagStep = (imagRange.min - imagRange.max)/numRows;
|
|
|
|
for (var i = 0, curReal = realRange.min;
|
|
|
|
i < numCols;
|
|
|
|
++i, curReal += realStep) {
|
|
|
|
for (var j = 0, curImag = imagRange.max;
|
|
|
|
j < numRows;
|
|
|
|
++j, curImag += imagStep) {
|
|
|
|
var n = computeEscapeSpeed(curReal, curImag);
|
|
|
|
addPoint(points, n, i, j)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
var result;
|
|
|
|
if (doImageData) {
|
|
|
|
if (colorMap == fuzzyColors) {
|
|
|
|
result = mandelbrotImageDataFuzzyResult;
|
|
|
|
} else {
|
|
|
|
result = mandelbrotImageDataModdedResult;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
result = mandelbrotNoImageDataResult;
|
|
|
|
}
|
|
|
|
return points.toSource() == result;
|
|
|
|
}
|
|
|
|
|
|
|
|
createMandelSet.expected = true;
|
|
|
|
|
|
|
|
const escapeTests = [ escapeAbsDiff ];
|
|
|
|
const colorMaps = [ fuzzyColors, moddedColors ];
|
|
|
|
const escapeComputations = [ computeEscapeSpeedObjects,
|
|
|
|
computeEscapeSpeedOneObject,
|
|
|
|
computeEscapeSpeedDoubles ];
|
2008-10-08 15:19:15 -07:00
|
|
|
// Test all possible escape-speed generation codepaths, using the
|
2008-10-02 16:30:46 -07:00
|
|
|
// imageData + sparse array avoidance storage.
|
|
|
|
doImageData = true;
|
|
|
|
avoidSparseArray = true;
|
|
|
|
for (var escapeIdx in escapeTests) {
|
|
|
|
escape = escapeTests[escapeIdx];
|
|
|
|
for (var colorMapIdx in colorMaps) {
|
|
|
|
colorMap = colorMaps[colorMapIdx];
|
|
|
|
for (var escapeComputationIdx in escapeComputations) {
|
|
|
|
computeEscapeSpeed = escapeComputations[escapeComputationIdx];
|
|
|
|
test(createMandelSet);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Test all possible storage strategies. Note that we already tested
|
|
|
|
// doImageData == true with avoidSparseArray == true.
|
|
|
|
escape = escapeAbsDiff;
|
|
|
|
colorMap = fuzzyColors; // This part doesn't really matter too much here
|
|
|
|
computeEscapeSpeed = computeEscapeSpeedDoubles;
|
|
|
|
|
|
|
|
doImageData = true;
|
|
|
|
avoidSparseArray = false;
|
|
|
|
test(createMandelSet);
|
|
|
|
|
|
|
|
escape = escapeNorm2;
|
|
|
|
doImageData = false; // avoidSparseArray doesn't matter here
|
|
|
|
test(createMandelSet);
|
|
|
|
//}
|
|
|
|
//testMandelbrotAll();
|
|
|
|
// END MANDELBROT STUFF
|
|
|
|
|
2008-10-06 17:28:22 -07:00
|
|
|
function testNewDate()
|
|
|
|
{
|
|
|
|
// Accessing global.Date for the first time will change the global shape,
|
|
|
|
// so do it before the loop starts; otherwise we have to loop an extra time
|
|
|
|
// to pick things up.
|
|
|
|
var start = new Date();
|
|
|
|
var time = new Date();
|
|
|
|
for (var j = 0; j < RUNLOOP; ++j) {
|
|
|
|
time = new Date();
|
|
|
|
}
|
|
|
|
return time > 0 && time >= start;
|
|
|
|
}
|
|
|
|
testNewDate.expected = true;
|
|
|
|
testNewDate.jitstats = {
|
|
|
|
recorderStarted: 1,
|
|
|
|
recorderAborted: 0,
|
|
|
|
traceTriggered: 1
|
|
|
|
};
|
|
|
|
test(testNewDate);
|
|
|
|
|
2008-10-07 11:00:16 -07:00
|
|
|
function testArrayPushPop() {
|
|
|
|
var a = [], sum1 = 0, sum2 = 0;
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
sum1 += a.push(i);
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
sum2 += a.pop();
|
|
|
|
a.push(sum1);
|
|
|
|
a.push(sum2);
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
testArrayPushPop.expected = "55,45";
|
|
|
|
test(testArrayPushPop);
|
|
|
|
|
|
|
|
function testResumeOp() {
|
|
|
|
var a = [1,"2",3,"4",5,"6",7,"8",9,"10",11,"12",13,"14",15,"16"];
|
|
|
|
var x = "";
|
|
|
|
while (a.length > 0)
|
|
|
|
x += a.pop();
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testResumeOp.expected = "16151413121110987654321";
|
|
|
|
test(testResumeOp);
|
|
|
|
|
2008-10-07 13:32:30 -07:00
|
|
|
function testUndefinedCmp() {
|
|
|
|
var a = false;
|
|
|
|
for (var j = 0; j < 4; ++j) { if (undefined < false) { a = true; } }
|
|
|
|
return a;
|
|
|
|
}
|
|
|
|
testUndefinedCmp.expected = false;
|
|
|
|
test(testUndefinedCmp);
|
|
|
|
|
2008-10-12 15:39:32 -07:00
|
|
|
function reallyDeepNestedExit(schedule)
|
|
|
|
{
|
|
|
|
var c = 0, j = 0;
|
|
|
|
for (var i = 0; i < 5; i++) {
|
|
|
|
for (j = 0; j < 4; j++) {
|
|
|
|
c += (schedule[i*4 + j] == 1) ? 1 : 2;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return c;
|
|
|
|
}
|
|
|
|
function testReallyDeepNestedExit()
|
|
|
|
{
|
|
|
|
var c = 0;
|
|
|
|
var schedule1 = new Array(5*4);
|
|
|
|
var schedule2 = new Array(5*4);
|
|
|
|
for (var i = 0; i < 5*4; i++) {
|
|
|
|
schedule1[i] = 0;
|
|
|
|
schedule2[i] = 0;
|
|
|
|
}
|
|
|
|
/**
|
|
|
|
* First innermost compile: true branch runs through.
|
|
|
|
* Second '': false branch compiles new loop edge.
|
|
|
|
* First outer compile: expect true branch.
|
|
|
|
* Second '': hit false branch.
|
|
|
|
*/
|
|
|
|
schedule1[0*4 + 3] = 1;
|
|
|
|
var schedules = [schedule1,
|
|
|
|
schedule2,
|
|
|
|
schedule1,
|
|
|
|
schedule2,
|
|
|
|
schedule2];
|
|
|
|
|
|
|
|
for (var i = 0; i < 5; i++) {
|
|
|
|
c += reallyDeepNestedExit(schedules[i]);
|
|
|
|
}
|
|
|
|
return c;
|
|
|
|
}
|
|
|
|
testReallyDeepNestedExit.expected = 198;
|
|
|
|
test(testReallyDeepNestedExit);
|
|
|
|
|
2008-10-13 19:07:30 -07:00
|
|
|
function testRegExpTest() {
|
|
|
|
var r = /abc/;
|
|
|
|
var flag = false;
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
flag = r.test("abc");
|
|
|
|
return flag;
|
|
|
|
}
|
|
|
|
testRegExpTest.expected = true;
|
|
|
|
test(testRegExpTest);
|
|
|
|
|
|
|
|
function testNumToString() {
|
|
|
|
var r = [];
|
|
|
|
var d = 123456789;
|
|
|
|
for (var i = 0; i < 10; ++i) {
|
|
|
|
r = [
|
|
|
|
d.toString(),
|
|
|
|
(-d).toString(),
|
|
|
|
d.toString(10),
|
|
|
|
(-d).toString(10),
|
|
|
|
d.toString(16),
|
|
|
|
(-d).toString(16),
|
|
|
|
d.toString(36),
|
|
|
|
(-d).toString(36)
|
|
|
|
];
|
|
|
|
}
|
|
|
|
return r.join(",");
|
|
|
|
}
|
|
|
|
testNumToString.expected = "123456789,-123456789,123456789,-123456789,75bcd15,-75bcd15,21i3v9,-21i3v9";
|
|
|
|
test(testNumToString);
|
|
|
|
|
2008-10-21 15:21:23 -07:00
|
|
|
function testSubstring() {
|
|
|
|
for (var i = 0; i < 5; ++i) {
|
|
|
|
actual = "".substring(5);
|
|
|
|
}
|
|
|
|
return actual;
|
|
|
|
}
|
|
|
|
testSubstring.expected = "";
|
|
|
|
test(testSubstring);
|
|
|
|
|
2008-10-22 19:06:18 -07:00
|
|
|
function testForInLoopChangeIteratorType() {
|
|
|
|
for(y in [0,1,2]) y = NaN;
|
2008-10-28 00:11:26 -07:00
|
|
|
(function(){
|
|
|
|
[].__proto__.u = void 0;
|
|
|
|
for (let y in [5,6,7,8])
|
|
|
|
y = NaN;
|
|
|
|
delete [].__proto__.u;
|
|
|
|
})()
|
2008-10-22 19:06:18 -07:00
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
testForInLoopChangeIteratorType.expected = "ok";
|
|
|
|
test(testForInLoopChangeIteratorType);
|
|
|
|
|
2008-10-24 21:51:04 -07:00
|
|
|
function testGrowDenseArray() {
|
|
|
|
var a = new Array();
|
|
|
|
for (var i = 0; i < 10; ++i)
|
|
|
|
a[i] |= 5;
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
testGrowDenseArray.expected = "5,5,5,5,5,5,5,5,5,5";
|
|
|
|
test(testGrowDenseArray);
|
|
|
|
|
2008-10-27 16:15:32 -07:00
|
|
|
function testCallProtoMethod() {
|
|
|
|
function X() { this.x = 1; }
|
|
|
|
X.prototype.getName = function () { return "X"; }
|
|
|
|
|
|
|
|
function Y() { this.x = 2; }
|
|
|
|
Y.prototype.getName = function() "Y";
|
|
|
|
|
|
|
|
var a = [new X, new X, new X, new X, new Y];
|
|
|
|
var s = '';
|
|
|
|
for (var i = 0; i < a.length; i++)
|
|
|
|
s += a[i].getName();
|
|
|
|
return s;
|
|
|
|
}
|
|
|
|
testCallProtoMethod.expected = 'XXXXY';
|
|
|
|
test(testCallProtoMethod);
|
|
|
|
|
2008-10-28 00:11:26 -07:00
|
|
|
function testTypeUnstableForIn() {
|
|
|
|
var a = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16];
|
|
|
|
var x = 0;
|
|
|
|
for (var i in a) {
|
|
|
|
i = parseInt(i);
|
|
|
|
x++;
|
|
|
|
}
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testTypeUnstableForIn.expected = 16;
|
|
|
|
test(testTypeUnstableForIn);
|
|
|
|
|
2008-10-28 17:34:09 -07:00
|
|
|
function testAddUndefined() {
|
|
|
|
for (var j = 0; j < 3; ++j)
|
|
|
|
(0 + void 0) && 0;
|
|
|
|
}
|
|
|
|
test(testAddUndefined);
|
|
|
|
|
2008-10-29 00:14:30 -07:00
|
|
|
function testStringify() {
|
|
|
|
var t = true, f = false, u = undefined, n = 5, d = 5.5, s = "x";
|
|
|
|
var a = [];
|
|
|
|
for (var i = 0; i < 10; ++i) {
|
|
|
|
a[0] = "" + t;
|
|
|
|
a[1] = t + "";
|
|
|
|
a[2] = "" + f;
|
|
|
|
a[3] = f + "";
|
|
|
|
a[4] = "" + u;
|
|
|
|
a[5] = u + "";
|
|
|
|
a[6] = "" + n;
|
|
|
|
a[7] = n + "";
|
|
|
|
a[8] = "" + d;
|
|
|
|
a[9] = d + "";
|
|
|
|
a[10] = "" + s;
|
|
|
|
a[11] = s + "";
|
|
|
|
}
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
testStringify.expected = "true,true,false,false,undefined,undefined,5,5,5.5,5.5,x,x";
|
|
|
|
test(testStringify);
|
|
|
|
|
2008-11-13 00:30:20 -08:00
|
|
|
function testObjectToString() {
|
|
|
|
var o = {toString: function()"foo"};
|
|
|
|
var s = "";
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
s += o;
|
|
|
|
return s;
|
|
|
|
}
|
|
|
|
testObjectToString.expected = "foofoofoofoofoofoofoofoofoofoo";
|
|
|
|
test(testObjectToString);
|
|
|
|
|
|
|
|
function testObjectToNumber() {
|
|
|
|
var o = {valueOf: function()-3};
|
|
|
|
var x = 0;
|
|
|
|
for (var i = 0; i < 10; i++)
|
|
|
|
x -= o;
|
|
|
|
return x;
|
|
|
|
}
|
|
|
|
testObjectToNumber.expected = 30;
|
|
|
|
test(testObjectToNumber);
|
|
|
|
|
|
|
|
function my_iterator_next() {
|
|
|
|
if (this.i == 10) {
|
|
|
|
this.i = 0;
|
|
|
|
throw this.StopIteration;
|
|
|
|
}
|
|
|
|
return this.i++;
|
|
|
|
}
|
|
|
|
function testCustomIterator() {
|
|
|
|
var o = {
|
|
|
|
__iterator__: function () {
|
|
|
|
return {
|
|
|
|
i: 0,
|
|
|
|
next: my_iterator_next,
|
|
|
|
StopIteration: StopIteration
|
|
|
|
};
|
|
|
|
}
|
|
|
|
};
|
|
|
|
var a=[];
|
|
|
|
for (var k = 0; k < 100; k += 10) {
|
|
|
|
for(var j in o) {
|
|
|
|
a[k + (j >> 0)] = j*k;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return a.join();
|
|
|
|
}
|
|
|
|
testCustomIterator.expected = "0,0,0,0,0,0,0,0,0,0,0,10,20,30,40,50,60,70,80,90,0,20,40,60,80,100,120,140,160,180,0,30,60,90,120,150,180,210,240,270,0,40,80,120,160,200,240,280,320,360,0,50,100,150,200,250,300,350,400,450,0,60,120,180,240,300,360,420,480,540,0,70,140,210,280,350,420,490,560,630,0,80,160,240,320,400,480,560,640,720,0,90,180,270,360,450,540,630,720,810";
|
|
|
|
test(testCustomIterator);
|
|
|
|
|
2008-11-13 15:58:58 -08:00
|
|
|
function bug464403() {
|
|
|
|
print(8);
|
|
|
|
var u = [print, print, function(){}]
|
|
|
|
for each (x in u) for (u.e in [1,1,1,1]);
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
bug464403.expected = "ok";
|
|
|
|
test(bug464403);
|
|
|
|
|
2008-11-15 16:42:35 -08:00
|
|
|
function testBoxDoubleWithDoubleSizedInt()
|
|
|
|
{
|
|
|
|
var i = 0;
|
|
|
|
var a = new Array(3);
|
|
|
|
|
|
|
|
while (i < a.length)
|
|
|
|
a[i++] = 0x5a827999;
|
|
|
|
return a.join(",");
|
|
|
|
}
|
|
|
|
testBoxDoubleWithDoubleSizedInt.expected = "1518500249,1518500249,1518500249";
|
|
|
|
test(testBoxDoubleWithDoubleSizedInt);
|
|
|
|
|
2008-10-28 17:34:09 -07:00
|
|
|
/* NOTE: Keep this test last, since it screws up all for...in loops after it. */
|
2008-10-28 00:11:26 -07:00
|
|
|
function testGlobalProtoAccess() {
|
|
|
|
return "ok";
|
|
|
|
}
|
|
|
|
this.__proto__.a = 3; for (var j = 0; j < 4; ++j) { [a]; }
|
|
|
|
testGlobalProtoAccess.expected = "ok";
|
|
|
|
test(testGlobalProtoAccess);
|
|
|
|
|
2008-07-20 13:17:58 -07:00
|
|
|
/* Keep these at the end so that we can see the summary after the trace-debug spew. */
|
2008-08-02 15:56:28 -07:00
|
|
|
print("\npassed:", passes.length && passes.join(","));
|
|
|
|
print("\nFAILED:", fails.length && fails.join(","));
|