summaryrefslogtreecommitdiff
path: root/op_crates
diff options
context:
space:
mode:
authorLuca Casonato <lucacasonato@yahoo.com>2021-03-08 14:22:05 +0100
committerGitHub <noreply@github.com>2021-03-08 14:22:05 +0100
commitc009dad9820fe3d565f2f8fc7025d24af82d29a4 (patch)
treef3228a873c1be8851e2627504d7c060953bb55ae /op_crates
parent0bc488c85c4bbc5b900cf5ff7b09227345b87763 (diff)
fix(webgpu): add webidl records and simple unions (#9698)
The only functional user facing difference is that this commit allows the use SPIRV shaders, not just WGSL. This matches FF and Chrome Canary.
Diffstat (limited to 'op_crates')
-rw-r--r--op_crates/web/00_webidl.js29
-rw-r--r--op_crates/web/internal.d.ts18
-rw-r--r--op_crates/webgpu/02_idl_types.js312
3 files changed, 249 insertions, 110 deletions
diff --git a/op_crates/web/00_webidl.js b/op_crates/web/00_webidl.js
index ab3047391..c00c605e8 100644
--- a/op_crates/web/00_webidl.js
+++ b/op_crates/web/00_webidl.js
@@ -596,6 +596,13 @@
converters.VoidFunction = convertCallbackFunction;
+ converters["UVString?"] = createNullableConverter(
+ converters.USVString,
+ );
+ converters["sequence<double>"] = createSequenceConverter(
+ converters["double"],
+ );
+
function requiredArguments(length, required, opts = {}) {
if (length < required) {
const errMsg = `${
@@ -737,6 +744,26 @@
};
}
+ function createRecordConverter(keyConverter, valueConverter) {
+ return (V, opts) => {
+ if (typeof V !== "object") {
+ throw makeException(
+ TypeError,
+ "can not be converted to dictionary.",
+ opts,
+ );
+ }
+ const result = {};
+ for (const key of V) {
+ const typedKey = keyConverter(key, opts);
+ const value = V[key];
+ const typedValue = valueConverter(value, opts);
+ result[typedKey] = typedValue;
+ }
+ return result;
+ };
+ }
+
const brand = Symbol("[[webidl.brand]]");
function createInterfaceConverter(name, prototype) {
@@ -766,12 +793,14 @@
window.__bootstrap ??= {};
window.__bootstrap.webidl = {
+ makeException,
converters,
requiredArguments,
createDictionaryConverter,
createEnumConverter,
createNullableConverter,
createSequenceConverter,
+ createRecordConverter,
createInterfaceConverter,
brand,
createBranded,
diff --git a/op_crates/web/internal.d.ts b/op_crates/web/internal.d.ts
index 8be80c8a5..efafee26c 100644
--- a/op_crates/web/internal.d.ts
+++ b/op_crates/web/internal.d.ts
@@ -25,6 +25,11 @@ declare namespace globalThis {
*/
context: string;
}
+ declare function makeException(
+ ErrorType: any,
+ message: string,
+ opts: ValueConverterOpts,
+ ): any;
declare interface IntConverterOpts extends ValueConverterOpts {
/**
* Wether to throw if the number is outside of the acceptable values for
@@ -191,6 +196,8 @@ declare namespace globalThis {
* Convert a value into a `VoidFunction` (() => void).
*/
VoidFunction(v: any, opts?: ValueConverterOpts): () => void;
+ ["UVString?"](v: any, opts?: ValueConverterOpts): string | null;
+ ["sequence<double>"](v: any, opts?: ValueConverterOpts): number[];
[type: string]: (v: any, opts: ValueConverterOpts) => any;
};
@@ -268,6 +275,17 @@ declare namespace globalThis {
name: string,
prototype: any,
): (v: any, opts: ValueConverterOpts) => any;
+
+ declare function createRecordConverter<
+ K extends string | number | symbol,
+ V,
+ >(
+ keyConverter: (v: any, opts: ValueConverterOpts) => K,
+ valueConverter: (v: any, opts: ValueConverterOpts) => V,
+ ): (
+ v: Record<K, V>,
+ opts: ValueConverterOpts,
+ ) => any;
}
declare var eventTarget: {
diff --git a/op_crates/webgpu/02_idl_types.js b/op_crates/webgpu/02_idl_types.js
index 68c3e3247..7e72ea2b1 100644
--- a/op_crates/webgpu/02_idl_types.js
+++ b/op_crates/webgpu/02_idl_types.js
@@ -42,7 +42,6 @@
// This needs to be initalized after all of the base classes are implmented,
// otherwise their converters might not be available yet.
-
// DICTIONARY: GPUObjectDescriptorBase
const dictMembersGPUObjectDescriptorBase = [
{ key: "label", converter: webidl.converters["USVString"] },
@@ -109,6 +108,10 @@
],
);
+ // TYPEDEF: GPUSize32
+ webidl.converters["GPUSize32"] = (V, opts) =>
+ webidl.converters["unsigned long"](V, { ...opts, enforceRange: true });
+
// DICTIONARY: GPUDeviceDescriptor
const dictMembersGPUDeviceDescriptor = [
{
@@ -120,7 +123,10 @@
},
{
key: "nonGuaranteedLimits",
- converter: webidl.converters.any,
+ converter: webidl.createRecordConverter(
+ webidl.converters["DOMString"],
+ webidl.converters["GPUSize32"],
+ ),
defaultValue: {},
},
];
@@ -192,16 +198,54 @@
GPUTexture,
);
- // TYPEDEF: GPUExtent3D
- webidl.converters["GPUExtent3D"] = webidl.converters.any;
-
// TYPEDEF: GPUIntegerCoordinate
webidl.converters["GPUIntegerCoordinate"] = (V, opts) =>
webidl.converters["unsigned long"](V, { ...opts, enforceRange: true });
+ webidl.converters["sequence<GPUIntegerCoordinate>"] = webidl
+ .createSequenceConverter(webidl.converters["GPUIntegerCoordinate"]);
- // TYPEDEF: GPUSize32
- webidl.converters["GPUSize32"] = (V, opts) =>
- webidl.converters["unsigned long"](V, { ...opts, enforceRange: true });
+ // DICTIONARY: GPUExtent3DDict
+ const dictMembersGPUExtent3DDict = [
+ {
+ key: "width",
+ converter: webidl.converters["GPUIntegerCoordinate"],
+ defaultValue: 1,
+ },
+ {
+ key: "height",
+ converter: webidl.converters["GPUIntegerCoordinate"],
+ defaultValue: 1,
+ },
+ {
+ key: "depthOrArrayLayers",
+ converter: webidl.converters["GPUIntegerCoordinate"],
+ defaultValue: 1,
+ },
+ ];
+ webidl.converters["GPUExtent3DDict"] = webidl.createDictionaryConverter(
+ "GPUExtent3DDict",
+ dictMembersGPUExtent3DDict,
+ );
+
+ // TYPEDEF: GPUExtent3D
+ webidl.converters["GPUExtent3D"] = (V, opts) => {
+ // Union for (sequence<GPUIntegerCoordinate> or GPUExtent3DDict)
+ if (V === null || V === undefined) {
+ return webidl.converters["GPUExtent3DDict"](V, opts);
+ }
+ if (typeof V === "object") {
+ const method = V[Symbol.iterator];
+ if (method !== undefined) {
+ return webidl.converters["sequence<GPUIntegerCoordinate>"](V, opts);
+ }
+ return webidl.converters["GPUExtent3DDict"](V, opts);
+ }
+ throw webidl.makeException(
+ TypeError,
+ "can not be converted to sequence<GPUIntegerCoordinate> or GPUExtent3DDict.",
+ opts,
+ );
+ };
// ENUM: GPUTextureDimension
webidl.converters["GPUTextureDimension"] = webidl.createEnumConverter(
@@ -685,8 +729,28 @@
GPUBindGroup,
);
+ // DICTIONARY: GPUBufferBinding
+ const dictMembersGPUBufferBinding = [
+ {
+ key: "buffer",
+ converter: webidl.converters["GPUBuffer"],
+ required: true,
+ },
+ {
+ key: "offset",
+ converter: webidl.converters["GPUSize64"],
+ defaultValue: 0,
+ },
+ { key: "size", converter: webidl.converters["GPUSize64"] },
+ ];
+ webidl.converters["GPUBufferBinding"] = webidl.createDictionaryConverter(
+ "GPUBufferBinding",
+ dictMembersGPUBufferBinding,
+ );
+
// TYPEDEF: GPUBindingResource
- webidl.converters["GPUBindingResource"] = webidl.converters.any;
+ webidl.converters["GPUBindingResource"] =
+ webidl.converters.any /** put union here! **/;
// DICTIONARY: GPUBindGroupEntry
const dictMembersGPUBindGroupEntry = [
@@ -728,25 +792,6 @@
dictMembersGPUBindGroupDescriptor,
);
- // DICTIONARY: GPUBufferBinding
- const dictMembersGPUBufferBinding = [
- {
- key: "buffer",
- converter: webidl.converters["GPUBuffer"],
- required: true,
- },
- {
- key: "offset",
- converter: webidl.converters["GPUSize64"],
- defaultValue: 0,
- },
- { key: "size", converter: webidl.converters["GPUSize64"] },
- ];
- webidl.converters["GPUBufferBinding"] = webidl.createDictionaryConverter(
- "GPUBufferBinding",
- dictMembersGPUBufferBinding,
- );
-
// INTERFACE: GPUPipelineLayout
webidl.converters.GPUPipelineLayout = webidl.createInterfaceConverter(
"GPUPipelineLayout",
@@ -800,7 +845,23 @@
// DICTIONARY: GPUShaderModuleDescriptor
const dictMembersGPUShaderModuleDescriptor = [
- { key: "code", converter: webidl.converters["USVString"], required: true },
+ {
+ key: "code",
+ converter: (V, opts) => {
+ if (V instanceof Uint32Array) {
+ return webidl.converters["Uint32Array"](V, opts);
+ }
+ if (typeof V === "string") {
+ return webidl.converters["DOMString"](V, opts);
+ }
+ throw webidl.makeException(
+ TypeError,
+ "can not be converted to Uint32Array or DOMString.",
+ opts,
+ );
+ },
+ required: true,
+ },
{ key: "sourceMap", converter: webidl.converters["object"] },
];
webidl.converters["GPUShaderModuleDescriptor"] = webidl
@@ -1333,6 +1394,8 @@
"GPUCommandBuffer",
GPUCommandBuffer,
);
+ webidl.converters["sequence<GPUCommandBuffer>"] = webidl
+ .createSequenceConverter(webidl.converters["GPUCommandBuffer"]);
// DICTIONARY: GPUCommandBufferDescriptor
const dictMembersGPUCommandBufferDescriptor = [];
@@ -1393,8 +1456,48 @@
dictMembersGPUImageCopyBuffer,
);
+ // DICTIONARY: GPUOrigin3DDict
+ const dictMembersGPUOrigin3DDict = [
+ {
+ key: "x",
+ converter: webidl.converters["GPUIntegerCoordinate"],
+ defaultValue: 0,
+ },
+ {
+ key: "y",
+ converter: webidl.converters["GPUIntegerCoordinate"],
+ defaultValue: 0,
+ },
+ {
+ key: "z",
+ converter: webidl.converters["GPUIntegerCoordinate"],
+ defaultValue: 0,
+ },
+ ];
+ webidl.converters["GPUOrigin3DDict"] = webidl.createDictionaryConverter(
+ "GPUOrigin3DDict",
+ dictMembersGPUOrigin3DDict,
+ );
+
// TYPEDEF: GPUOrigin3D
- webidl.converters["GPUOrigin3D"] = webidl.converters.any;
+ webidl.converters["GPUOrigin3D"] = (V, opts) => {
+ // Union for (sequence<GPUIntegerCoordinate> or GPUOrigin3DDict)
+ if (V === null || V === undefined) {
+ return webidl.converters["GPUOrigin3DDict"](V, opts);
+ }
+ if (typeof V === "object") {
+ const method = V[Symbol.iterator];
+ if (method !== undefined) {
+ return webidl.converters["sequence<GPUIntegerCoordinate>"](V, opts);
+ }
+ return webidl.converters["GPUOrigin3DDict"](V, opts);
+ }
+ throw webidl.makeException(
+ TypeError,
+ "can not be converted to sequence<GPUIntegerCoordinate> or GPUOrigin3DDict.",
+ opts,
+ );
+ };
// DICTIONARY: GPUImageCopyTexture
const dictMembersGPUImageCopyTexture = [
@@ -1445,7 +1548,43 @@
GPURenderPassEncoder,
);
- // ENUM: GPUStoreOp
+ // ENUM: GPULoadOp
+ webidl.converters["GPULoadOp"] = webidl.createEnumConverter("GPULoadOp", [
+ "load",
+ ]);
+
+ // DICTIONARY: GPUColorDict
+ const dictMembersGPUColorDict = [
+ { key: "r", converter: webidl.converters["double"], required: true },
+ { key: "g", converter: webidl.converters["double"], required: true },
+ { key: "b", converter: webidl.converters["double"], required: true },
+ { key: "a", converter: webidl.converters["double"], required: true },
+ ];
+ webidl.converters["GPUColorDict"] = webidl.createDictionaryConverter(
+ "GPUColorDict",
+ dictMembersGPUColorDict,
+ );
+
+ // TYPEDEF: GPUColor
+ webidl.converters["GPUColor"] = (V, opts) => {
+ // Union for (sequence<double> or GPUColorDict)
+ if (V === null || V === undefined) {
+ return webidl.converters["GPUColorDict"](V, opts);
+ }
+ if (typeof V === "object") {
+ const method = V[Symbol.iterator];
+ if (method !== undefined) {
+ return webidl.converters["sequence<double>"](V, opts);
+ }
+ return webidl.converters["GPUColorDict"](V, opts);
+ }
+ throw webidl.makeException(
+ TypeError,
+ "can not be converted to sequence<double> or GPUColorDict.",
+ opts,
+ );
+ }; // ENUM: GPUStoreOp
+
webidl.converters["GPUStoreOp"] = webidl.createEnumConverter("GPUStoreOp", [
"store",
"clear",
@@ -1459,7 +1598,11 @@
required: true,
},
{ key: "resolveTarget", converter: webidl.converters["GPUTextureView"] },
- { key: "loadValue", converter: webidl.converters.any, required: true },
+ {
+ key: "loadValue",
+ converter: webidl.converters.any, /** put union here! **/
+ required: true,
+ },
{
key: "storeOp",
converter: webidl.converters["GPUStoreOp"],
@@ -1479,7 +1622,11 @@
converter: webidl.converters["GPUTextureView"],
required: true,
},
- { key: "depthLoadValue", converter: webidl.converters.any, required: true },
+ {
+ key: "depthLoadValue",
+ converter: webidl.converters.any, /** put union here! **/
+ required: true,
+ },
{
key: "depthStoreOp",
converter: webidl.converters["GPUStoreOp"],
@@ -1492,7 +1639,7 @@
},
{
key: "stencilLoadValue",
- converter: webidl.converters.any,
+ converter: webidl.converters.any, /** put union here! **/
required: true,
},
{
@@ -1540,16 +1687,13 @@
dictMembersGPURenderPassDescriptor,
);
- // ENUM: GPULoadOp
- webidl.converters["GPULoadOp"] = webidl.createEnumConverter("GPULoadOp", [
- "load",
- ]);
-
// INTERFACE: GPURenderBundle
webidl.converters.GPURenderBundle = webidl.createInterfaceConverter(
"GPURenderBundle",
GPURenderBundle,
);
+ webidl.converters["sequence<GPURenderBundle>"] = webidl
+ .createSequenceConverter(webidl.converters["GPURenderBundle"]);
// DICTIONARY: GPURenderBundleDescriptor
const dictMembersGPURenderBundleDescriptor = [];
@@ -1678,7 +1822,7 @@
);
// TYPEDEF: GPUError
- webidl.converters["GPUError"] = webidl.converters.any;
+ webidl.converters["GPUError"] = webidl.converters.any /** put union here! **/;
// // INTERFACE: GPUUncapturedErrorEvent
// webidl.converters.GPUUncapturedErrorEvent = webidl.createInterfaceConverter(
@@ -1708,21 +1852,6 @@
// TYPEDEF: GPUFlagsConstant
webidl.converters["GPUFlagsConstant"] = webidl.converters["unsigned long"];
- // DICTIONARY: GPUColorDict
- const dictMembersGPUColorDict = [
- { key: "r", converter: webidl.converters["double"], required: true },
- { key: "g", converter: webidl.converters["double"], required: true },
- { key: "b", converter: webidl.converters["double"], required: true },
- { key: "a", converter: webidl.converters["double"], required: true },
- ];
- webidl.converters["GPUColorDict"] = webidl.createDictionaryConverter(
- "GPUColorDict",
- dictMembersGPUColorDict,
- );
-
- // TYPEDEF: GPUColor
- webidl.converters["GPUColor"] = webidl.converters.any;
-
// DICTIONARY: GPUOrigin2DDict
const dictMembersGPUOrigin2DDict = [
{
@@ -1742,59 +1871,22 @@
);
// TYPEDEF: GPUOrigin2D
- webidl.converters["GPUOrigin2D"] = webidl.converters.any;
-
- // DICTIONARY: GPUOrigin3DDict
- const dictMembersGPUOrigin3DDict = [
- {
- key: "x",
- converter: webidl.converters["GPUIntegerCoordinate"],
- defaultValue: 0,
- },
- {
- key: "y",
- converter: webidl.converters["GPUIntegerCoordinate"],
- defaultValue: 0,
- },
- {
- key: "z",
- converter: webidl.converters["GPUIntegerCoordinate"],
- defaultValue: 0,
- },
- ];
- webidl.converters["GPUOrigin3DDict"] = webidl.createDictionaryConverter(
- "GPUOrigin3DDict",
- dictMembersGPUOrigin3DDict,
- );
-
- // DICTIONARY: GPUExtent3DDict
- const dictMembersGPUExtent3DDict = [
- {
- key: "width",
- converter: webidl.converters["GPUIntegerCoordinate"],
- defaultValue: 1,
- },
- {
- key: "height",
- converter: webidl.converters["GPUIntegerCoordinate"],
- defaultValue: 1,
- },
- {
- key: "depthOrArrayLayers",
- converter: webidl.converters["GPUIntegerCoordinate"],
- defaultValue: 1,
- },
- ];
- webidl.converters["GPUExtent3DDict"] = webidl.createDictionaryConverter(
- "GPUExtent3DDict",
- dictMembersGPUExtent3DDict,
- );
-
- webidl.converters["sequence<GPURenderBundle>"] = webidl
- .createSequenceConverter(webidl.converters["GPURenderBundle"]);
- webidl.converters["sequence<GPUCommandBuffer>"] = webidl
- .createSequenceConverter(webidl.converters["GPUCommandBuffer"]);
- webidl.converters["UVString?"] = webidl.createNullableConverter(
- webidl.converters.USVString,
- );
+ webidl.converters["GPUOrigin2D"] = (V, opts) => {
+ // Union for (sequence<GPUIntegerCoordinate> or GPUOrigin2DDict)
+ if (V === null || V === undefined) {
+ return webidl.converters["GPUOrigin2DDict"](V, opts);
+ }
+ if (typeof V === "object") {
+ const method = V[Symbol.iterator];
+ if (method !== undefined) {
+ return webidl.converters["sequence<GPUIntegerCoordinate>"](V, opts);
+ }
+ return webidl.converters["GPUOrigin2DDict"](V, opts);
+ }
+ throw webidl.makeException(
+ TypeError,
+ "can not be converted to sequence<GPUIntegerCoordinate> or GPUOrigin2DDict.",
+ opts,
+ );
+ };
})(this);