blob: d369e33bd78bf3450e8609e8962fc466fe75f9d6 [file] [log] [blame]
function assert(b, m = "") {
if (!b)
throw new Error("Bad assertion: " + m);
}
noInline(assert);
const iterations = 20000;
function test1() {
function bar(a, b, ...args) {
return args.length;
}
noInline(bar);
for (let i = 0; i < iterations; i++) {
assert(bar() === 0, bar());
assert(bar(i) === 0);
assert(bar(i, i) === 0);
assert(bar(i, i, i) === 1);
assert(bar(i, i, i, i, i) === 3);
}
}
function shallowEq(a, b) {
if (a.length !== b.length)
return false;
for (let i = 0; i < a.length; i++) {
if (a.length !== b.length)
return false;
}
return true;
}
noInline(shallowEq);
function test2() {
function jaz(a, b, ...args) {
let result = [];
for (let i = 0; i < args.length; i++) {
result.push(args[i]);
}
return result;
}
noInline(jaz);
function jaz2(...args) {
function kaz(a, b, ...args) {
let result = [];
for (let i = 0; i < args.length; i++) {
result.push(args[i]);
}
return result;
}
return kaz.apply(null, args);
}
noInline(jaz2);
for (let f of [jaz, jaz2]) {
for (let i = 0; i < iterations; i++) {
let r = f();
assert(!r.length);
r = f(i);
assert(!r.length);
r = f(i, i)
assert(!r.length);
r = f(i, i, i)
assert(r.length === 1);
assert(shallowEq(r, [i]));
r = f(i, i, i)
assert(r.length === 1);
assert(shallowEq(r, [i]));
r = f(i, i, i, i*2, i*4)
assert(r.length === 3);
assert(shallowEq(r, [i, i*2, i*4]));
}
}
}
function test3() {
function foo(...args) {
return args;
}
function baz(a, b, c, ...args) {
return foo.apply(null, args);
}
function jaz(a, b, c, d, e, f) {
return baz(a, b, c, d, e, f);
}
noInline(jaz);
for (let i = 0; i < iterations; i++) {
let r = jaz();
assert(r.length === 3);
assert(shallowEq(r, [undefined, undefined, undefined]));
r = jaz(i, i);
assert(r.length === 3);
assert(shallowEq(r, [undefined, undefined, undefined]));
r = jaz(i, i, i);
assert(r.length === 3);
assert(shallowEq(r, [undefined, undefined, undefined]));
r = jaz(i, i, i, i);
assert(r.length === 3);
assert(shallowEq(r, [i, undefined, undefined]));
r = jaz(i, i, i, i, i, i);
assert(r.length === 3);
assert(shallowEq(r, [i, i, i]));
}
}
function test4() {
function baz(...args) {
return args;
}
function jaz(a, b, ...args) {
return baz.apply(null, args);
}
noInline(jaz);
for (let i = 0; i < iterations; i++) {
let r = jaz();
assert(r.length === 0);
r = jaz(i);
assert(r.length === 0);
r = jaz(i, i);
assert(r.length === 0);
r = jaz(i, i, i);
assert(r.length === 1);
assert(shallowEq(r, [i]));
r = jaz(i, i, i, i*10);
assert(r.length === 2);
assert(shallowEq(r, [i, i*10]));
let o = {};
r = jaz(i, i, i, i*10, o);
assert(r.length === 3);
assert(shallowEq(r, [i, i*10, o]));
}
}
function test5() {
function baz(...args) {
return args;
}
noInline(baz);
function jaz(a, b, ...args) {
return baz.apply(null, args);
}
noInline(jaz);
for (let i = 0; i < iterations; i++) {
let r = jaz();
assert(r.length === 0);
r = jaz(i);
assert(r.length === 0);
r = jaz(i, i);
assert(r.length === 0);
r = jaz(i, i, i);
assert(r.length === 1);
assert(shallowEq(r, [i]));
r = jaz(i, i, i, i*10);
assert(r.length === 2);
assert(shallowEq(r, [i, i*10]));
let o = {};
r = jaz(i, i, i, i*10, o);
assert(r.length === 3);
assert(shallowEq(r, [i, i*10, o]));
}
}
function test6() {
"use strict";
function baz(...args) {
return args;
}
noInline(baz);
function jaz(a, b, ...args) {
return baz.apply(null, args);
}
noInline(jaz);
for (let i = 0; i < iterations; i++) {
let r = jaz();
assert(r.length === 0);
r = jaz(i);
assert(r.length === 0);
r = jaz(i, i);
assert(r.length === 0);
r = jaz(i, i, i);
assert(r.length === 1);
assert(shallowEq(r, [i]));
r = jaz(i, i, i, i*10);
assert(r.length === 2);
assert(shallowEq(r, [i, i*10]));
let o = {};
r = jaz(i, i, i, i*10, o);
assert(r.length === 3);
assert(shallowEq(r, [i, i*10, o]));
}
}
function test7() {
let shouldExit = false;
function baz(...args) {
if (shouldExit) {
OSRExit();
return [args.length, args[0], args[1], args[2]];
}
return [args.length, args[0], args[1], args[2]];
}
function jaz(a, b, ...args) {
return baz.apply(null, args);
}
noInline(jaz);
function check(i) {
let [length, a, b, c] = jaz();
assert(length === 0);
assert(a === undefined);
assert(b === undefined);
assert(c === undefined);
[length, a, b, c] = jaz(i);
assert(length === 0);
assert(a === undefined);
assert(b === undefined);
assert(c === undefined);
[length, a, b, c] = jaz(i, i);
assert(length === 0);
assert(a === undefined);
assert(b === undefined);
assert(c === undefined);
[length, a, b, c] = jaz(i, i, i);
assert(length === 1);
assert(a === i, JSON.stringify(a));
assert(b === undefined);
assert(c === undefined);
[length, a, b, c] = jaz(i, i, i, i*10);
assert(length === 2);
assert(a === i);
assert(b === i*10);
assert(c === undefined);
let o = {oooo:20};
[length, a, b, c] = jaz(i, i, i, i*10, o);
assert(length === 3);
assert(a === i);
assert(b === i*10);
assert(c === o);
}
shouldExit = true;
for (let i = 0; i < 400; i++) {
check(i);
}
shouldExit = false;
for (let i = 0; i < iterations; i++) {
check(i);
}
shouldExit = false;
check(10);
}
function test8() {
let shouldExit = false;
function baz(...args) {
if (shouldExit) {
OSRExit();
return args;
}
return args;
}
function jaz(a, b, ...args) {
return baz.apply(null, args);
}
noInline(jaz);
function check(i) {
let args = jaz();
assert(args.length === 0);
args = jaz(i);
assert(args.length === 0);
args = jaz(i, i);
assert(args.length === 0);
args = jaz(i, i, i);
assert(args.length === 1);
assert(args[0] === i);
args = jaz(i, i, i, i*10);
assert(args.length === 2);
assert(args[0] === i);
assert(args[1] === i*10);
let o = {oooo:20};
args = jaz(i, i, i, i*10, o);
assert(args.length === 3);
assert(args[0] === i);
assert(args[1] === i*10);
assert(args[2] === o);
}
shouldExit = true;
for (let i = 0; i < 400; i++) {
check(i);
}
shouldExit = false;
for (let i = 0; i < iterations; i++) {
check(i);
}
shouldExit = false;
check(10);
}
function test9() {
let shouldExit = false;
function baz(a, ...args) {
if (shouldExit) {
OSRExit();
return [args.length, args[0], args[1]];
}
return [args.length, args[0], args[1]];
}
function jaz(...args) {
return baz.apply(null, args);
}
noInline(jaz);
function check(i) {
let [length, a, b] = jaz();
assert(length === 0);
[length, a, b] = jaz(i);
assert(length === 0);
assert(a === undefined);
assert(b === undefined);
[length, a, b] = jaz(i, i + 1);
assert(length === 1);
assert(a === i+1);
assert(b === undefined);
[length, a, b] = jaz(i, i+1, i+2);
assert(length === 2);
assert(a === i+1);
assert(b === i+2);
let o = {oooo:20};
[length, a, b] = jaz(i, i+1, o);
assert(length === 2);
assert(a === i+1);
assert(b === o);
}
shouldExit = true;
for (let i = 0; i < 400; i++) {
check(i);
}
shouldExit = false;
for (let i = 0; i < iterations; i++) {
check(i);
}
shouldExit = false;
check(10);
}
function test10() {
function baz(a, b, c, ...args) {
return [args.length, args[0], args[1], args[2], args[3]];
}
function jaz(a, b, c, d, e, f) {
return baz(a, b, c, d, e, f);
}
noInline(jaz);
for (let i = 0; i < iterations; i++) {
let [length, a, b, c, d] = jaz(1, 2, 3, 4, 5, 6);
assert(length === 3);
assert(a === 4);
assert(b === 5);
assert(c === 6);
assert(d === undefined);
}
}
function test11() {
function bar(...args) {
return args;
}
noInline(bar);
function foo(a, b, c, d, ...args) {
return bar.apply(null, args);
}
noInline(foo);
function makeArguments(args) {
return [1,2,3,4, ...args];
}
for (let i = 0; i < iterations; i++) {
function test() { assert(shallowEq(a, foo.apply(null, makeArguments(a)))); }
let a = [{}, 25, 50];
test();
a = [];
test();
a = [{foo: 20}];
test();
a = [10, 20, 30, 40, 50, 60, 70, 80];
test();
}
}
function test12() {
"use strict";
let thisValue = {};
function getThisValue() { return thisValue; }
noInline(getThisValue);
function bar(...args) {
assert(this === thisValue);
return args;
}
noInline(bar);
function foo(a, b, c, d, ...args) {
return bar.apply(getThisValue(), args);
}
noInline(foo);
function makeArguments(args) {
return [1,2,3,4, ...args];
}
for (let i = 0; i < iterations; i++) {
function test() { assert(shallowEq(a, foo.apply(null, makeArguments(a)))); }
let a = [{}, 25, 50];
test();
a = [];
test();
a = [{foo: 20}];
test();
a = [10, 20, 30, 40, 50, 60, 70, 80];
test();
}
}
function test13() {
"use strict";
function bar(...args) {
return args;
}
noInline(bar);
function top(a, b, c, d, ...args) {
return bar.apply(null, args);
}
function foo(...args) {
let r = top.apply(null, args);
return r;
}
noInline(foo);
function makeArguments(args) {
return [1,2,3,4, ...args];
}
for (let i = 0; i < iterations; i++) {
function test() { assert(shallowEq(a, foo.apply(null, makeArguments(a)))); }
let a = [{}, 25, 50];
test();
a = [];
test();
a = [10, 20, 30, 40, 50, 60, 70, 80];
test();
}
}
function test14() {
"use strict";
function bar(...args) {
return args;
}
noInline(bar);
function top(a, b, c, d, ...args) {
return bar.apply(null, args);
}
function foo(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10, a11, a12, a13, a14, a15, a16, a17) {
return top(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10, a11, a12, a13, a14, a15, a16, a17);
}
noInline(foo);
function makeArguments(args) {
let r = [1,2,3,4, ...args];
while (r.length < foo.length)
r.push(undefined);
return r;
}
for (let i = 0; i < iterations; i++) {
function test()
{
let args = makeArguments(a);
assert(shallowEq(args.slice(4), foo.apply(null, args)));
}
let a = [{}, 25, 50];
test();
a = [];
test();
a = [10, 20, 30, 40, 50, 60, 70, 80];
test();
}
}
function test15() {
"use strict";
function bar(...args) {
return args;
}
noInline(bar);
function top(a, b, c, d, ...args) {
return bar.apply(null, args);
}
function foo(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10, a11, a12, a13, a14, a15, a16, a17) {
let r = top(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10, a11, a12, a13, a14, a15, a16, a17);
return r;
}
noInline(foo);
function makeArguments(args) {
let r = [1,2,3,4, ...args];
while (r.length < foo.length)
r.push(undefined);
return r;
}
for (let i = 0; i < iterations; i++) {
function test()
{
let args = makeArguments(a);
assert(shallowEq(args.slice(4), foo.apply(null, args)));
}
let a = [{}, 25, 50];
test();
a = [];
test();
a = [10, 20, 30, 40, 50, 60, 70, 80];
test();
}
}
let start = Date.now();
test1();
test2();
test3();
test4();
test5();
test6();
test7();
test8();
test9();
test10();
test11();
test12();
test13();
test14();
test15();
const verbose = false;
if (verbose)
print(Date.now() - start);