OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
279 | 279 |
280 CcTest::i_isolate()->stack_guard()->SetStackLimit(GetCurrentStackPosition() - | 280 CcTest::i_isolate()->stack_guard()->SetStackLimit(GetCurrentStackPosition() - |
281 128 * 1024); | 281 128 * 1024); |
282 | 282 |
283 const char* programs[] = { | 283 const char* programs[] = { |
284 "{label: 42}", | 284 "{label: 42}", |
285 "var x = 42;", | 285 "var x = 42;", |
286 "function foo(x, y) { return x + y; }", | 286 "function foo(x, y) { return x + y; }", |
287 "%ArgleBargle(glop);", | 287 "%ArgleBargle(glop);", |
288 "var x = new new Function('this.x = 42');", | 288 "var x = new new Function('this.x = 42');", |
| 289 "var f = (x, y) => x + y;", |
289 NULL | 290 NULL |
290 }; | 291 }; |
291 | 292 |
292 uintptr_t stack_limit = CcTest::i_isolate()->stack_guard()->real_climit(); | 293 uintptr_t stack_limit = CcTest::i_isolate()->stack_guard()->real_climit(); |
293 for (int i = 0; programs[i]; i++) { | 294 for (int i = 0; programs[i]; i++) { |
294 const char* program = programs[i]; | 295 const char* program = programs[i]; |
295 i::Utf8ToUtf16CharacterStream stream( | 296 i::Utf8ToUtf16CharacterStream stream( |
296 reinterpret_cast<const i::byte*>(program), | 297 reinterpret_cast<const i::byte*>(program), |
297 static_cast<unsigned>(strlen(program))); | 298 static_cast<unsigned>(strlen(program))); |
298 i::CompleteParserRecorder log; | 299 i::CompleteParserRecorder log; |
299 i::Scanner scanner(CcTest::i_isolate()->unicode_cache()); | 300 i::Scanner scanner(CcTest::i_isolate()->unicode_cache()); |
300 scanner.Initialize(&stream); | 301 scanner.Initialize(&stream); |
301 | 302 |
302 i::PreParser preparser(&scanner, &log, stack_limit); | 303 i::PreParser preparser(&scanner, &log, stack_limit); |
303 preparser.set_allow_lazy(true); | 304 preparser.set_allow_lazy(true); |
304 preparser.set_allow_natives_syntax(true); | 305 preparser.set_allow_natives_syntax(true); |
| 306 preparser.set_allow_arrow_functions(true); |
305 i::PreParser::PreParseResult result = preparser.PreParseProgram(); | 307 i::PreParser::PreParseResult result = preparser.PreParseProgram(); |
306 CHECK_EQ(i::PreParser::kPreParseSuccess, result); | 308 CHECK_EQ(i::PreParser::kPreParseSuccess, result); |
307 CHECK(!log.HasError()); | 309 CHECK(!log.HasError()); |
308 } | 310 } |
309 } | 311 } |
310 | 312 |
311 | 313 |
312 TEST(StandAlonePreParserNoNatives) { | 314 TEST(StandAlonePreParserNoNatives) { |
313 v8::V8::Initialize(); | 315 v8::V8::Initialize(); |
314 | 316 |
(...skipping 863 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1178 } | 1180 } |
1179 | 1181 |
1180 | 1182 |
1181 enum ParserFlag { | 1183 enum ParserFlag { |
1182 kAllowLazy, | 1184 kAllowLazy, |
1183 kAllowNativesSyntax, | 1185 kAllowNativesSyntax, |
1184 kAllowHarmonyScoping, | 1186 kAllowHarmonyScoping, |
1185 kAllowModules, | 1187 kAllowModules, |
1186 kAllowGenerators, | 1188 kAllowGenerators, |
1187 kAllowForOf, | 1189 kAllowForOf, |
1188 kAllowHarmonyNumericLiterals | 1190 kAllowHarmonyNumericLiterals, |
| 1191 kAllowArrowFunctions |
1189 }; | 1192 }; |
1190 | 1193 |
1191 | 1194 |
1192 enum ParserSyncTestResult { | 1195 enum ParserSyncTestResult { |
1193 kSuccessOrError, | 1196 kSuccessOrError, |
1194 kSuccess, | 1197 kSuccess, |
1195 kError | 1198 kError |
1196 }; | 1199 }; |
1197 | 1200 |
1198 template <typename Traits> | 1201 template <typename Traits> |
1199 void SetParserFlags(i::ParserBase<Traits>* parser, | 1202 void SetParserFlags(i::ParserBase<Traits>* parser, |
1200 i::EnumSet<ParserFlag> flags) { | 1203 i::EnumSet<ParserFlag> flags) { |
1201 parser->set_allow_lazy(flags.Contains(kAllowLazy)); | 1204 parser->set_allow_lazy(flags.Contains(kAllowLazy)); |
1202 parser->set_allow_natives_syntax(flags.Contains(kAllowNativesSyntax)); | 1205 parser->set_allow_natives_syntax(flags.Contains(kAllowNativesSyntax)); |
1203 parser->set_allow_harmony_scoping(flags.Contains(kAllowHarmonyScoping)); | 1206 parser->set_allow_harmony_scoping(flags.Contains(kAllowHarmonyScoping)); |
1204 parser->set_allow_modules(flags.Contains(kAllowModules)); | 1207 parser->set_allow_modules(flags.Contains(kAllowModules)); |
1205 parser->set_allow_generators(flags.Contains(kAllowGenerators)); | 1208 parser->set_allow_generators(flags.Contains(kAllowGenerators)); |
1206 parser->set_allow_for_of(flags.Contains(kAllowForOf)); | 1209 parser->set_allow_for_of(flags.Contains(kAllowForOf)); |
1207 parser->set_allow_harmony_numeric_literals( | 1210 parser->set_allow_harmony_numeric_literals( |
1208 flags.Contains(kAllowHarmonyNumericLiterals)); | 1211 flags.Contains(kAllowHarmonyNumericLiterals)); |
| 1212 parser->set_allow_arrow_functions(flags.Contains(kAllowArrowFunctions)); |
1209 } | 1213 } |
1210 | 1214 |
1211 | 1215 |
1212 void TestParserSyncWithFlags(i::Handle<i::String> source, | 1216 void TestParserSyncWithFlags(i::Handle<i::String> source, |
1213 i::EnumSet<ParserFlag> flags, | 1217 i::EnumSet<ParserFlag> flags, |
1214 ParserSyncTestResult result) { | 1218 ParserSyncTestResult result) { |
1215 i::Isolate* isolate = CcTest::i_isolate(); | 1219 i::Isolate* isolate = CcTest::i_isolate(); |
1216 i::Factory* factory = isolate->factory(); | 1220 i::Factory* factory = isolate->factory(); |
1217 | 1221 |
1218 uintptr_t stack_limit = isolate->stack_guard()->real_climit(); | 1222 uintptr_t stack_limit = isolate->stack_guard()->real_climit(); |
(...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1405 | 1409 |
1406 v8::HandleScope handles(CcTest::isolate()); | 1410 v8::HandleScope handles(CcTest::isolate()); |
1407 v8::Handle<v8::Context> context = v8::Context::New(CcTest::isolate()); | 1411 v8::Handle<v8::Context> context = v8::Context::New(CcTest::isolate()); |
1408 v8::Context::Scope context_scope(context); | 1412 v8::Context::Scope context_scope(context); |
1409 | 1413 |
1410 CcTest::i_isolate()->stack_guard()->SetStackLimit(GetCurrentStackPosition() - | 1414 CcTest::i_isolate()->stack_guard()->SetStackLimit(GetCurrentStackPosition() - |
1411 128 * 1024); | 1415 128 * 1024); |
1412 | 1416 |
1413 static const ParserFlag flags1[] = { | 1417 static const ParserFlag flags1[] = { |
1414 kAllowLazy, kAllowHarmonyScoping, kAllowModules, kAllowGenerators, | 1418 kAllowLazy, kAllowHarmonyScoping, kAllowModules, kAllowGenerators, |
1415 kAllowForOf | 1419 kAllowForOf, kAllowArrowFunctions |
1416 }; | 1420 }; |
1417 for (int i = 0; context_data[i][0] != NULL; ++i) { | 1421 for (int i = 0; context_data[i][0] != NULL; ++i) { |
1418 for (int j = 0; statement_data[j] != NULL; ++j) { | 1422 for (int j = 0; statement_data[j] != NULL; ++j) { |
1419 for (int k = 0; termination_data[k] != NULL; ++k) { | 1423 for (int k = 0; termination_data[k] != NULL; ++k) { |
1420 int kPrefixLen = i::StrLength(context_data[i][0]); | 1424 int kPrefixLen = i::StrLength(context_data[i][0]); |
1421 int kStatementLen = i::StrLength(statement_data[j]); | 1425 int kStatementLen = i::StrLength(statement_data[j]); |
1422 int kTerminationLen = i::StrLength(termination_data[k]); | 1426 int kTerminationLen = i::StrLength(termination_data[k]); |
1423 int kSuffixLen = i::StrLength(context_data[i][1]); | 1427 int kSuffixLen = i::StrLength(context_data[i][1]); |
1424 int kProgramSize = kPrefixLen + kStatementLen + kTerminationLen | 1428 int kProgramSize = kPrefixLen + kStatementLen + kTerminationLen |
1425 + kSuffixLen + i::StrLength("label: for (;;) { }"); | 1429 + kSuffixLen + i::StrLength("label: for (;;) { }"); |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1482 int always_true_flags_len = 0) { | 1486 int always_true_flags_len = 0) { |
1483 v8::HandleScope handles(CcTest::isolate()); | 1487 v8::HandleScope handles(CcTest::isolate()); |
1484 v8::Handle<v8::Context> context = v8::Context::New(CcTest::isolate()); | 1488 v8::Handle<v8::Context> context = v8::Context::New(CcTest::isolate()); |
1485 v8::Context::Scope context_scope(context); | 1489 v8::Context::Scope context_scope(context); |
1486 | 1490 |
1487 CcTest::i_isolate()->stack_guard()->SetStackLimit(GetCurrentStackPosition() - | 1491 CcTest::i_isolate()->stack_guard()->SetStackLimit(GetCurrentStackPosition() - |
1488 128 * 1024); | 1492 128 * 1024); |
1489 | 1493 |
1490 static const ParserFlag default_flags[] = { | 1494 static const ParserFlag default_flags[] = { |
1491 kAllowLazy, kAllowHarmonyScoping, kAllowModules, kAllowGenerators, | 1495 kAllowLazy, kAllowHarmonyScoping, kAllowModules, kAllowGenerators, |
1492 kAllowForOf, kAllowNativesSyntax | 1496 kAllowForOf, kAllowNativesSyntax, kAllowArrowFunctions |
1493 }; | 1497 }; |
1494 ParserFlag* generated_flags = NULL; | 1498 ParserFlag* generated_flags = NULL; |
1495 if (flags == NULL) { | 1499 if (flags == NULL) { |
1496 flags = default_flags; | 1500 flags = default_flags; |
1497 flags_len = ARRAY_SIZE(default_flags); | 1501 flags_len = ARRAY_SIZE(default_flags); |
1498 if (always_true_flags != NULL) { | 1502 if (always_true_flags != NULL) { |
1499 // Remove always_true_flags from default_flags. | 1503 // Remove always_true_flags from default_flags. |
1500 CHECK(always_true_flags_len < flags_len); | 1504 CHECK(always_true_flags_len < flags_len); |
1501 generated_flags = new ParserFlag[flags_len - always_true_flags_len]; | 1505 generated_flags = new ParserFlag[flags_len - always_true_flags_len]; |
1502 int flag_index = 0; | 1506 int flag_index = 0; |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1559 "var foo, eval;", | 1563 "var foo, eval;", |
1560 "var foo, arguments;", | 1564 "var foo, arguments;", |
1561 "try { } catch (eval) { }", | 1565 "try { } catch (eval) { }", |
1562 "try { } catch (arguments) { }", | 1566 "try { } catch (arguments) { }", |
1563 "function eval() { }", | 1567 "function eval() { }", |
1564 "function arguments() { }", | 1568 "function arguments() { }", |
1565 "function foo(eval) { }", | 1569 "function foo(eval) { }", |
1566 "function foo(arguments) { }", | 1570 "function foo(arguments) { }", |
1567 "function foo(bar, eval) { }", | 1571 "function foo(bar, eval) { }", |
1568 "function foo(bar, arguments) { }", | 1572 "function foo(bar, arguments) { }", |
| 1573 "(eval) => { }", |
| 1574 "(arguments) => { }", |
| 1575 "(foo, eval) => { }", |
| 1576 "(foo, arguments) => { }", |
1569 "eval = 1;", | 1577 "eval = 1;", |
1570 "arguments = 1;", | 1578 "arguments = 1;", |
1571 "var foo = eval = 1;", | 1579 "var foo = eval = 1;", |
1572 "var foo = arguments = 1;", | 1580 "var foo = arguments = 1;", |
1573 "++eval;", | 1581 "++eval;", |
1574 "++arguments;", | 1582 "++arguments;", |
1575 "eval++;", | 1583 "eval++;", |
1576 "arguments++;", | 1584 "arguments++;", |
1577 NULL | 1585 NULL |
1578 }; | 1586 }; |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1615 }; | 1623 }; |
1616 | 1624 |
1617 RunParserSyncTest(context_data, statement_data, kSuccess); | 1625 RunParserSyncTest(context_data, statement_data, kSuccess); |
1618 } | 1626 } |
1619 | 1627 |
1620 | 1628 |
1621 TEST(NoErrorsEvalAndArgumentsStrict) { | 1629 TEST(NoErrorsEvalAndArgumentsStrict) { |
1622 const char* context_data[][2] = { | 1630 const char* context_data[][2] = { |
1623 { "\"use strict\";", "" }, | 1631 { "\"use strict\";", "" }, |
1624 { "function test_func() { \"use strict\";", "}" }, | 1632 { "function test_func() { \"use strict\";", "}" }, |
| 1633 { "() => { \"use strict\"; ", "}" }, |
1625 { NULL, NULL } | 1634 { NULL, NULL } |
1626 }; | 1635 }; |
1627 | 1636 |
1628 const char* statement_data[] = { | 1637 const char* statement_data[] = { |
1629 "eval;", | 1638 "eval;", |
1630 "arguments;", | 1639 "arguments;", |
1631 "var foo = eval;", | 1640 "var foo = eval;", |
1632 "var foo = arguments;", | 1641 "var foo = arguments;", |
1633 "var foo = { eval: 1 };", | 1642 "var foo = { eval: 1 };", |
1634 "var foo = { arguments: 1 };", | 1643 "var foo = { arguments: 1 };", |
1635 "var foo = { }; foo.eval = {};", | 1644 "var foo = { }; foo.eval = {};", |
1636 "var foo = { }; foo.arguments = {};", | 1645 "var foo = { }; foo.arguments = {};", |
1637 NULL | 1646 NULL |
1638 }; | 1647 }; |
1639 | 1648 |
1640 RunParserSyncTest(context_data, statement_data, kSuccess); | 1649 static const ParserFlag always_flags[] = {kAllowArrowFunctions}; |
| 1650 RunParserSyncTest(context_data, statement_data, kSuccess, NULL, 0, |
| 1651 always_flags, ARRAY_SIZE(always_flags)); |
1641 } | 1652 } |
1642 | 1653 |
1643 | 1654 |
1644 TEST(ErrorsFutureStrictReservedWords) { | 1655 TEST(ErrorsFutureStrictReservedWords) { |
1645 // Tests that both preparsing and parsing produce the right kind of errors for | 1656 // Tests that both preparsing and parsing produce the right kind of errors for |
1646 // using future strict reserved words as identifiers. Without the strict mode, | 1657 // using future strict reserved words as identifiers. Without the strict mode, |
1647 // it's ok to use future strict reserved words as identifiers. With the strict | 1658 // it's ok to use future strict reserved words as identifiers. With the strict |
1648 // mode, it isn't. | 1659 // mode, it isn't. |
1649 const char* context_data[][2] = { | 1660 const char* context_data[][2] = { |
1650 { "\"use strict\";", "" }, | 1661 { "\"use strict\";", "" }, |
1651 { "function test_func() {\"use strict\"; ", "}"}, | 1662 { "function test_func() {\"use strict\"; ", "}"}, |
| 1663 { "() => { \"use strict\"; ", "}" }, |
1652 { NULL, NULL } | 1664 { NULL, NULL } |
1653 }; | 1665 }; |
1654 | 1666 |
1655 const char* statement_data[] = { | 1667 const char* statement_data[] = { |
1656 "var interface;", | 1668 "var interface;", |
1657 "var foo, interface;", | 1669 "var foo, interface;", |
1658 "try { } catch (interface) { }", | 1670 "try { } catch (interface) { }", |
1659 "function interface() { }", | 1671 "function interface() { }", |
1660 "function foo(interface) { }", | 1672 "function foo(interface) { }", |
1661 "function foo(bar, interface) { }", | 1673 "function foo(bar, interface) { }", |
1662 "interface = 1;", | 1674 "interface = 1;", |
1663 "var foo = interface = 1;", | 1675 "var foo = interface = 1;", |
1664 "++interface;", | 1676 "++interface;", |
1665 "interface++;", | 1677 "interface++;", |
1666 "var yield = 13;", | 1678 "var yield = 13;", |
1667 NULL | 1679 NULL |
1668 }; | 1680 }; |
1669 | 1681 |
1670 RunParserSyncTest(context_data, statement_data, kError); | 1682 static const ParserFlag always_flags[] = {kAllowArrowFunctions}; |
| 1683 RunParserSyncTest(context_data, statement_data, kError, NULL, 0, always_flags, |
| 1684 ARRAY_SIZE(always_flags)); |
1671 } | 1685 } |
1672 | 1686 |
1673 | 1687 |
1674 TEST(NoErrorsFutureStrictReservedWords) { | 1688 TEST(NoErrorsFutureStrictReservedWords) { |
1675 const char* context_data[][2] = { | 1689 const char* context_data[][2] = { |
1676 { "", "" }, | 1690 { "", "" }, |
1677 { "function test_func() {", "}"}, | 1691 { "function test_func() {", "}"}, |
| 1692 { "() => {", "}" }, |
1678 { NULL, NULL } | 1693 { NULL, NULL } |
1679 }; | 1694 }; |
1680 | 1695 |
1681 const char* statement_data[] = { | 1696 const char* statement_data[] = { |
1682 "var interface;", | 1697 "var interface;", |
1683 "var foo, interface;", | 1698 "var foo, interface;", |
1684 "try { } catch (interface) { }", | 1699 "try { } catch (interface) { }", |
1685 "function interface() { }", | 1700 "function interface() { }", |
1686 "function foo(interface) { }", | 1701 "function foo(interface) { }", |
1687 "function foo(bar, interface) { }", | 1702 "function foo(bar, interface) { }", |
1688 "interface = 1;", | 1703 "interface = 1;", |
1689 "var foo = interface = 1;", | 1704 "var foo = interface = 1;", |
1690 "++interface;", | 1705 "++interface;", |
1691 "interface++;", | 1706 "interface++;", |
1692 "var yield = 13;", | 1707 "var yield = 13;", |
1693 NULL | 1708 NULL |
1694 }; | 1709 }; |
1695 | 1710 |
1696 RunParserSyncTest(context_data, statement_data, kSuccess); | 1711 static const ParserFlag always_flags[] = {kAllowArrowFunctions}; |
| 1712 RunParserSyncTest(context_data, statement_data, kSuccess, NULL, 0, |
| 1713 always_flags, ARRAY_SIZE(always_flags)); |
1697 } | 1714 } |
1698 | 1715 |
1699 | 1716 |
1700 TEST(ErrorsReservedWords) { | 1717 TEST(ErrorsReservedWords) { |
1701 // Tests that both preparsing and parsing produce the right kind of errors for | 1718 // Tests that both preparsing and parsing produce the right kind of errors for |
1702 // using future reserved words as identifiers. These tests don't depend on the | 1719 // using future reserved words as identifiers. These tests don't depend on the |
1703 // strict mode. | 1720 // strict mode. |
1704 const char* context_data[][2] = { | 1721 const char* context_data[][2] = { |
1705 { "", "" }, | 1722 { "", "" }, |
1706 { "\"use strict\";", "" }, | 1723 { "\"use strict\";", "" }, |
1707 { "var eval; function test_func() {", "}"}, | 1724 { "var eval; function test_func() {", "}"}, |
1708 { "var eval; function test_func() {\"use strict\"; ", "}"}, | 1725 { "var eval; function test_func() {\"use strict\"; ", "}"}, |
| 1726 { "var eval; () => {", "}"}, |
| 1727 { "var eval; () => {\"use strict\"; ", "}"}, |
1709 { NULL, NULL } | 1728 { NULL, NULL } |
1710 }; | 1729 }; |
1711 | 1730 |
1712 const char* statement_data[] = { | 1731 const char* statement_data[] = { |
1713 "var super;", | 1732 "var super;", |
1714 "var foo, super;", | 1733 "var foo, super;", |
1715 "try { } catch (super) { }", | 1734 "try { } catch (super) { }", |
1716 "function super() { }", | 1735 "function super() { }", |
1717 "function foo(super) { }", | 1736 "function foo(super) { }", |
1718 "function foo(bar, super) { }", | 1737 "function foo(bar, super) { }", |
| 1738 "(super) => { }", |
| 1739 "(bar, super) => { }", |
1719 "super = 1;", | 1740 "super = 1;", |
1720 "var foo = super = 1;", | 1741 "var foo = super = 1;", |
1721 "++super;", | 1742 "++super;", |
1722 "super++;", | 1743 "super++;", |
1723 "function foo super", | 1744 "function foo super", |
1724 NULL | 1745 NULL |
1725 }; | 1746 }; |
1726 | 1747 |
1727 RunParserSyncTest(context_data, statement_data, kError); | 1748 RunParserSyncTest(context_data, statement_data, kError); |
1728 } | 1749 } |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1787 "yield++;", | 1808 "yield++;", |
1788 "yield: 34", | 1809 "yield: 34", |
1789 "function yield(yield) { yield: yield (yield + yield(0)); }", | 1810 "function yield(yield) { yield: yield (yield + yield(0)); }", |
1790 "({ yield: 1 })", | 1811 "({ yield: 1 })", |
1791 "({ get yield() { 1 } })", | 1812 "({ get yield() { 1 } })", |
1792 "yield(100)", | 1813 "yield(100)", |
1793 "yield[100]", | 1814 "yield[100]", |
1794 NULL | 1815 NULL |
1795 }; | 1816 }; |
1796 | 1817 |
1797 RunParserSyncTest(context_data, statement_data, kSuccess); | 1818 static const ParserFlag always_flags[] = {kAllowArrowFunctions}; |
| 1819 RunParserSyncTest(context_data, statement_data, kSuccess, NULL, 0, |
| 1820 always_flags, ARRAY_SIZE(always_flags)); |
1798 } | 1821 } |
1799 | 1822 |
1800 | 1823 |
1801 TEST(NoErrorsYieldSloppyGeneratorsEnabled) { | 1824 TEST(NoErrorsYieldSloppyGeneratorsEnabled) { |
1802 // In sloppy mode, it's okay to use "yield" as identifier, *except* inside a | 1825 // In sloppy mode, it's okay to use "yield" as identifier, *except* inside a |
1803 // generator (see next test). | 1826 // generator (see next test). |
1804 const char* context_data[][2] = { | 1827 const char* context_data[][2] = { |
1805 { "", "" }, | 1828 { "", "" }, |
1806 { "function not_gen() {", "}" }, | 1829 { "function not_gen() {", "}" }, |
1807 { "function * gen() { function not_gen() {", "} }" }, | 1830 { "function * gen() { function not_gen() {", "} }" }, |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1842 | 1865 |
1843 | 1866 |
1844 TEST(ErrorsYieldStrict) { | 1867 TEST(ErrorsYieldStrict) { |
1845 const char* context_data[][2] = { | 1868 const char* context_data[][2] = { |
1846 { "\"use strict\";", "" }, | 1869 { "\"use strict\";", "" }, |
1847 { "\"use strict\"; function not_gen() {", "}" }, | 1870 { "\"use strict\"; function not_gen() {", "}" }, |
1848 { "function test_func() {\"use strict\"; ", "}"}, | 1871 { "function test_func() {\"use strict\"; ", "}"}, |
1849 { "\"use strict\"; function * gen() { function not_gen() {", "} }" }, | 1872 { "\"use strict\"; function * gen() { function not_gen() {", "} }" }, |
1850 { "\"use strict\"; (function not_gen() {", "})" }, | 1873 { "\"use strict\"; (function not_gen() {", "})" }, |
1851 { "\"use strict\"; (function * gen() { (function not_gen() {", "}) })" }, | 1874 { "\"use strict\"; (function * gen() { (function not_gen() {", "}) })" }, |
| 1875 { "() => {\"use strict\"; ", "}" }, |
1852 { NULL, NULL } | 1876 { NULL, NULL } |
1853 }; | 1877 }; |
1854 | 1878 |
1855 const char* statement_data[] = { | 1879 const char* statement_data[] = { |
1856 "var yield;", | 1880 "var yield;", |
1857 "var foo, yield;", | 1881 "var foo, yield;", |
1858 "try { } catch (yield) { }", | 1882 "try { } catch (yield) { }", |
1859 "function yield() { }", | 1883 "function yield() { }", |
1860 "(function yield() { })", | 1884 "(function yield() { })", |
1861 "function foo(yield) { }", | 1885 "function foo(yield) { }", |
(...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2052 RunParserSyncTest(context_data, statement_data, kSuccess, NULL, 0, | 2076 RunParserSyncTest(context_data, statement_data, kSuccess, NULL, 0, |
2053 always_true_flags, 1); | 2077 always_true_flags, 1); |
2054 } | 2078 } |
2055 | 2079 |
2056 | 2080 |
2057 TEST(ErrorsIllegalWordsAsLabelsSloppy) { | 2081 TEST(ErrorsIllegalWordsAsLabelsSloppy) { |
2058 // Using future reserved words as labels is always an error. | 2082 // Using future reserved words as labels is always an error. |
2059 const char* context_data[][2] = { | 2083 const char* context_data[][2] = { |
2060 { "", ""}, | 2084 { "", ""}, |
2061 { "function test_func() {", "}" }, | 2085 { "function test_func() {", "}" }, |
| 2086 { "() => {", "}" }, |
2062 { NULL, NULL } | 2087 { NULL, NULL } |
2063 }; | 2088 }; |
2064 | 2089 |
2065 const char* statement_data[] = { | 2090 const char* statement_data[] = { |
2066 "super: while(true) { break super; }", | 2091 "super: while(true) { break super; }", |
2067 NULL | 2092 NULL |
2068 }; | 2093 }; |
2069 | 2094 |
2070 RunParserSyncTest(context_data, statement_data, kError); | 2095 RunParserSyncTest(context_data, statement_data, kError); |
2071 } | 2096 } |
2072 | 2097 |
2073 | 2098 |
2074 TEST(ErrorsIllegalWordsAsLabelsStrict) { | 2099 TEST(ErrorsIllegalWordsAsLabelsStrict) { |
2075 // Tests that illegal tokens as labels produce the correct errors. | 2100 // Tests that illegal tokens as labels produce the correct errors. |
2076 const char* context_data[][2] = { | 2101 const char* context_data[][2] = { |
2077 { "\"use strict\";", "" }, | 2102 { "\"use strict\";", "" }, |
2078 { "function test_func() {\"use strict\"; ", "}"}, | 2103 { "function test_func() {\"use strict\"; ", "}"}, |
| 2104 { "() => {\"use strict\"; ", "}" }, |
2079 { NULL, NULL } | 2105 { NULL, NULL } |
2080 }; | 2106 }; |
2081 | 2107 |
2082 const char* statement_data[] = { | 2108 const char* statement_data[] = { |
2083 "super: while(true) { break super; }", | 2109 "super: while(true) { break super; }", |
2084 "interface: while(true) { break interface; }", | 2110 "interface: while(true) { break interface; }", |
2085 "yield: while(true) { break yield; }", | 2111 "yield: while(true) { break yield; }", |
2086 NULL | 2112 NULL |
2087 }; | 2113 }; |
2088 | 2114 |
2089 RunParserSyncTest(context_data, statement_data, kError); | 2115 RunParserSyncTest(context_data, statement_data, kError); |
2090 } | 2116 } |
2091 | 2117 |
2092 | 2118 |
2093 TEST(NoErrorsIllegalWordsAsLabels) { | 2119 TEST(NoErrorsIllegalWordsAsLabels) { |
2094 // Using eval and arguments as labels is legal even in strict mode. | 2120 // Using eval and arguments as labels is legal even in strict mode. |
2095 const char* context_data[][2] = { | 2121 const char* context_data[][2] = { |
2096 { "", ""}, | 2122 { "", ""}, |
2097 { "function test_func() {", "}" }, | 2123 { "function test_func() {", "}" }, |
| 2124 { "() => {", "}" }, |
2098 { "\"use strict\";", "" }, | 2125 { "\"use strict\";", "" }, |
2099 { "\"use strict\"; function test_func() {", "}" }, | 2126 { "\"use strict\"; function test_func() {", "}" }, |
| 2127 { "\"use strict\"; () => {", "}" }, |
2100 { NULL, NULL } | 2128 { NULL, NULL } |
2101 }; | 2129 }; |
2102 | 2130 |
2103 const char* statement_data[] = { | 2131 const char* statement_data[] = { |
2104 "mylabel: while(true) { break mylabel; }", | 2132 "mylabel: while(true) { break mylabel; }", |
2105 "eval: while(true) { break eval; }", | 2133 "eval: while(true) { break eval; }", |
2106 "arguments: while(true) { break arguments; }", | 2134 "arguments: while(true) { break arguments; }", |
2107 NULL | 2135 NULL |
2108 }; | 2136 }; |
2109 | 2137 |
2110 RunParserSyncTest(context_data, statement_data, kSuccess); | 2138 static const ParserFlag always_flags[] = {kAllowArrowFunctions}; |
| 2139 RunParserSyncTest(context_data, statement_data, kSuccess, NULL, 0, |
| 2140 always_flags, ARRAY_SIZE(always_flags)); |
2111 } | 2141 } |
2112 | 2142 |
2113 | 2143 |
2114 TEST(ErrorsParenthesizedLabels) { | 2144 TEST(ErrorsParenthesizedLabels) { |
2115 // Parenthesized identifiers shouldn't be recognized as labels. | 2145 // Parenthesized identifiers shouldn't be recognized as labels. |
2116 const char* context_data[][2] = { | 2146 const char* context_data[][2] = { |
2117 { "", ""}, | 2147 { "", ""}, |
2118 { "function test_func() {", "}" }, | 2148 { "function test_func() {", "}" }, |
| 2149 { "() => {", "}" }, |
2119 { NULL, NULL } | 2150 { NULL, NULL } |
2120 }; | 2151 }; |
2121 | 2152 |
2122 const char* statement_data[] = { | 2153 const char* statement_data[] = { |
2123 "(mylabel): while(true) { break mylabel; }", | 2154 "(mylabel): while(true) { break mylabel; }", |
2124 NULL | 2155 NULL |
2125 }; | 2156 }; |
2126 | 2157 |
2127 RunParserSyncTest(context_data, statement_data, kError); | 2158 RunParserSyncTest(context_data, statement_data, kError); |
2128 } | 2159 } |
(...skipping 820 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2949 LocalContext env; | 2980 LocalContext env; |
2950 int use_counts[v8::Isolate::kUseCounterFeatureCount] = {}; | 2981 int use_counts[v8::Isolate::kUseCounterFeatureCount] = {}; |
2951 global_use_counts = use_counts; | 2982 global_use_counts = use_counts; |
2952 CcTest::isolate()->SetUseCounterCallback(MockUseCounterCallback); | 2983 CcTest::isolate()->SetUseCounterCallback(MockUseCounterCallback); |
2953 CompileRun("\"use asm\";\n" | 2984 CompileRun("\"use asm\";\n" |
2954 "var foo = 1;\n" | 2985 "var foo = 1;\n" |
2955 "\"use asm\";\n" // Only the first one counts. | 2986 "\"use asm\";\n" // Only the first one counts. |
2956 "function bar() { \"use asm\"; var baz = 1; }"); | 2987 "function bar() { \"use asm\"; var baz = 1; }"); |
2957 CHECK_EQ(2, use_counts[v8::Isolate::kUseAsm]); | 2988 CHECK_EQ(2, use_counts[v8::Isolate::kUseAsm]); |
2958 } | 2989 } |
| 2990 |
| 2991 |
| 2992 TEST(ErrorsArrowFunctions) { |
| 2993 // Tests that parser and preparser generate the same kind of errors |
| 2994 // on invalid arrow function syntax. |
| 2995 const char* context_data[][2] = { |
| 2996 {"", ";"}, |
| 2997 {"v = ", ";"}, |
| 2998 {"bar ? (", ") : baz;"}, |
| 2999 {"bar ? baz : (", ");"}, |
| 3000 {"bar[", "];"}, |
| 3001 {"bar, ", ";"}, |
| 3002 {"", ", bar;"}, |
| 3003 {NULL, NULL} |
| 3004 }; |
| 3005 |
| 3006 const char* statement_data[] = { |
| 3007 "=> 0", |
| 3008 "=>", |
| 3009 "() =>", |
| 3010 "=> {}", |
| 3011 ") => {}", |
| 3012 ", => {}", |
| 3013 "(,) => {}", |
| 3014 "return => {}", |
| 3015 "() => {'value': 42}", |
| 3016 |
| 3017 // Check that the early return introduced in ParsePrimaryExpression |
| 3018 // does not accept stray closing parentheses. |
| 3019 ")", |
| 3020 ") => 0", |
| 3021 "foo[()]", |
| 3022 "()", |
| 3023 |
| 3024 // Parameter lists with extra parens should be recognized as errors. |
| 3025 "(()) => 0", |
| 3026 "((x)) => 0", |
| 3027 "((x, y)) => 0", |
| 3028 "(x, (y)) => 0", |
| 3029 "((x, y, z)) => 0", |
| 3030 "(x, (y, z)) => 0", |
| 3031 "((x, y), z) => 0", |
| 3032 |
| 3033 // Parameter lists are always validated as strict, so those are errors. |
| 3034 "eval => {}", |
| 3035 "arguments => {}", |
| 3036 "yield => {}", |
| 3037 "interface => {}", |
| 3038 "(eval) => {}", |
| 3039 "(arguments) => {}", |
| 3040 "(yield) => {}", |
| 3041 "(interface) => {}", |
| 3042 "(eval, bar) => {}", |
| 3043 "(bar, eval) => {}", |
| 3044 "(bar, arguments) => {}", |
| 3045 "(bar, yield) => {}", |
| 3046 "(bar, interface) => {}", |
| 3047 // TODO(aperez): Detecting duplicates does not work in PreParser. |
| 3048 // "(bar, bar) => {}", |
| 3049 |
| 3050 // The parameter list is parsed as an expression, but only |
| 3051 // a comma-separated list of identifier is valid. |
| 3052 "32 => {}", |
| 3053 "(32) => {}", |
| 3054 "(a, 32) => {}", |
| 3055 "if => {}", |
| 3056 "(if) => {}", |
| 3057 "(a, if) => {}", |
| 3058 "a + b => {}", |
| 3059 "(a + b) => {}", |
| 3060 "(a + b, c) => {}", |
| 3061 "(a, b - c) => {}", |
| 3062 "\"a\" => {}", |
| 3063 "(\"a\") => {}", |
| 3064 "(\"a\", b) => {}", |
| 3065 "(a, \"b\") => {}", |
| 3066 "-a => {}", |
| 3067 "(-a) => {}", |
| 3068 "(-a, b) => {}", |
| 3069 "(a, -b) => {}", |
| 3070 "{} => {}", |
| 3071 "({}) => {}", |
| 3072 "(a, {}) => {}", |
| 3073 "({}, a) => {}", |
| 3074 "a++ => {}", |
| 3075 "(a++) => {}", |
| 3076 "(a++, b) => {}", |
| 3077 "(a, b++) => {}", |
| 3078 "[] => {}", |
| 3079 "([]) => {}", |
| 3080 "(a, []) => {}", |
| 3081 "([], a) => {}", |
| 3082 "(a = b) => {}", |
| 3083 "(a = b, c) => {}", |
| 3084 "(a, b = c) => {}", |
| 3085 "(foo ? bar : baz) => {}", |
| 3086 "(a, foo ? bar : baz) => {}", |
| 3087 "(foo ? bar : baz, a) => {}", |
| 3088 NULL |
| 3089 }; |
| 3090 |
| 3091 RunParserSyncTest(context_data, statement_data, kError); |
| 3092 } |
| 3093 |
| 3094 |
| 3095 TEST(NoErrorsArrowFunctions) { |
| 3096 // Tests that parser and preparser accept valid arrow functions syntax. |
| 3097 const char* context_data[][2] = { |
| 3098 {"", ";"}, |
| 3099 {"bar ? (", ") : baz;"}, |
| 3100 {"bar ? baz : (", ");"}, |
| 3101 {"bar, ", ";"}, |
| 3102 {"", ", bar;"}, |
| 3103 {NULL, NULL} |
| 3104 }; |
| 3105 |
| 3106 const char* statement_data[] = { |
| 3107 "() => {}", |
| 3108 "() => { return 42 }", |
| 3109 "x => { return x; }", |
| 3110 "(x) => { return x; }", |
| 3111 "(x, y) => { return x + y; }", |
| 3112 "(x, y, z) => { return x + y + z; }", |
| 3113 "(x, y) => { x.a = y; }", |
| 3114 "() => 42", |
| 3115 "x => x", |
| 3116 "x => x * x", |
| 3117 "(x) => x", |
| 3118 "(x) => x * x", |
| 3119 "(x, y) => x + y", |
| 3120 "(x, y, z) => x, y, z", |
| 3121 "(x, y) => x.a = y", |
| 3122 "() => ({'value': 42})", |
| 3123 "x => y => x + y", |
| 3124 "(x, y) => (u, v) => x*u + y*v", |
| 3125 "(x, y) => z => z * (x + y)", |
| 3126 "x => (y, z) => z * (x + y)", |
| 3127 |
| 3128 // Those are comma-separated expressions, with arrow functions as items. |
| 3129 // They stress the code for validating arrow function parameter lists. |
| 3130 "a, b => 0", |
| 3131 "a, b, (c, d) => 0", |
| 3132 "(a, b, (c, d) => 0)", |
| 3133 "(a, b) => 0, (c, d) => 1", |
| 3134 "(a, b => {}, a => a + 1)", |
| 3135 "((a, b) => {}, (a => a + 1))", |
| 3136 "(a, (a, (b, c) => 0))", |
| 3137 |
| 3138 // Arrow has more precedence, this is the same as: foo ? bar : (baz = {}) |
| 3139 "foo ? bar : baz => {}", |
| 3140 NULL |
| 3141 }; |
| 3142 |
| 3143 static const ParserFlag always_flags[] = {kAllowArrowFunctions}; |
| 3144 RunParserSyncTest(context_data, statement_data, kSuccess, NULL, 0, |
| 3145 always_flags, ARRAY_SIZE(always_flags)); |
| 3146 } |
OLD | NEW |