Bug 1185106 - Part 6.2: Add parser test for async function expression. r=efaust,till
MozReview-Commit-ID: 4C5ePdMARoJ
--- a/js/src/jit-test/lib/syntax.js
+++ b/js/src/jit-test/lib/syntax.js
@@ -1236,10 +1236,39 @@ function test_syntax(postfixes, check_er
test("async function A(a) { await X ");
test("async function A(a) { await X; ");
test("async function A(a) { await X; } ");
test("async function A(a) { await await ");
test("async function A(a) { await await await ");
test("async function A(a) { await await await X ");
test("async function A(a) { await await await X; ");
test("async function A(a) { await await await X; } ");
+
+ // async/await function expression
+
+ test("(async ");
+ test("(async function ");
+ test("(async function A ");
+ test("(async function A( ");
+ test("(async function A() ");
+ test("(async function A(a ");
+ test("(async function A(a) ");
+ test("(async function A(a) { ");
+ test("(async function A(a) {} ");
+ test("(async function A(a) { await ");
+ test("(async function A(a) { await X ");
+ test("(async function A(a) { await X; ");
+ test("(async function A(a) { await X; } ");
+ test("(async function A(a) { await X; }) ");
+
+ test("(async function ( ");
+ test("(async function () ");
+ test("(async function (a ");
+ test("(async function (a) ");
+ test("(async function (a) { ");
+ test("(async function (a) {} ");
+ test("(async function (a) { await ");
+ test("(async function (a) { await X ");
+ test("(async function (a) { await X; ");
+ test("(async function (a) { await X; } ");
+ test("(async function (a) { await X; }) ");
}
}
--- a/js/src/tests/ecma_7/AsyncFunctions/EarlyErrors.js
+++ b/js/src/tests/ecma_7/AsyncFunctions/EarlyErrors.js
@@ -5,33 +5,47 @@ print(BUGNUMBER + ": " + summary);
function assertThrowsSE(code) {
assertThrows(() => Reflect.parse(code), SyntaxError);
}
if (asyncFunctionsEnabled() && typeof Reflect !== "undefined" && Reflect.parse) {
// If FormalParameters Contains AwaitExpression is true.
assertThrowsSE("async function a(k = await 3) {}");
+ assertThrowsSE("(async function(k = await 3) {})");
+ assertThrowsSE("(async function a(k = await 3) {})");
// If BindingIdentifier is `eval` or `arguments`.
assertThrowsSE("'use strict'; async function eval() {}");
+ assertThrowsSE("'use strict'; (async function eval() {})");
assertThrowsSE("'use strict'; async function arguments() {}");
+ assertThrowsSE("'use strict'; (async function arguments() {})");
// If any element of the BoundNames of FormalParameters also occurs in the
// LexicallyDeclaredNames of AsyncFunctionBody.
assertThrowsSE("async function a(x) { let x; }");
+ assertThrowsSE("(async function(x) { let x; })");
+ assertThrowsSE("(async function a(x) { let x; })");
// If FormalParameters contains SuperProperty is true.
assertThrowsSE("async function a(k = super.prop) { }");
+ assertThrowsSE("(async function(k = super.prop) {})");
+ assertThrowsSE("(async function a(k = super.prop) {})");
// If AsyncFunctionBody contains SuperProperty is true.
assertThrowsSE("async function a() { super.prop(); }");
+ assertThrowsSE("(async function() { super.prop(); })");
+ assertThrowsSE("(async function a() { super.prop(); })");
// If FormalParameters contains SuperCall is true.
assertThrowsSE("async function a(k = super()) {}");
+ assertThrowsSE("(async function(k = super()) {})");
+ assertThrowsSE("(async function a(k = super()) {})");
// If AsyncFunctionBody contains SuperCall is true.
assertThrowsSE("async function a() { super(); }");
+ assertThrowsSE("(async function() { super(); })");
+ assertThrowsSE("(async function a() { super(); })");
}
if (typeof reportCompare === "function")
reportCompare(true, true);
--- a/js/src/tests/ecma_7/AsyncFunctions/syntax.js
+++ b/js/src/tests/ecma_7/AsyncFunctions/syntax.js
@@ -9,20 +9,28 @@ if (asyncFunctionsEnabled() && typeof Re
assertEq(Reflect.parse("async function a() {}").body[0].async, true);
// Async generators are not allowed (with regards to spec)
assertThrows(() => Reflect.parse("async function* a() {}"), SyntaxError);
// No line terminator after async
assertEq(Reflect.parse("async\nfunction a(){}").body[0].expression.name, "async");
+ // Async function expressions
+ assertEq(Reflect.parse("(async function() {})()").body[0].expression.callee.async, true);
+ assertEq(Reflect.parse("var k = async function() {}").body[0].declarations[0].init.async, true);
+ assertEq(Reflect.parse("var nmd = async function named() {}").body[0].declarations[0].init.id.name, "named");
+
// `await` handling for function declaration name inherits.
assertEq(Reflect.parse("async function await() {}").body[0].id.name, "await");
assertThrows(() => Reflect.parse("async function f() { async function await() {} }"), SyntaxError);
+ // `await` is not allowed in function expression name.
+ assertThrows(() => Reflect.parse("(async function await() {})"), SyntaxError);
+
// Awaiting not directly inside an async function is not allowed
assertThrows(() => Reflect.parse("await 4;"), SyntaxError);
assertThrows(() => Reflect.parse("function a() { await 4; }"), SyntaxError);
assertThrows(() => Reflect.parse("function* a() { await 4; }"), SyntaxError);
assertThrows(() => Reflect.parse("async function k() { function a() { await 4; } }"), SyntaxError);
// No line terminator after await is allowed
assertThrows(() => Reflect.parse("async function a() { await\n4; }"), SyntaxError);
@@ -66,12 +74,15 @@ if (asyncFunctionsEnabled() && typeof Re
assertEq(Reflect.parse("async function a() { await 2 + 3; }")
.body[0].body.body[0].expression.left.operator, "await");
assertEq(Reflect.parse("async function a() { await 2 + 3; }")
.body[0].body.body[0].expression.right.value, 3);
// blocks and other constructions
assertEq(Reflect.parse("{ async function a() { return 2; } }")
.body[0].body[0].async, true);
+
+ // Async function expression is primary expression.
+ Reflect.parse("(async function a() {}.constructor)");
}
if (typeof reportCompare === "function")
reportCompare(true, true);
--- a/js/src/tests/js1_8_5/reflect-parse/async.js
+++ b/js/src/tests/js1_8_5/reflect-parse/async.js
@@ -8,14 +8,18 @@ function asyncFunctionsEnabled() {
return false;
}
}
if (asyncFunctionsEnabled()) {
// async function declaration.
assertDecl("async function foo() {}", asyncFunDecl(ident("foo"), [], blockStmt([])));
+ // async function expression.
+ assertExpr("(async function() {})", asyncFunExpr(null, [], blockStmt([])));
+ assertExpr("(async function foo() {})", asyncFunExpr(ident("foo"), [], blockStmt([])));
+
// await expression.
assertDecl("async function foo() { await bar }", asyncFunDecl(ident("foo"), [], blockStmt([exprStmt(unExpr("await", ident("bar")))])));
}
if (typeof reportCompare === 'function')
reportCompare(true, true);