Title: [288473] trunk
Revision
288473
Author
[email protected]
Date
2022-01-24 14:51:13 -0800 (Mon, 24 Jan 2022)

Log Message

[JSC] Support import assertion syntax
https://bugs.webkit.org/show_bug.cgi?id=235312

Reviewed by Ross Kirsling.

JSTests:

* modules/import-meta-syntax.js:
(shouldThrow):
* stress/import-syntax.js:
* stress/modules-syntax-error.js:
* stress/modules-syntax-import-assertion-error.js: Added.
(shouldThrow):
* stress/modules-syntax-import-assertion.js: Added.

LayoutTests/imported/w3c:

* web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/css-module-worker-test-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/import-css-module-dynamic-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any.worker-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any.worker-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any.worker-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/json-module-service-worker-test.https-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any.worker-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any-expected.txt:
* web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any.worker-expected.txt:
* web-platform-tests/service-workers/service-worker/dedicated-worker-service-worker-interception.https-expected.txt:
* web-platform-tests/workers/dedicated-worker-parse-error-failure-expected.txt:
* web-platform-tests/workers/modules/dedicated-worker-options-credentials-expected.txt:

Source/_javascript_Core:

This patch adds syntax support for import assertion[1].
This does not add the actual feature propagating import assertion
to the module request yet.

[1]: https://github.com/tc39/proposal-import-assertions

* bytecompiler/NodesCodegen.cpp:
(JSC::ImportNode::emitBytecode):
* parser/ASTBuilder.h:
(JSC::ASTBuilder::createImportExpr):
(JSC::ASTBuilder::createImportAssertionList):
(JSC::ASTBuilder::appendImportAssertion):
(JSC::ASTBuilder::createImportDeclaration):
(JSC::ASTBuilder::createExportAllDeclaration):
(JSC::ASTBuilder::createExportNamedDeclaration):
* parser/NodeConstructors.h:
(JSC::ImportNode::ImportNode):
(JSC::ImportDeclarationNode::ImportDeclarationNode):
(JSC::ExportAllDeclarationNode::ExportAllDeclarationNode):
(JSC::ExportNamedDeclarationNode::ExportNamedDeclarationNode):
* parser/Nodes.h:
* parser/Parser.cpp:
(JSC::Parser<LexerType>::parseImportAssertions):
(JSC::Parser<LexerType>::parseImportDeclaration):
(JSC::Parser<LexerType>::parseExportDeclaration):
(JSC::Parser<LexerType>::parseMemberExpression):
* parser/Parser.h:
* parser/SyntaxChecker.h:
(JSC::SyntaxChecker::createImportExpr):
(JSC::SyntaxChecker::createImportAssertionList):
(JSC::SyntaxChecker::appendImportAssertion):
(JSC::SyntaxChecker::createImportDeclaration):
(JSC::SyntaxChecker::createExportAllDeclaration):
(JSC::SyntaxChecker::createExportNamedDeclaration):
* runtime/JSGlobalObjectFunctions.cpp:
(JSC::JSC_DEFINE_HOST_FUNCTION):
* runtime/OptionsList.h:

Modified Paths

Added Paths

Diff

Modified: trunk/JSTests/ChangeLog (288472 => 288473)


--- trunk/JSTests/ChangeLog	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/JSTests/ChangeLog	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,3 +1,18 @@
+2022-01-24  Yusuke Suzuki  <[email protected]>
+
+        [JSC] Support import assertion syntax
+        https://bugs.webkit.org/show_bug.cgi?id=235312
+
+        Reviewed by Ross Kirsling.
+
+        * modules/import-meta-syntax.js:
+        (shouldThrow):
+        * stress/import-syntax.js:
+        * stress/modules-syntax-error.js:
+        * stress/modules-syntax-import-assertion-error.js: Added.
+        (shouldThrow):
+        * stress/modules-syntax-import-assertion.js: Added.
+
 2022-01-21  Yusuke Suzuki  <[email protected]>
 
         [JSC] Relax Date.parse requirement

Modified: trunk/JSTests/modules/import-meta-syntax.js (288472 => 288473)


--- trunk/JSTests/modules/import-meta-syntax.js	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/JSTests/modules/import-meta-syntax.js	2022-01-24 22:51:13 UTC (rev 288473)
@@ -14,7 +14,7 @@
 
 shouldThrow(() => {
     checkModuleSyntax(`(import["Cocoa"])`);
-}, `SyntaxError: Unexpected token '['. import call expects exactly one argument.:1`);
+}, `SyntaxError: Unexpected token '['. import call expects one or two arguments.:1`);
 
 shouldThrow(() => {
     checkModuleSyntax(`import.cocoa`);

Modified: trunk/JSTests/stress/import-syntax.js (288472 => 288473)


--- trunk/JSTests/stress/import-syntax.js	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/JSTests/stress/import-syntax.js	2022-01-24 22:51:13 UTC (rev 288473)
@@ -27,27 +27,26 @@
     }
 }
 
-testSyntaxError(`import)`, `SyntaxError: Unexpected token ')'. import call expects exactly one argument.`);
+testSyntaxError(`import)`, `SyntaxError: Unexpected token ')'. import call expects one or two arguments.`);
 testSyntaxError(`new import(`, `SyntaxError: Cannot use new with import.`);
 testSyntaxError(`import.hello()`, `SyntaxError: Unexpected identifier 'hello'. "import." can only be followed with meta.`);
-testSyntaxError(`import[`, `SyntaxError: Unexpected token '['. import call expects exactly one argument.`);
-testSyntaxError(`import<`, `SyntaxError: Unexpected token '<'. import call expects exactly one argument.`);
+testSyntaxError(`import[`, `SyntaxError: Unexpected token '['. import call expects one or two arguments.`);
+testSyntaxError(`import<`, `SyntaxError: Unexpected token '<'. import call expects one or two arguments.`);
 
 testSyntaxError(`import()`, `SyntaxError: Unexpected token ')'`);
-testSyntaxError(`import(a, b)`, `SyntaxError: Unexpected token ','. import call expects exactly one argument.`);
-testSyntaxError(`import(a, b, c)`, `SyntaxError: Unexpected token ','. import call expects exactly one argument.`);
+testSyntaxError(`import(a, b, c)`, `SyntaxError: Unexpected identifier 'c'. import call expects one or two arguments.`);
 testSyntaxError(`import(...a)`, `SyntaxError: Unexpected token '...'`);
 testSyntaxError(`import(,a)`, `SyntaxError: Unexpected token ','`);
 testSyntaxError(`import(,)`, `SyntaxError: Unexpected token ','`);
-testSyntaxError(`import("Hello";`, `SyntaxError: Unexpected token ';'. import call expects exactly one argument.`);
-testSyntaxError(`import("Hello"];`, `SyntaxError: Unexpected token ']'. import call expects exactly one argument.`);
-testSyntaxError(`import("Hello",;`, `SyntaxError: Unexpected token ','. import call expects exactly one argument.`);
-testSyntaxError(`import("Hello", "Hello2";`, `SyntaxError: Unexpected token ','. import call expects exactly one argument.`);
+testSyntaxError(`import("Hello";`, `SyntaxError: Unexpected token ';'. import call expects one or two arguments.`);
+testSyntaxError(`import("Hello"];`, `SyntaxError: Unexpected token ']'. import call expects one or two arguments.`);
+testSyntaxError(`import("Hello",;`, `SyntaxError: Unexpected token ';'`);
+testSyntaxError(`import("Hello", "Hello2";`, `SyntaxError: Unexpected token ';'. import call expects one or two arguments.`);
 
 
-testSyntaxError(`import = 42`, `SyntaxError: Unexpected token '='. import call expects exactly one argument.`);
-testSyntaxError(`[import] = 42`, `SyntaxError: Unexpected token ']'. import call expects exactly one argument.`);
-testSyntaxError(`{import} = 42`, `SyntaxError: Unexpected token '}'. import call expects exactly one argument.`);
+testSyntaxError(`import = 42`, `SyntaxError: Unexpected token '='. import call expects one or two arguments.`);
+testSyntaxError(`[import] = 42`, `SyntaxError: Unexpected token ']'. import call expects one or two arguments.`);
+testSyntaxError(`{import} = 42`, `SyntaxError: Unexpected token '}'. import call expects one or two arguments.`);
 testSyntaxError(`let import = 42`, `SyntaxError: Unexpected keyword 'import'`);
 testSyntaxError(`var import = 42`, `SyntaxError: Cannot use the keyword 'import' as a variable name.`);
 testSyntaxError(`const import = 42`, `SyntaxError: Cannot use the keyword 'import' as a lexical variable name.`);

Modified: trunk/JSTests/stress/modules-syntax-error.js (288472 => 288473)


--- trunk/JSTests/stress/modules-syntax-error.js	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/JSTests/stress/modules-syntax-error.js	2022-01-24 22:51:13 UTC (rev 288473)
@@ -107,25 +107,25 @@
 function noTopLevel() {
     import * as from from "Cocoa"
 }
-`, `SyntaxError: Unexpected token '*'. import call expects exactly one argument.:3`);
+`, `SyntaxError: Unexpected token '*'. import call expects one or two arguments.:3`);
 
 checkModuleSyntaxError(String.raw`
 if (noTopLevel) {
     import * as from from "Cocoa"
 }
-`, `SyntaxError: Unexpected token '*'. import call expects exactly one argument.:3`);
+`, `SyntaxError: Unexpected token '*'. import call expects one or two arguments.:3`);
 
 checkModuleSyntaxError(String.raw`
 {
     import * as from from "Cocoa"
 }
-`, `SyntaxError: Unexpected token '*'. import call expects exactly one argument.:3`);
+`, `SyntaxError: Unexpected token '*'. import call expects one or two arguments.:3`);
 
 checkModuleSyntaxError(String.raw`
 for (var i = 0; i < 1000; ++i) {
     import * as from from "Cocoa"
 }
-`, `SyntaxError: Unexpected token '*'. import call expects exactly one argument.:3`);
+`, `SyntaxError: Unexpected token '*'. import call expects one or two arguments.:3`);
 
 checkModuleSyntaxError(String.raw`
 import for from "Cocoa";

Added: trunk/JSTests/stress/modules-syntax-import-assertion-error.js (0 => 288473)


--- trunk/JSTests/stress/modules-syntax-import-assertion-error.js	                        (rev 0)
+++ trunk/JSTests/stress/modules-syntax-import-assertion-error.js	2022-01-24 22:51:13 UTC (rev 288473)
@@ -0,0 +1,62 @@
+//@requireOptions("--useImportAssertion=true")
+
+function shouldThrow(func, errorMessage) {
+    var errorThrown = false;
+    var error = null;
+    try {
+        func();
+    } catch (e) {
+        errorThrown = true;
+        error = e;
+    }
+    if (!errorThrown)
+        throw new Error('not thrown');
+    if (errorMessage) {
+        if (String(error) !== errorMessage)
+            throw new Error(`bad error: ${String(error)}`);
+    }
+}
+
+function checkModuleSyntaxError(source, errorMessage) {
+    shouldThrow(() => checkModuleSyntax(source), errorMessage);
+}
+
+var list = [
+    String.raw`import v from "mod"`,
+    String.raw`import * as ns from "mod"`,
+    String.raw`import {x} from "mod"`,
+    String.raw`import {x,} from "mod"`,
+    String.raw`import {} from "mod"`,
+    String.raw`import {x as v} from "mod"`,
+    String.raw`export {x} from "mod"`,
+    String.raw`export {v as x} from "mod"`,
+    String.raw`export * from "mod"`,
+    String.raw`export * as b from "Cocoa"`,
+    String.raw`export * as delete from "Cocoa"`,
+    String.raw`import a, { b as c } from "Cocoa"`,
+    String.raw`import d, { e, f, g as h } from "Cappuccino"`,
+    String.raw`import { } from "Cappuccino"`,
+    String.raw`import i, * as j from "Cappuccino"`,
+    String.raw`import a, { } from "Cappuccino"`,
+    String.raw`import a, { b, } from "Cappuccino"`,
+    String.raw`import * as from from "Matcha"`,
+    String.raw`import * as as from "Cocoa"`,
+    String.raw`import { default as module } from "Cocoa"`,
+    String.raw`export * from "Cocoa"`,
+    String.raw`export { } from "Cocoa"`,
+    String.raw`export { a } from "Cocoa"`,
+    String.raw`export { a as b } from "Cocoa"`,
+    String.raw`export { a, b } from "Cocoa"`,
+    String.raw`export { default } from "Cocoa"`,
+    String.raw`export { enum } from "Cocoa"`,
+    String.raw`export { default as default } from "Cocoa"`,
+    String.raw`export { enum as enum } from "Cocoa"`,
+];
+
+for (let entry of list) {
+    checkModuleSyntaxError(entry + ` assert { , }`);
+    checkModuleSyntaxError(entry + ` assert { type: json }`);
+    checkModuleSyntaxError(entry + ` assert { type, }`);
+    checkModuleSyntaxError(entry + ` assert { type: "json",, }`);
+    checkModuleSyntaxError(entry + ` assert { `);
+}

Added: trunk/JSTests/stress/modules-syntax-import-assertion.js (0 => 288473)


--- trunk/JSTests/stress/modules-syntax-import-assertion.js	                        (rev 0)
+++ trunk/JSTests/stress/modules-syntax-import-assertion.js	2022-01-24 22:51:13 UTC (rev 288473)
@@ -0,0 +1,41 @@
+//@requireOptions("--useImportAssertion=true")
+
+var list = [
+    String.raw`import v from "mod"`,
+    String.raw`import * as ns from "mod"`,
+    String.raw`import {x} from "mod"`,
+    String.raw`import {x,} from "mod"`,
+    String.raw`import {} from "mod"`,
+    String.raw`import {x as v} from "mod"`,
+    String.raw`export {x} from "mod"`,
+    String.raw`export {v as x} from "mod"`,
+    String.raw`export * from "mod"`,
+    String.raw`export * as b from "Cocoa"`,
+    String.raw`export * as delete from "Cocoa"`,
+    String.raw`import a, { b as c } from "Cocoa"`,
+    String.raw`import d, { e, f, g as h } from "Cappuccino"`,
+    String.raw`import { } from "Cappuccino"`,
+    String.raw`import i, * as j from "Cappuccino"`,
+    String.raw`import a, { } from "Cappuccino"`,
+    String.raw`import a, { b, } from "Cappuccino"`,
+    String.raw`import * as from from "Matcha"`,
+    String.raw`import * as as from "Cocoa"`,
+    String.raw`import { default as module } from "Cocoa"`,
+    String.raw`export * from "Cocoa"`,
+    String.raw`export { } from "Cocoa"`,
+    String.raw`export { a } from "Cocoa"`,
+    String.raw`export { a as b } from "Cocoa"`,
+    String.raw`export { a, b } from "Cocoa"`,
+    String.raw`export { default } from "Cocoa"`,
+    String.raw`export { enum } from "Cocoa"`,
+    String.raw`export { default as default } from "Cocoa"`,
+    String.raw`export { enum as enum } from "Cocoa"`,
+];
+
+for (let entry of list) {
+    checkModuleSyntax(entry + ` assert { }`);
+    checkModuleSyntax(entry + ` assert { type: "json" }`);
+    checkModuleSyntax(entry + ` assert { "type": "json" }`);
+    checkModuleSyntax(entry + ` assert { "type": "json", }`);
+    checkModuleSyntax(entry + ` assert { type: "json", hello: "world" }`);
+}

Modified: trunk/LayoutTests/imported/w3c/ChangeLog (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/ChangeLog	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/ChangeLog	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,3 +1,27 @@
+2022-01-24  Yusuke Suzuki  <[email protected]>
+
+        [JSC] Support import assertion syntax
+        https://bugs.webkit.org/show_bug.cgi?id=235312
+
+        Reviewed by Ross Kirsling.
+
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/css-module-worker-test-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/import-css-module-dynamic-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any.worker-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any.worker-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any.worker-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/json-module-service-worker-test.https-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any.worker-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any-expected.txt:
+        * web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any.worker-expected.txt:
+        * web-platform-tests/service-workers/service-worker/dedicated-worker-service-worker-interception.https-expected.txt:
+        * web-platform-tests/workers/dedicated-worker-parse-error-failure-expected.txt:
+        * web-platform-tests/workers/modules/dedicated-worker-options-credentials-expected.txt:
+
 2022-01-24  Antti Koivisto  <[email protected]>
 
         [CSS Container Queries] Basic parsing support for container-type property

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/css-module-worker-test-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/css-module-worker-test-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/css-module-worker-test-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,5 @@
 
-PASS A static import CSS Module within a web worker should not load.
-PASS A dynamic import CSS Module within a web worker should not load.
-PASS A CSS Module within a web worker should not load.
+PASS A static import CSS Module within a web worker should not load and should not attempt to fetch the module.
+FAIL A dynamic import CSS Module within a web worker should not load and should not attempt to fetch the module. assert_equals: Shouldn't have tried fetching CSS module in worker expected 0 but got 1
+PASS An attempt to load a CSS module as a worker should fail.
 

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/import-css-module-dynamic-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/import-css-module-dynamic-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/css-module/import-css-module-dynamic-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,4 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+FAIL Load a CSS module with dynamic import() promise_test: Unhandled rejection with value: object "TypeError: 'text/css' is not a valid _javascript_ MIME type."
+PASS Ensure that loading a CSS module with dymnamic import() fails without a type assertion
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,5 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+PASS Dynamic import with an empty assert clause should succeed
+PASS Dynamic import with an unsupported import assertion should succeed
+FAIL Dynamic import with an unsupported type assertion should fail assert_unreached: Should have rejected: Dynamic import with an unsupported type assertion should fail Reached unreachable code
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any.worker-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any.worker-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/import-assertions/dynamic-import-with-assertion-argument.any.worker-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,5 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+PASS Dynamic import with an empty assert clause should succeed
+PASS Dynamic import with an unsupported import assertion should succeed
+FAIL Dynamic import with an unsupported type assertion should fail assert_unreached: Should have rejected: Dynamic import with an unsupported type assertion should fail Reached unreachable code
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,9 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+FAIL UTF-8 BOM should be stripped when decoding JSON module script promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL UTF-16BE BOM should result in parse error in JSON module script promise_rejects_js: Expected parse error from UTF-16BE BOM function "function () { throw e }" threw object "TypeError: 'application/json' is not a valid _javascript_ MIME type." ("TypeError") expected instance of function "function SyntaxError() {
+    [native code]
+}" ("SyntaxError")
+FAIL UTF-16LE BOM should result in parse error in JSON module script promise_rejects_js: Expected parse error from UTF-16LE BOM function "function () { throw e }" threw object "TypeError: 'application/json' is not a valid _javascript_ MIME type." ("TypeError") expected instance of function "function SyntaxError() {
+    [native code]
+}" ("SyntaxError")
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any.worker-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any.worker-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/charset-bom.any.worker-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,9 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+FAIL UTF-8 BOM should be stripped when decoding JSON module script promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL UTF-16BE BOM should result in parse error in JSON module script promise_rejects_js: Expected parse error from UTF-16BE BOM function "function () { throw e }" threw object "TypeError: 'application/json' is not a valid _javascript_ MIME type." ("TypeError") expected instance of function "function SyntaxError() {
+    [native code]
+}" ("SyntaxError")
+FAIL UTF-16LE BOM should result in parse error in JSON module script promise_rejects_js: Expected parse error from UTF-16LE BOM function "function () { throw e }" threw object "TypeError: 'application/json' is not a valid _javascript_ MIME type." ("TypeError") expected instance of function "function SyntaxError() {
+    [native code]
+}" ("SyntaxError")
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,8 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+PASS Try importing JSON module with MIME type application/json+protobuf
+PASS Try importing JSON module with MIME type application/json+blah
+PASS Try importing JSON module with MIME type text/x-json
+PASS Try importing JSON module with MIME type text/json+blah
+PASS Try importing JSON module with MIME type application/blahjson
+PASS Try importing JSON module with MIME type image/json
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any.worker-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any.worker-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/invalid-content-type.any.worker-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,8 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+PASS Try importing JSON module with MIME type application/json+protobuf
+PASS Try importing JSON module with MIME type application/json+blah
+PASS Try importing JSON module with MIME type text/x-json
+PASS Try importing JSON module with MIME type text/json+blah
+PASS Try importing JSON module with MIME type application/blahjson
+PASS Try importing JSON module with MIME type image/json
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/json-module-service-worker-test.https-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/json-module-service-worker-test.https-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/json-module-service-worker-test.https-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,5 @@
 
 FAIL _javascript_ importing JSON Module should load within the context of a service worker promise_test: Unhandled rejection with value: object "TypeError: SyntaxError: Unexpected identifier 'assert'. Expected a ';' following a targeted import declaration."
 PASS Trying to register a service worker with a top-level JSON Module should fail
-FAIL JSON Module dynamic import should not load within the context of a service worker promise_test: Unhandled rejection with value: object "TypeError: SyntaxError: Unexpected token ','. import call expects exactly one argument."
+PASS JSON Module dynamic import should not load within the context of a service worker
 

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,7 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+FAIL Non-object: null promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: true promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: false promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: string promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: array promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any.worker-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any.worker-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/non-object.any.worker-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,7 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+FAIL Non-object: null promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: true promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: false promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: string promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Non-object: array promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,7 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+FAIL Importing a specifier that previously failed due to an incorrect type assertion can succeed if the correct assertion is later given promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Importing a specifier that previously succeeded with the correct type assertion should fail if the incorrect assertion is later given promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Two modules of different type with the same specifier can load if the server changes its responses promise_test: Unhandled rejection with value: object "TypeError: 'text/json' is not a valid _javascript_ MIME type."
+FAIL An import should always fail if the same specifier/type assertion pair failed previously assert_unreached: Should have rejected: import should always fail if the same specifier/type assertion pair failed previously Reached unreachable code
+FAIL If an import previously succeeded for a given specifier/type assertion pair, future uses of that pair should yield the same result promise_test: Unhandled rejection with value: object "TypeError: 'text/json' is not a valid _javascript_ MIME type."
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any.worker-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any.worker-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/html/semantics/scripting-1/the-script-element/json-module/repeated-imports.any.worker-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,7 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected token ','. import call expects exactly one argument.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected token ','. import call expects exactly one argument.
+FAIL Importing a specifier that previously failed due to an incorrect type assertion can succeed if the correct assertion is later given promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Importing a specifier that previously succeeded with the correct type assertion should fail if the incorrect assertion is later given promise_test: Unhandled rejection with value: object "TypeError: 'application/json' is not a valid _javascript_ MIME type."
+FAIL Two modules of different type with the same specifier can load if the server changes its responses promise_test: Unhandled rejection with value: object "TypeError: 'text/json' is not a valid _javascript_ MIME type."
+FAIL An import should always fail if the same specifier/type assertion pair failed previously assert_unreached: Should have rejected: import should always fail if the same specifier/type assertion pair failed previously Reached unreachable code
+FAIL If an import previously succeeded for a given specifier/type assertion pair, future uses of that pair should yield the same result promise_test: Unhandled rejection with value: object "TypeError: 'text/json' is not a valid _javascript_ MIME type."
 
-

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/service-workers/service-worker/dedicated-worker-service-worker-interception.https-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/service-workers/service-worker/dedicated-worker-service-worker-interception.https-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/service-workers/service-worker/dedicated-worker-service-worker-interception.https-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,5 @@
 
-Harness Error (FAIL), message = SyntaxError: Unexpected string literal './service-worker-interception-network-worker.js'. import call expects exactly one argument.
+Harness Error (FAIL), message = SyntaxError: Unexpected string literal './service-worker-interception-network-worker.js'. import call expects one or two arguments.
 
 FAIL Top-level module loading should be intercepted by a service worker. assert_equals: expected "LOADED_FROM_SERVICE_WORKER" but got "LOADED_FROM_NETWORK"
 TIMEOUT Static import should be intercepted by a service worker. Test timed out

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/workers/dedicated-worker-parse-error-failure-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/workers/dedicated-worker-parse-error-failure-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/workers/dedicated-worker-parse-error-failure-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,5 +1,5 @@
 CONSOLE MESSAGE: SyntaxError: Unexpected token ';'
-CONSOLE MESSAGE: SyntaxError: Unexpected token '*'. import call expects exactly one argument.
+CONSOLE MESSAGE: SyntaxError: Unexpected token '*'. import call expects one or two arguments.
 
 FAIL Classic worker construction for script with syntax error should dispatch an event named error. assert_equals: expected function "function Event() {
     [native code]

Modified: trunk/LayoutTests/imported/w3c/web-platform-tests/workers/modules/dedicated-worker-options-credentials-expected.txt (288472 => 288473)


--- trunk/LayoutTests/imported/w3c/web-platform-tests/workers/modules/dedicated-worker-options-credentials-expected.txt	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/LayoutTests/imported/w3c/web-platform-tests/workers/modules/dedicated-worker-options-credentials-expected.txt	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,6 +1,6 @@
-CONSOLE MESSAGE: SyntaxError: Unexpected string literal './credentials.py'. import call expects exactly one argument.
+CONSOLE MESSAGE: SyntaxError: Unexpected string literal './credentials.py'. import call expects one or two arguments.
 
-Harness Error (FAIL), message = SyntaxError: Unexpected string literal './credentials.py'. import call expects exactly one argument.
+Harness Error (FAIL), message = SyntaxError: Unexpected string literal './credentials.py'. import call expects one or two arguments.
 
 PASS Test initialization: setting up cross-origin cookie
 PASS new Worker() with type=module and default credentials option should behave as credentials=same-origin and send the credentials

Modified: trunk/Source/_javascript_Core/ChangeLog (288472 => 288473)


--- trunk/Source/_javascript_Core/ChangeLog	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/ChangeLog	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1,3 +1,48 @@
+2022-01-24  Yusuke Suzuki  <[email protected]>
+
+        [JSC] Support import assertion syntax
+        https://bugs.webkit.org/show_bug.cgi?id=235312
+
+        Reviewed by Ross Kirsling.
+
+        This patch adds syntax support for import assertion[1].
+        This does not add the actual feature propagating import assertion
+        to the module request yet.
+
+        [1]: https://github.com/tc39/proposal-import-assertions
+
+        * bytecompiler/NodesCodegen.cpp:
+        (JSC::ImportNode::emitBytecode):
+        * parser/ASTBuilder.h:
+        (JSC::ASTBuilder::createImportExpr):
+        (JSC::ASTBuilder::createImportAssertionList):
+        (JSC::ASTBuilder::appendImportAssertion):
+        (JSC::ASTBuilder::createImportDeclaration):
+        (JSC::ASTBuilder::createExportAllDeclaration):
+        (JSC::ASTBuilder::createExportNamedDeclaration):
+        * parser/NodeConstructors.h:
+        (JSC::ImportNode::ImportNode):
+        (JSC::ImportDeclarationNode::ImportDeclarationNode):
+        (JSC::ExportAllDeclarationNode::ExportAllDeclarationNode):
+        (JSC::ExportNamedDeclarationNode::ExportNamedDeclarationNode):
+        * parser/Nodes.h:
+        * parser/Parser.cpp:
+        (JSC::Parser<LexerType>::parseImportAssertions):
+        (JSC::Parser<LexerType>::parseImportDeclaration):
+        (JSC::Parser<LexerType>::parseExportDeclaration):
+        (JSC::Parser<LexerType>::parseMemberExpression):
+        * parser/Parser.h:
+        * parser/SyntaxChecker.h:
+        (JSC::SyntaxChecker::createImportExpr):
+        (JSC::SyntaxChecker::createImportAssertionList):
+        (JSC::SyntaxChecker::appendImportAssertion):
+        (JSC::SyntaxChecker::createImportDeclaration):
+        (JSC::SyntaxChecker::createExportAllDeclaration):
+        (JSC::SyntaxChecker::createExportNamedDeclaration):
+        * runtime/JSGlobalObjectFunctions.cpp:
+        (JSC::JSC_DEFINE_HOST_FUNCTION):
+        * runtime/OptionsList.h:
+
 2022-01-24  Mark Lam  <[email protected]>
 
         Add FixedVector::clear(), contains(), find(), and findMatching().

Modified: trunk/Source/_javascript_Core/bytecompiler/NodesCodegen.cpp (288472 => 288473)


--- trunk/Source/_javascript_Core/bytecompiler/NodesCodegen.cpp	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/bytecompiler/NodesCodegen.cpp	2022-01-24 22:51:13 UTC (rev 288473)
@@ -224,9 +224,11 @@
 RegisterID* ImportNode::emitBytecode(BytecodeGenerator& generator, RegisterID* dst)
 {
     RefPtr<RegisterID> importModule = generator.moveLinkTimeConstant(nullptr, LinkTimeConstant::importModule);
-    CallArguments arguments(generator, nullptr, 1);
+    CallArguments arguments(generator, nullptr, m_option ? 2 : 1);
     generator.emitLoad(arguments.thisRegister(), jsUndefined());
     generator.emitNode(arguments.argumentRegister(0), m_expr);
+    if (m_option)
+        generator.emitNode(arguments.argumentRegister(1), m_option);
     return generator.emitCall(generator.finalDestination(dst, importModule.get()), importModule.get(), NoExpectedFunction, arguments, divot(), divotStart(), divotEnd(), DebuggableCall::No);
 }
 

Modified: trunk/Source/_javascript_Core/parser/ASTBuilder.h (288472 => 288473)


--- trunk/Source/_javascript_Core/parser/ASTBuilder.h	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/parser/ASTBuilder.h	2022-01-24 22:51:13 UTC (rev 288473)
@@ -111,6 +111,7 @@
     typedef ModuleNameNode* ModuleName;
     typedef ImportSpecifierNode* ImportSpecifier;
     typedef ImportSpecifierListNode* ImportSpecifierList;
+    typedef ImportAssertionListNode* ImportAssertionList;
     typedef ExportSpecifierNode* ExportSpecifier;
     typedef ExportSpecifierListNode* ExportSpecifierList;
     typedef StatementNode* Statement;
@@ -179,9 +180,9 @@
     {
         return new (m_parserArena) SuperNode(location);
     }
-    ExpressionNode* createImportExpr(const JSTokenLocation& location, ExpressionNode* expr, const JSTextPosition& start, const JSTextPosition& divot, const JSTextPosition& end)
+    ExpressionNode* createImportExpr(const JSTokenLocation& location, ExpressionNode* expr, ExpressionNode* option, const JSTextPosition& start, const JSTextPosition& divot, const JSTextPosition& end)
     {
-        auto* node = new (m_parserArena) ImportNode(location, expr);
+        auto* node = new (m_parserArena) ImportNode(location, expr, option);
         setExceptionLocation(node, start, divot, end);
         return node;
     }
@@ -811,16 +812,26 @@
         specifierList->append(specifier);
     }
 
-    StatementNode* createImportDeclaration(const JSTokenLocation& location, ImportSpecifierListNode* importSpecifierList, ModuleNameNode* moduleName)
+    ImportAssertionListNode* createImportAssertionList()
     {
-        return new (m_parserArena) ImportDeclarationNode(location, importSpecifierList, moduleName);
+        return new (m_parserArena) ImportAssertionListNode();
     }
 
-    StatementNode* createExportAllDeclaration(const JSTokenLocation& location, ModuleNameNode* moduleName)
+    void appendImportAssertion(ImportAssertionListNode* assertionList, const Identifier& key, const Identifier& value)
     {
-        return new (m_parserArena) ExportAllDeclarationNode(location, moduleName);
+        assertionList->append(key, value);
     }
 
+    StatementNode* createImportDeclaration(const JSTokenLocation& location, ImportSpecifierListNode* importSpecifierList, ModuleNameNode* moduleName, ImportAssertionListNode* importAssertionList)
+    {
+        return new (m_parserArena) ImportDeclarationNode(location, importSpecifierList, moduleName, importAssertionList);
+    }
+
+    StatementNode* createExportAllDeclaration(const JSTokenLocation& location, ModuleNameNode* moduleName, ImportAssertionListNode* importAssertionList)
+    {
+        return new (m_parserArena) ExportAllDeclarationNode(location, moduleName, importAssertionList);
+    }
+
     StatementNode* createExportDefaultDeclaration(const JSTokenLocation& location, StatementNode* declaration, const Identifier& localName)
     {
         return new (m_parserArena) ExportDefaultDeclarationNode(location, declaration, localName);
@@ -831,9 +842,9 @@
         return new (m_parserArena) ExportLocalDeclarationNode(location, declaration);
     }
 
-    StatementNode* createExportNamedDeclaration(const JSTokenLocation& location, ExportSpecifierListNode* exportSpecifierList, ModuleNameNode* moduleName)
+    StatementNode* createExportNamedDeclaration(const JSTokenLocation& location, ExportSpecifierListNode* exportSpecifierList, ModuleNameNode* moduleName, ImportAssertionListNode* importAssertionList)
     {
-        return new (m_parserArena) ExportNamedDeclarationNode(location, exportSpecifierList, moduleName);
+        return new (m_parserArena) ExportNamedDeclarationNode(location, exportSpecifierList, moduleName, importAssertionList);
     }
 
     ExportSpecifierNode* createExportSpecifier(const JSTokenLocation& location, const Identifier& localName, const Identifier& exportedName)

Modified: trunk/Source/_javascript_Core/parser/NodeConstructors.h (288472 => 288473)


--- trunk/Source/_javascript_Core/parser/NodeConstructors.h	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/parser/NodeConstructors.h	2022-01-24 22:51:13 UTC (rev 288473)
@@ -179,9 +179,10 @@
     {
     }
 
-    inline ImportNode::ImportNode(const JSTokenLocation& location, ExpressionNode* expr)
+    inline ImportNode::ImportNode(const JSTokenLocation& location, ExpressionNode* expr, ExpressionNode* option)
         : ExpressionNode(location)
         , m_expr(expr)
+        , m_option(option)
     {
     }
 
@@ -865,16 +866,18 @@
     {
     }
 
-    inline ImportDeclarationNode::ImportDeclarationNode(const JSTokenLocation& location, ImportSpecifierListNode* importSpecifierList, ModuleNameNode* moduleName)
+    inline ImportDeclarationNode::ImportDeclarationNode(const JSTokenLocation& location, ImportSpecifierListNode* importSpecifierList, ModuleNameNode* moduleName, ImportAssertionListNode* importAssertionList)
         : ModuleDeclarationNode(location)
         , m_specifierList(importSpecifierList)
         , m_moduleName(moduleName)
+        , m_assertionList(importAssertionList)
     {
     }
 
-    inline ExportAllDeclarationNode::ExportAllDeclarationNode(const JSTokenLocation& location, ModuleNameNode* moduleName)
+    inline ExportAllDeclarationNode::ExportAllDeclarationNode(const JSTokenLocation& location, ModuleNameNode* moduleName, ImportAssertionListNode* importAssertionList)
         : ModuleDeclarationNode(location)
         , m_moduleName(moduleName)
+        , m_assertionList(importAssertionList)
     {
     }
 
@@ -891,10 +894,11 @@
     {
     }
 
-    inline ExportNamedDeclarationNode::ExportNamedDeclarationNode(const JSTokenLocation& location, ExportSpecifierListNode* exportSpecifierList, ModuleNameNode* moduleName)
+    inline ExportNamedDeclarationNode::ExportNamedDeclarationNode(const JSTokenLocation& location, ExportSpecifierListNode* exportSpecifierList, ModuleNameNode* moduleName, ImportAssertionListNode* importAssertionList)
         : ModuleDeclarationNode(location)
         , m_specifierList(exportSpecifierList)
         , m_moduleName(moduleName)
+        , m_assertionList(importAssertionList)
     {
     }
 

Modified: trunk/Source/_javascript_Core/parser/Nodes.h (288472 => 288473)


--- trunk/Source/_javascript_Core/parser/Nodes.h	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/parser/Nodes.h	2022-01-24 22:51:13 UTC (rev 288473)
@@ -627,7 +627,7 @@
 
     class ImportNode final : public ExpressionNode, public ThrowableExpressionData {
     public:
-        ImportNode(const JSTokenLocation&, ExpressionNode*);
+        ImportNode(const JSTokenLocation&, ExpressionNode*, ExpressionNode*);
 
     private:
         bool isImportNode() const final { return true; }
@@ -634,6 +634,7 @@
         RegisterID* emitBytecode(BytecodeGenerator&, RegisterID* = nullptr) final;
 
         ExpressionNode* m_expr;
+        ExpressionNode* m_option;
     };
 
     class MetaPropertyNode : public ExpressionNode {
@@ -2057,6 +2058,21 @@
         Specifiers m_specifiers;
     };
 
+    class ImportAssertionListNode final : public ParserArenaDeletable {
+        JSC_MAKE_PARSER_ARENA_DELETABLE_ALLOCATED(ImportAssertionListNode);
+    public:
+        using Assertions = Vector<std::tuple<const Identifier*, const Identifier*>, 3>;
+
+        const Assertions& assertions() const { return m_assertions; }
+        void append(const Identifier& key, const Identifier& value)
+        {
+            m_assertions.append(std::tuple { &key, &value });
+        }
+
+    private:
+        Assertions m_assertions;
+    };
+
     class ModuleDeclarationNode : public StatementNode {
     public:
         virtual void analyzeModule(ModuleAnalyzer&) = 0;
@@ -2069,10 +2085,11 @@
 
     class ImportDeclarationNode final : public ModuleDeclarationNode {
     public:
-        ImportDeclarationNode(const JSTokenLocation&, ImportSpecifierListNode*, ModuleNameNode*);
+        ImportDeclarationNode(const JSTokenLocation&, ImportSpecifierListNode*, ModuleNameNode*, ImportAssertionListNode*);
 
         ImportSpecifierListNode* specifierList() const { return m_specifierList; }
         ModuleNameNode* moduleName() const { return m_moduleName; }
+        ImportAssertionListNode* assertionList() const { return m_assertionList; }
 
     private:
         void emitBytecode(BytecodeGenerator&, RegisterID* = nullptr) final;
@@ -2080,13 +2097,15 @@
 
         ImportSpecifierListNode* m_specifierList;
         ModuleNameNode* m_moduleName;
+        ImportAssertionListNode* m_assertionList;
     };
 
     class ExportAllDeclarationNode final : public ModuleDeclarationNode {
     public:
-        ExportAllDeclarationNode(const JSTokenLocation&, ModuleNameNode*);
+        ExportAllDeclarationNode(const JSTokenLocation&, ModuleNameNode*, ImportAssertionListNode*);
 
         ModuleNameNode* moduleName() const { return m_moduleName; }
+        ImportAssertionListNode* assertionList() const { return m_assertionList; }
 
     private:
         void emitBytecode(BytecodeGenerator&, RegisterID* = nullptr) final;
@@ -2093,6 +2112,7 @@
         void analyzeModule(ModuleAnalyzer&) final;
 
         ModuleNameNode* m_moduleName;
+        ImportAssertionListNode* m_assertionList;
     };
 
     class ExportDefaultDeclarationNode final : public ModuleDeclarationNode {
@@ -2150,10 +2170,11 @@
 
     class ExportNamedDeclarationNode final : public ModuleDeclarationNode {
     public:
-        ExportNamedDeclarationNode(const JSTokenLocation&, ExportSpecifierListNode*, ModuleNameNode*);
+        ExportNamedDeclarationNode(const JSTokenLocation&, ExportSpecifierListNode*, ModuleNameNode*, ImportAssertionListNode*);
 
         ExportSpecifierListNode* specifierList() const { return m_specifierList; }
         ModuleNameNode* moduleName() const { return m_moduleName; }
+        ImportAssertionListNode* assertionList() const { return m_assertionList; }
 
     private:
         void emitBytecode(BytecodeGenerator&, RegisterID* = nullptr) final;
@@ -2160,6 +2181,7 @@
         void analyzeModule(ModuleAnalyzer&) final;
         ExportSpecifierListNode* m_specifierList;
         ModuleNameNode* m_moduleName { nullptr };
+        ImportAssertionListNode* m_assertionList { nullptr };
     };
 
     class FunctionMetadataNode final : public ParserArenaDeletable, public Node {

Modified: trunk/Source/_javascript_Core/parser/Parser.cpp (288472 => 288473)


--- trunk/Source/_javascript_Core/parser/Parser.cpp	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/parser/Parser.cpp	2022-01-24 22:51:13 UTC (rev 288473)
@@ -3576,6 +3576,27 @@
 }
 
 template <typename LexerType>
+template <class TreeBuilder> typename TreeBuilder::ImportAssertionList Parser<LexerType>::parseImportAssertions(TreeBuilder& context)
+{
+    auto assertionList = context.createImportAssertionList();
+    consumeOrFail(OPENBRACE, "Expected opening '{' at the start of import assertion");
+    while (!match(CLOSEBRACE)) {
+        failIfFalse(matchIdentifierOrKeyword() || match(STRING), "Expected an assertion key");
+        auto key = m_token.m_data.ident;
+        next();
+        consumeOrFail(COLON, "Expected ':' after assertion key");
+        failIfFalse(match(STRING), "Expected an assertion value");
+        auto value = m_token.m_data.ident;
+        next();
+        context.appendImportAssertion(assertionList, *key, *value);
+        if (!consume(COMMA))
+            break;
+    }
+    handleProductionOrFail2(CLOSEBRACE, "}", "end", "import assertion");
+    return assertionList;
+}
+
+template <typename LexerType>
 template <class TreeBuilder> TreeStatement Parser<LexerType>::parseImportDeclaration(TreeBuilder& context)
 {
     // http://www.ecma-international.org/ecma-262/6.0/#sec-imports
@@ -3587,10 +3608,19 @@
 
     if (match(STRING)) {
         // import ModuleSpecifier ;
+        // import ModuleSpecifier [no LineTerminator here] AssertClause ;
         auto moduleName = parseModuleName(context);
         failIfFalse(moduleName, "Cannot parse the module name");
+
+        typename TreeBuilder::ImportAssertionList assertionList = 0;
+        if (Options::useImportAssertion() && !m_lexer->hasLineTerminatorBeforeToken() && matchContextualKeyword(m_vm.propertyNames->builtinNames().assertPublicName())) {
+            next();
+            assertionList = parseImportAssertions(context);
+            failIfFalse(assertionList, "Unable to parse import assertion");
+        }
+
         failIfFalse(autoSemiColon(), "Expected a ';' following a targeted import declaration");
-        return context.createImportDeclaration(importLocation, specifierList, moduleName);
+        return context.createImportDeclaration(importLocation, specifierList, moduleName, assertionList);
     }
 
     bool isFinishedParsingImport = false;
@@ -3640,9 +3670,18 @@
 
     auto moduleName = parseModuleName(context);
     failIfFalse(moduleName, "Cannot parse the module name");
+
+    // [no LineTerminator here] AssertClause ;
+    typename TreeBuilder::ImportAssertionList assertionList = 0;
+    if (Options::useImportAssertion() && !m_lexer->hasLineTerminatorBeforeToken() && matchContextualKeyword(m_vm.propertyNames->builtinNames().assertPublicName())) {
+        next();
+        assertionList = parseImportAssertions(context);
+        failIfFalse(assertionList, "Unable to parse import assertion");
+    }
+
     failIfFalse(autoSemiColon(), "Expected a ';' following a targeted import declaration");
 
-    return context.createImportDeclaration(importLocation, specifierList, moduleName);
+    return context.createImportDeclaration(importLocation, specifierList, moduleName, assertionList);
 }
 
 template <typename LexerType>
@@ -3714,6 +3753,15 @@
         next();
         auto moduleName = parseModuleName(context);
         failIfFalse(moduleName, "Cannot parse the 'from' clause");
+
+        // [no LineTerminator here] AssertClause ;
+        typename TreeBuilder::ImportAssertionList assertionList = 0;
+        if (Options::useImportAssertion() && !m_lexer->hasLineTerminatorBeforeToken() && matchContextualKeyword(m_vm.propertyNames->builtinNames().assertPublicName())) {
+            next();
+            assertionList = parseImportAssertions(context);
+            failIfFalse(assertionList, "Unable to parse import assertion");
+        }
+
         failIfFalse(autoSemiColon(), "Expected a ';' following a targeted export declaration");
 
         if (exportedName) {
@@ -3722,10 +3770,10 @@
             auto localName = &m_vm.propertyNames->starNamespacePrivateName;
             auto specifier = context.createExportSpecifier(specifierLocation, *localName, *exportedName);
             context.appendExportSpecifier(specifierList, specifier);
-            return context.createExportNamedDeclaration(exportLocation, specifierList, moduleName);
+            return context.createExportNamedDeclaration(exportLocation, specifierList, moduleName, assertionList);
         }
 
-        return context.createExportAllDeclaration(exportLocation, moduleName);
+        return context.createExportAllDeclaration(exportLocation, moduleName, assertionList);
     }
 
     case DEFAULT: {
@@ -3847,10 +3895,18 @@
         handleProductionOrFail2(CLOSEBRACE, "}", "end", "export list");
 
         typename TreeBuilder::ModuleName moduleName = 0;
+        typename TreeBuilder::ImportAssertionList assertionList = 0;
         if (matchContextualKeyword(m_vm.propertyNames->from)) {
             next();
             moduleName = parseModuleName(context);
             failIfFalse(moduleName, "Cannot parse the 'from' clause");
+
+            // [no LineTerminator here] AssertClause ;
+            if (Options::useImportAssertion() && !m_lexer->hasLineTerminatorBeforeToken() && matchContextualKeyword(m_vm.propertyNames->builtinNames().assertPublicName())) {
+                next();
+                assertionList = parseImportAssertions(context);
+                failIfFalse(assertionList, "Unable to parse import assertion");
+            }
         } else
             semanticFailIfTrue(hasReferencedModuleExportNames, "Cannot use module export names if they reference variable names in the current module");
         failIfFalse(autoSemiColon(), "Expected a ';' following a targeted export declaration");
@@ -3872,7 +3928,7 @@
             }
         }
 
-        return context.createExportNamedDeclaration(exportLocation, specifierList, moduleName);
+        return context.createExportNamedDeclaration(exportLocation, specifierList, moduleName, assertionList);
     }
 
     default: {
@@ -5136,11 +5192,19 @@
             }
         } else {
             semanticFailIfTrue(newCount, "Cannot use new with import");
-            consumeOrFail(OPENPAREN, "import call expects exactly one argument");
+            consumeOrFail(OPENPAREN, "import call expects one or two arguments");
             TreeExpression expr = parseAssignmentExpression(context);
             failIfFalse(expr, "Cannot parse _expression_");
-            consumeOrFail(CLOSEPAREN, "import call expects exactly one argument");
-            base = context.createImportExpr(location, expr, expressionStart, expressionEnd, lastTokenEndPosition());
+            TreeExpression optionExpression = 0;
+            if (consume(COMMA)) {
+                if (!match(CLOSEPAREN)) {
+                    optionExpression = parseAssignmentExpression(context);
+                    failIfFalse(optionExpression, "Cannot parse _expression_");
+                    consume(COMMA);
+                }
+            }
+            consumeOrFail(CLOSEPAREN, "import call expects one or two arguments");
+            base = context.createImportExpr(location, expr, optionExpression, expressionStart, expressionEnd, lastTokenEndPosition());
         }
     } else if (!baseIsNewTarget) {
         const bool isAsync = matchContextualKeyword(m_vm.propertyNames->async);

Modified: trunk/Source/_javascript_Core/parser/Parser.h (288472 => 288473)


--- trunk/Source/_javascript_Core/parser/Parser.h	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/parser/Parser.h	2022-01-24 22:51:13 UTC (rev 288473)
@@ -1784,6 +1784,7 @@
     enum class ImportSpecifierType { NamespaceImport, NamedImport, DefaultImport };
     template <class TreeBuilder> typename TreeBuilder::ImportSpecifier parseImportClauseItem(TreeBuilder&, ImportSpecifierType);
     template <class TreeBuilder> typename TreeBuilder::ModuleName parseModuleName(TreeBuilder&);
+    template <class TreeBuilder> typename TreeBuilder::ImportAssertionList parseImportAssertions(TreeBuilder&);
     template <class TreeBuilder> TreeStatement parseImportDeclaration(TreeBuilder&);
     template <class TreeBuilder> typename TreeBuilder::ExportSpecifier parseExportSpecifier(TreeBuilder& context, Vector<std::pair<const Identifier*, const Identifier*>>& maybeExportedLocalNames, bool& hasKeywordForLocalBindings, bool& hasReferencedModuleExportNames);
     template <class TreeBuilder> TreeStatement parseExportDeclaration(TreeBuilder&);

Modified: trunk/Source/_javascript_Core/parser/SyntaxChecker.h (288472 => 288473)


--- trunk/Source/_javascript_Core/parser/SyntaxChecker.h	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/parser/SyntaxChecker.h	2022-01-24 22:51:13 UTC (rev 288473)
@@ -86,7 +86,7 @@
         TemplateExpressionListResult, TemplateExpr,
         TaggedTemplateExpr, YieldExpr, AwaitExpr,
         ModuleNameResult, PrivateIdentifier,
-        ImportSpecifierResult, ImportSpecifierListResult,
+        ImportSpecifierResult, ImportSpecifierListResult, ImportAssertionListResult,
         ExportSpecifierResult, ExportSpecifierListResult,
 
         NewTargetExpr = MetaPropertyBit | 0,
@@ -128,6 +128,7 @@
     typedef int ModuleName;
     typedef int ImportSpecifier;
     typedef int ImportSpecifierList;
+    typedef int ImportAssertionList;
     typedef int ExportSpecifier;
     typedef int ExportSpecifierList;
     typedef int Statement;
@@ -159,7 +160,7 @@
     ExpressionType createLogicalNot(const JSTokenLocation&, ExpressionType) { return UnaryExpr; }
     ExpressionType createUnaryPlus(const JSTokenLocation&, ExpressionType) { return UnaryExpr; }
     ExpressionType createVoid(const JSTokenLocation&, ExpressionType) { return UnaryExpr; }
-    ExpressionType createImportExpr(const JSTokenLocation&, ExpressionType, int, int, int) { return ImportExpr; }
+    ExpressionType createImportExpr(const JSTokenLocation&, ExpressionType, ExpressionType, int, int, int) { return ImportExpr; }
     ExpressionType createThisExpr(const JSTokenLocation&) { return ThisExpr; }
     ExpressionType createSuperExpr(const JSTokenLocation&) { return SuperExpr; }
     ExpressionType createNewTargetExpr(const JSTokenLocation&) { return NewTargetExpr; }
@@ -278,11 +279,13 @@
     ImportSpecifier createImportSpecifier(const JSTokenLocation&, const Identifier&, const Identifier&) { return ImportSpecifierResult; }
     ImportSpecifierList createImportSpecifierList() { return ImportSpecifierListResult; }
     void appendImportSpecifier(ImportSpecifierList, ImportSpecifier) { }
-    int createImportDeclaration(const JSTokenLocation&, ImportSpecifierList, ModuleName) { return StatementResult; }
-    int createExportAllDeclaration(const JSTokenLocation&, ModuleName) { return StatementResult; }
+    ImportAssertionList createImportAssertionList() { return ImportAssertionListResult; }
+    void appendImportAssertion(ImportAssertionList, const Identifier&, const Identifier&) { }
+    int createImportDeclaration(const JSTokenLocation&, ImportSpecifierList, ModuleName, ImportAssertionList) { return StatementResult; }
+    int createExportAllDeclaration(const JSTokenLocation&, ModuleName, ImportAssertionList) { return StatementResult; }
     int createExportDefaultDeclaration(const JSTokenLocation&, int, const Identifier&) { return StatementResult; }
     int createExportLocalDeclaration(const JSTokenLocation&, int) { return StatementResult; }
-    int createExportNamedDeclaration(const JSTokenLocation&, ExportSpecifierList, ModuleName) { return StatementResult; }
+    int createExportNamedDeclaration(const JSTokenLocation&, ExportSpecifierList, ModuleName, ImportAssertionList) { return StatementResult; }
     ExportSpecifier createExportSpecifier(const JSTokenLocation&, const Identifier&, const Identifier&) { return ExportSpecifierResult; }
     ExportSpecifierList createExportSpecifierList() { return ExportSpecifierListResult; }
     void appendExportSpecifier(ExportSpecifierList, ExportSpecifier) { }

Modified: trunk/Source/_javascript_Core/runtime/JSGlobalObjectFunctions.cpp (288472 => 288473)


--- trunk/Source/_javascript_Core/runtime/JSGlobalObjectFunctions.cpp	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/runtime/JSGlobalObjectFunctions.cpp	2022-01-24 22:51:13 UTC (rev 288473)
@@ -822,7 +822,7 @@
     auto scope = DECLARE_THROW_SCOPE(vm);
 
     auto sourceOrigin = callFrame->callerSourceOrigin(vm);
-    RELEASE_ASSERT(callFrame->argumentCount() == 1);
+    RELEASE_ASSERT(callFrame->argumentCount() >= 1);
     auto* specifier = callFrame->uncheckedArgument(0).toString(globalObject);
     RETURN_IF_EXCEPTION(scope, JSValue::encode(promise->rejectWithCaughtException(globalObject, scope)));
 

Modified: trunk/Source/_javascript_Core/runtime/OptionsList.h (288472 => 288473)


--- trunk/Source/_javascript_Core/runtime/OptionsList.h	2022-01-24 22:47:51 UTC (rev 288472)
+++ trunk/Source/_javascript_Core/runtime/OptionsList.h	2022-01-24 22:51:13 UTC (rev 288473)
@@ -541,6 +541,7 @@
     v(Bool, useArrayGroupByMethod, false, Normal, "Expose the groupBy() and groupByToMap() methods on Array.") \
     v(Bool, useAtMethod, true, Normal, "Expose the at() method on Array, %TypedArray%, and String.") \
     v(Bool, useHasOwn, true, Normal, "Expose the Object.hasOwn method") \
+    v(Bool, useImportAssertion, false, Normal, "Enable import assertion.") \
     v(Bool, useIntlEnumeration, true, Normal, "Expose the Intl enumeration APIs.") \
     v(Bool, useSharedArrayBuffer, false, Normal, nullptr) \
     /* FIXME: ShadownRealm can be enabled once WebCore's JSGlobalObject == JSDOMGlobalObject assumption is removed,  https://bugs.webkit.org/show_bug.cgi?id=231506 */\
_______________________________________________
webkit-changes mailing list
[email protected]
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to