Bug 1185106 - Part 6.2: Add parser test for async function expression. r=efaust,till draft
authorMariusz Kierski <mkierski@mozilla.com>
Sun, 28 Aug 2016 23:58:28 +0900
changeset 430933 e3ac6d185295ce982b606aefd6bb1bf9efb65172
parent 430932 6bde9502ed3cbcf771b8169ff89a58922dfae87d
child 430934 604969949219386e333fcc3f8f5520ab6c47ad3a
push id33945
push userarai_a@mac.com
push dateFri, 28 Oct 2016 11:34:02 +0000
reviewersefaust, till
bugs1185106
milestone52.0a1
Bug 1185106 - Part 6.2: Add parser test for async function expression. r=efaust,till MozReview-Commit-ID: 4C5ePdMARoJ
js/src/jit-test/lib/syntax.js
js/src/tests/ecma_7/AsyncFunctions/EarlyErrors.js
js/src/tests/ecma_7/AsyncFunctions/syntax.js
js/src/tests/js1_8_5/reflect-parse/async.js
--- 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);