mirror of
https://github.com/vercel-labs/scriptc.git
synced 2026-10-26 06:34:20 +08:00
Admit direct arguments reads in Test262 scripts
This commit is contained in:
@@ -73,6 +73,18 @@ test("receiver-bound this is admitted without adapting script-level this", () =>
|
||||
}
|
||||
});
|
||||
|
||||
test("arguments reads are admitted only for indexed and length access inside a function", () => {
|
||||
for (const [body, expected] of [
|
||||
["function f() { return arguments.length === 1 && arguments[0] === 3; } assert(f(3));", undefined],
|
||||
["function f() { return arguments; }", "host:arguments"],
|
||||
["function f() { return Array.isArray(arguments); }", "host:arguments"],
|
||||
["assert.sameValue(arguments.length, 0);", "host:arguments"],
|
||||
]) {
|
||||
const text = source("description: arguments", body!);
|
||||
expect(exclusion(text, metadata(text), "strict")).toBe(expected);
|
||||
}
|
||||
});
|
||||
|
||||
test("negative parse cases require the compiler's matching source diagnostic", () => {
|
||||
const text = source("negative: {phase: parse, type: SyntaxError}", "$DONOTEVALUATE();\nconst = ;");
|
||||
expect(exclusion(text, metadata(text), "strict")).toBeUndefined();
|
||||
|
||||
@@ -95,6 +95,14 @@ function hasOwnThisBinding(node) {
|
||||
return false;
|
||||
}
|
||||
|
||||
function argumentsOwner(node) {
|
||||
for (let parent = node.parent; parent; parent = parent.parent) {
|
||||
if (ts.isArrowFunction(parent)) continue;
|
||||
if (ts.isFunctionLike(parent) && parent.body) return parent;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
// The first static profile adapts scripts to standalone strict modules. Be
|
||||
// conservative about observable global-script semantics and helper reflection.
|
||||
// Exclusions are runner limitations, never implementation support claims.
|
||||
@@ -111,7 +119,7 @@ export function exclusion(source, meta, variant) {
|
||||
if (unsupportedIncludes.length) return `harness-includes:${unsupportedIncludes.join(",")}`;
|
||||
const sf = ts.createSourceFile("test.js", source, ts.ScriptTarget.Latest, true, ts.ScriptKind.JS);
|
||||
let reason;
|
||||
const forbidden = new Set(["$262", "$DONE", "$DONOTEVALUATE", "globalThis", "eval", "Function", "print", "process", "require", "arguments"]);
|
||||
const forbidden = new Set(["$262", "$DONE", "$DONOTEVALUATE", "globalThis", "eval", "Function", "print", "process", "require"]);
|
||||
if (variant === "sloppy") for (const name of ["module", "exports", "__dirname", "__filename"]) forbidden.add(name);
|
||||
if (meta.flags.includes("async")) forbidden.delete("$DONE");
|
||||
const visit = (node) => {
|
||||
@@ -121,6 +129,11 @@ export function exclusion(source, meta, variant) {
|
||||
reason = "host:script-environment";
|
||||
} else if (ts.isIdentifier(node) && forbidden.has(node.text)) {
|
||||
reason = `host:${node.text}`;
|
||||
} else if (ts.isIdentifier(node) && node.text === "arguments" &&
|
||||
(!argumentsOwner(node) ||
|
||||
!(ts.isPropertyAccessExpression(node.parent) && node.parent.expression === node && node.parent.name.text === "length") &&
|
||||
!(ts.isElementAccessExpression(node.parent) && node.parent.expression === node))) {
|
||||
reason = "host:arguments";
|
||||
} else if (ts.isIdentifier(node) && node.text === "assert") {
|
||||
const parent = node.parent;
|
||||
if (ts.isCallExpression(parent) && parent.expression === node) {
|
||||
|
||||
@@ -168,6 +168,8 @@
|
||||
"test/built-ins/String/prototype/trim/15.5.4.20-2-47.js",
|
||||
"test/built-ins/String/prototype/trim/15.5.4.20-2-50.js",
|
||||
"test/built-ins/String/prototype/trim/15.5.4.20-2-6.js",
|
||||
"test/language/arguments-object/func-decl-args-trailing-comma-null.js",
|
||||
"test/language/arguments-object/func-expr-args-trailing-comma-undefined.js",
|
||||
"test/language/expressions/addition/S11.6.1_A4_T1.js",
|
||||
"test/language/expressions/addition/S11.6.1_A4_T2.js",
|
||||
"test/language/expressions/addition/S11.6.1_A4_T3.js",
|
||||
@@ -372,6 +374,8 @@
|
||||
"test/built-ins/String/prototype/trim/15.5.4.20-2-47.js": "3e1a745af465177a96a29601e56299afc044060dbc2ac3061a59032be451cfde",
|
||||
"test/built-ins/String/prototype/trim/15.5.4.20-2-50.js": "38b84997faa99e422408917eeac7f3575bd6064b429ea390a9d041fd77fce532",
|
||||
"test/built-ins/String/prototype/trim/15.5.4.20-2-6.js": "3d5857f24117f65f07a70edd0d254dfa07f593c76effed94500847ccf8564c06",
|
||||
"test/language/arguments-object/func-decl-args-trailing-comma-null.js": "80aecea8edd0d7bac1ddcfcd6cb97dc9a513b25a9283bb9cedd21fd77dd64d50",
|
||||
"test/language/arguments-object/func-expr-args-trailing-comma-undefined.js": "cf39515a9031db4c81db231a157516bdc97617c392e4ef28890b2ae74777a99e",
|
||||
"test/language/expressions/addition/S11.6.1_A4_T1.js": "12928eb319dcf0cc785e399580effb0b7495709296dce9c0a58e8408616a959f",
|
||||
"test/language/expressions/addition/S11.6.1_A4_T2.js": "aee914241b607f56a98de04492f2d580e7bc69cca232af679d0c02b7025cc06b",
|
||||
"test/language/expressions/addition/S11.6.1_A4_T3.js": "987b1c3cf66b6bbb2f6d8aaf6d1435cb1238b19132fa861a91aa2c35085d229d",
|
||||
|
||||
+43
@@ -0,0 +1,43 @@
|
||||
// This file was procedurally generated from the following sources:
|
||||
// - src/arguments/args-trailing-comma-null.case
|
||||
// - src/arguments/default/func-decl.template
|
||||
/*---
|
||||
description: A trailing comma after null should not increase the arguments.length (function declaration)
|
||||
esid: sec-arguments-exotic-objects
|
||||
flags: [generated]
|
||||
info: |
|
||||
9.4.4 Arguments Exotic Objects
|
||||
|
||||
Most ECMAScript functions make an arguments object available to their code. Depending upon the
|
||||
characteristics of the function definition, its arguments object is either an ordinary object
|
||||
or an arguments exotic object.
|
||||
|
||||
Trailing comma in the arguments list
|
||||
|
||||
Left-Hand-Side Expressions
|
||||
|
||||
Arguments :
|
||||
( )
|
||||
( ArgumentList )
|
||||
( ArgumentList , )
|
||||
|
||||
ArgumentList :
|
||||
AssignmentExpression
|
||||
... AssignmentExpression
|
||||
ArgumentList , AssignmentExpression
|
||||
ArgumentList , ... AssignmentExpression
|
||||
---*/
|
||||
|
||||
|
||||
var callCount = 0;
|
||||
// Stores a reference `ref` for case evaluation
|
||||
function ref() {
|
||||
assert.sameValue(arguments.length, 2);
|
||||
assert.sameValue(arguments[0], 42);
|
||||
assert.sameValue(arguments[1], null);
|
||||
callCount = callCount + 1;
|
||||
}
|
||||
|
||||
ref(42, null,);
|
||||
|
||||
assert.sameValue(callCount, 1, 'function invoked exactly once');
|
||||
Vendored
+44
@@ -0,0 +1,44 @@
|
||||
// This file was procedurally generated from the following sources:
|
||||
// - src/arguments/args-trailing-comma-undefined.case
|
||||
// - src/arguments/default/func-expr.template
|
||||
/*---
|
||||
description: A trailing comma after undefined should not increase the arguments.length (function expression)
|
||||
esid: sec-arguments-exotic-objects
|
||||
flags: [generated]
|
||||
info: |
|
||||
9.4.4 Arguments Exotic Objects
|
||||
|
||||
Most ECMAScript functions make an arguments object available to their code. Depending upon the
|
||||
characteristics of the function definition, its arguments object is either an ordinary object
|
||||
or an arguments exotic object.
|
||||
|
||||
Trailing comma in the arguments list
|
||||
|
||||
Left-Hand-Side Expressions
|
||||
|
||||
Arguments :
|
||||
( )
|
||||
( ArgumentList )
|
||||
( ArgumentList , )
|
||||
|
||||
ArgumentList :
|
||||
AssignmentExpression
|
||||
... AssignmentExpression
|
||||
ArgumentList , AssignmentExpression
|
||||
ArgumentList , ... AssignmentExpression
|
||||
---*/
|
||||
|
||||
|
||||
var callCount = 0;
|
||||
// Stores a reference `ref` for case evaluation
|
||||
var ref;
|
||||
ref = function() {
|
||||
assert.sameValue(arguments.length, 2);
|
||||
assert.sameValue(arguments[0], 42);
|
||||
assert.sameValue(arguments[1], undefined);
|
||||
callCount = callCount + 1;
|
||||
};
|
||||
|
||||
ref(42, undefined,);
|
||||
|
||||
assert.sameValue(callCount, 1, 'function invoked exactly once');
|
||||
Reference in New Issue
Block a user