From e179cf25405c5c5d4c329d1782d6e74c8e385669 Mon Sep 17 00:00:00 2001 From: davidot Date: Wed, 29 Dec 2021 12:15:29 +0100 Subject: [PATCH] LibJS: Don't VERIFY that the token after 'import' is one of '.' and '(' Although those are the only valid options parse_primary_expression is sometimes called when only an expression is valid which means it did not check match_expression and might fail the now removed VERIFY. --- Userland/Libraries/LibJS/Parser.cpp | 14 +++++++++----- .../LibJS/Tests/syntax/dynamic-import-usage.js | 18 ++++++++++++++++++ 2 files changed, 27 insertions(+), 5 deletions(-) create mode 100644 Userland/Libraries/LibJS/Tests/syntax/dynamic-import-usage.js diff --git a/Userland/Libraries/LibJS/Parser.cpp b/Userland/Libraries/LibJS/Parser.cpp index b785892cab..7132713aae 100644 --- a/Userland/Libraries/LibJS/Parser.cpp +++ b/Userland/Libraries/LibJS/Parser.cpp @@ -1425,14 +1425,18 @@ Parser::PrimaryExpressionParseResult Parser::parse_primary_expression() } case TokenType::Import: { auto lookahead_token = next_token(); - VERIFY(lookahead_token.type() == TokenType::Period || lookahead_token.type() == TokenType::ParenOpen); if (lookahead_token.type() == TokenType::ParenOpen) return { parse_import_call() }; - if (auto import_meta = try_parse_import_meta_expression()) { - if (m_program_type != Program::Type::Module) - syntax_error("import.meta is only allowed in modules"); - return { import_meta.release_nonnull() }; + if (lookahead_token.type() == TokenType::Period) { + if (auto import_meta = try_parse_import_meta_expression()) { + if (m_program_type != Program::Type::Module) + syntax_error("import.meta is only allowed in modules"); + return { import_meta.release_nonnull() }; + } + } else { + consume(); + expected("import.meta or import call"); } break; } diff --git a/Userland/Libraries/LibJS/Tests/syntax/dynamic-import-usage.js b/Userland/Libraries/LibJS/Tests/syntax/dynamic-import-usage.js new file mode 100644 index 0000000000..b396a7c878 --- /dev/null +++ b/Userland/Libraries/LibJS/Tests/syntax/dynamic-import-usage.js @@ -0,0 +1,18 @@ +describe("parsing", () => { + test("can parse call import call", () => { + expect("import('a')").toEval(); + expect("import('a', )").toEval(); + expect("import('a', {options: true})").toEval(); + }); + + test("does not crash on unexpected tokens after import", () => { + expect("f = import('a')").toEval(); + + expect("f= import").not.toEval(); + expect("f= import;").not.toEval(); + expect("f= import?").not.toEval(); + expect("f= import'").not.toEval(); + expect("f= import 'a'").not.toEval(); + expect("f= import['a']").not.toEval(); + }); +});