mirror of
https://github.com/denoland/deno.git
synced 2025-02-01 12:16:11 -05:00
chore(ext): update webgpu (#15059)
This commit is contained in:
parent
649536e266
commit
2b1f145c3e
24 changed files with 1605 additions and 1867 deletions
57
Cargo.lock
generated
57
Cargo.lock
generated
|
@ -102,6 +102,15 @@ dependencies = [
|
||||||
"alloc-no-stdlib",
|
"alloc-no-stdlib",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "android_system_properties"
|
||||||
|
version = "0.1.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "a20ae67ce26261f218e2b3f2f0d01887a9818283ca6fb260fa7c67e253d61c92"
|
||||||
|
dependencies = [
|
||||||
|
"libc",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "ansi_term"
|
name = "ansi_term"
|
||||||
version = "0.12.1"
|
version = "0.12.1"
|
||||||
|
@ -128,9 +137,9 @@ dependencies = [
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "ash"
|
name = "ash"
|
||||||
version = "0.34.0+1.2.203"
|
version = "0.37.0+1.3.209"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "b0f780da53d0063880d45554306489f09dd8d1bda47688b4a57bc579119356df"
|
checksum = "006ca68e0f2b03f22d6fa9f2860f85aed430d257fec20f8879b2145e7c7ae1a6"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"libloading",
|
"libloading",
|
||||||
]
|
]
|
||||||
|
@ -687,9 +696,9 @@ checksum = "b365fabc795046672053e29c954733ec3b05e4be654ab130fe8f1f94d7051f35"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "d3d12"
|
name = "d3d12"
|
||||||
version = "0.4.1"
|
version = "0.5.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "2daefd788d1e96e0a9d66dee4b828b883509bc3ea9ce30665f04c3246372690c"
|
checksum = "827914e1f53b1e0e025ecd3d967a7836b7bcb54520f90e21ef8df7b4d88a2759"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"bitflags",
|
"bitflags",
|
||||||
"libloading",
|
"libloading",
|
||||||
|
@ -2358,6 +2367,7 @@ checksum = "8c2352bd1d0bceb871cb9d40f24360c8133c11d7486b68b5381c1dd1a32015e3"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"libc",
|
"libc",
|
||||||
"libloading",
|
"libloading",
|
||||||
|
"pkg-config",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
@ -2625,9 +2635,9 @@ dependencies = [
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "metal"
|
name = "metal"
|
||||||
version = "0.23.1"
|
version = "0.24.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "e0514f491f4cc03632ab399ee01e2c1c1b12d3e1cf2d667c1ff5f87d6dcd2084"
|
checksum = "de11355d1f6781482d027a3b4d4de7825dcedb197bf573e0596d00008402d060"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"bitflags",
|
"bitflags",
|
||||||
"block",
|
"block",
|
||||||
|
@ -2684,9 +2694,9 @@ dependencies = [
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "naga"
|
name = "naga"
|
||||||
version = "0.8.5"
|
version = "0.9.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "3012f2dbcc79e8e0b5825a4836a7106a75dd9b2fe42c528163be0f572538c705"
|
checksum = "5f50357e1167a3ab92d6b3c7f4bf5f7fd13fde3f4b28bf0d5ea07b5100fdb6c0"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"bit-set",
|
"bit-set",
|
||||||
"bitflags",
|
"bitflags",
|
||||||
|
@ -2698,7 +2708,9 @@ dependencies = [
|
||||||
"rustc-hash",
|
"rustc-hash",
|
||||||
"serde",
|
"serde",
|
||||||
"spirv",
|
"spirv",
|
||||||
|
"termcolor",
|
||||||
"thiserror",
|
"thiserror",
|
||||||
|
"unicode-xid 0.2.3",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
@ -3236,7 +3248,7 @@ version = "0.4.30"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759"
|
checksum = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"unicode-xid",
|
"unicode-xid 0.1.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
@ -4497,7 +4509,7 @@ checksum = "9ca4b3b69a77cbe1ffc9e198781b7acb0c7365a883670e8f1c1bc66fba79a5c5"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"proc-macro2 0.4.30",
|
"proc-macro2 0.4.30",
|
||||||
"quote 0.6.13",
|
"quote 0.6.13",
|
||||||
"unicode-xid",
|
"unicode-xid 0.1.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
@ -5086,6 +5098,12 @@ version = "0.1.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc"
|
checksum = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "unicode-xid"
|
||||||
|
version = "0.2.3"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "957e51f3646910546462e67d5f7599b9e4fb8acdd304b087a6494730f9eebf04"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "universal-hash"
|
name = "universal-hash"
|
||||||
version = "0.4.1"
|
version = "0.4.1"
|
||||||
|
@ -5331,11 +5349,12 @@ dependencies = [
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wgpu-core"
|
name = "wgpu-core"
|
||||||
version = "0.12.2"
|
version = "0.13.1"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "c4688c000eb841ca55f7b35db659b78d6e1cd77d7caf8fb929f4e181f754047d"
|
checksum = "266ca6be6004fd1b2a768023b1cb0afbf7af0cbffaba19af25c5792d44e74784"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"arrayvec",
|
"arrayvec",
|
||||||
|
"bit-vec",
|
||||||
"bitflags",
|
"bitflags",
|
||||||
"cfg_aliases",
|
"cfg_aliases",
|
||||||
"codespan-reporting",
|
"codespan-reporting",
|
||||||
|
@ -5343,22 +5362,24 @@ dependencies = [
|
||||||
"fxhash",
|
"fxhash",
|
||||||
"log 0.4.17",
|
"log 0.4.17",
|
||||||
"naga",
|
"naga",
|
||||||
"parking_lot 0.11.2",
|
"parking_lot 0.12.1",
|
||||||
"profiling",
|
"profiling",
|
||||||
"ron",
|
"ron",
|
||||||
"serde",
|
"serde",
|
||||||
"smallvec",
|
"smallvec",
|
||||||
"thiserror",
|
"thiserror",
|
||||||
|
"web-sys",
|
||||||
"wgpu-hal",
|
"wgpu-hal",
|
||||||
"wgpu-types",
|
"wgpu-types",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wgpu-hal"
|
name = "wgpu-hal"
|
||||||
version = "0.12.5"
|
version = "0.13.1"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "d684ea6a34974a2fc19f1dfd183d11a62e22d75c4f187a574bb1224df8e056c2"
|
checksum = "bef50e48812c7eb958fa52d28a912f8b77c96453ebab21c72b01cdda61d3e65d"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
|
"android_system_properties",
|
||||||
"arrayvec",
|
"arrayvec",
|
||||||
"ash",
|
"ash",
|
||||||
"bit-set",
|
"bit-set",
|
||||||
|
@ -5379,7 +5400,7 @@ dependencies = [
|
||||||
"metal",
|
"metal",
|
||||||
"naga",
|
"naga",
|
||||||
"objc",
|
"objc",
|
||||||
"parking_lot 0.11.2",
|
"parking_lot 0.12.1",
|
||||||
"profiling",
|
"profiling",
|
||||||
"range-alloc",
|
"range-alloc",
|
||||||
"raw-window-handle",
|
"raw-window-handle",
|
||||||
|
@ -5393,9 +5414,9 @@ dependencies = [
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wgpu-types"
|
name = "wgpu-types"
|
||||||
version = "0.12.0"
|
version = "0.13.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "549533d9e1cdd4b4cda7718d33ff500fc4c34b5467b71d76b547ae0324f3b2a2"
|
checksum = "f48d691b733b9d50ea8cb18f377fd1ed927c90c55ad1ec5b90f68885471977f7"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"bitflags",
|
"bitflags",
|
||||||
"bitflags_serde_shim",
|
"bitflags_serde_shim",
|
||||||
|
|
134
cli/dts/lib.deno_webgpu.d.ts
vendored
134
cli/dts/lib.deno_webgpu.d.ts
vendored
|
@ -5,10 +5,8 @@
|
||||||
/// <reference no-default-lib="true" />
|
/// <reference no-default-lib="true" />
|
||||||
/// <reference lib="esnext" />
|
/// <reference lib="esnext" />
|
||||||
|
|
||||||
// 8cc98b6f10b7f354473a08c3773bb1de839845b9
|
|
||||||
|
|
||||||
interface GPUObjectBase {
|
interface GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUObjectDescriptorBase {
|
declare interface GPUObjectDescriptorBase {
|
||||||
|
@ -64,6 +62,13 @@ declare class GPUSupportedFeatures {
|
||||||
values(): IterableIterator<GPUFeatureName>;
|
values(): IterableIterator<GPUFeatureName>;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
declare class GPUAdapterInfo {
|
||||||
|
readonly vendor: string;
|
||||||
|
readonly architecture: string;
|
||||||
|
readonly device: string;
|
||||||
|
readonly description: string;
|
||||||
|
}
|
||||||
|
|
||||||
declare class GPU {
|
declare class GPU {
|
||||||
requestAdapter(
|
requestAdapter(
|
||||||
options?: GPURequestAdapterOptions,
|
options?: GPURequestAdapterOptions,
|
||||||
|
@ -78,12 +83,12 @@ declare interface GPURequestAdapterOptions {
|
||||||
declare type GPUPowerPreference = "low-power" | "high-performance";
|
declare type GPUPowerPreference = "low-power" | "high-performance";
|
||||||
|
|
||||||
declare class GPUAdapter {
|
declare class GPUAdapter {
|
||||||
readonly name: string;
|
|
||||||
readonly features: GPUSupportedFeatures;
|
readonly features: GPUSupportedFeatures;
|
||||||
readonly limits: GPUSupportedLimits;
|
readonly limits: GPUSupportedLimits;
|
||||||
readonly isFallbackAdapter: boolean;
|
readonly isFallbackAdapter: boolean;
|
||||||
|
|
||||||
requestDevice(descriptor?: GPUDeviceDescriptor): Promise<GPUDevice>;
|
requestDevice(descriptor?: GPUDeviceDescriptor): Promise<GPUDevice>;
|
||||||
|
requestAdapterInfo(unmaskHints?: string[]): Promise<GPUAdapterInfo>;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUDeviceDescriptor extends GPUObjectDescriptorBase {
|
declare interface GPUDeviceDescriptor extends GPUObjectDescriptorBase {
|
||||||
|
@ -101,6 +106,7 @@ declare type GPUFeatureName =
|
||||||
| "texture-compression-astc"
|
| "texture-compression-astc"
|
||||||
| "timestamp-query"
|
| "timestamp-query"
|
||||||
| "indirect-first-instance"
|
| "indirect-first-instance"
|
||||||
|
| "shader-f16"
|
||||||
// extended from spec
|
// extended from spec
|
||||||
| "mappable-primary-buffers"
|
| "mappable-primary-buffers"
|
||||||
| "sampled-texture-binding-array"
|
| "sampled-texture-binding-array"
|
||||||
|
@ -116,7 +122,7 @@ declare type GPUFeatureName =
|
||||||
| "vertex-attribute-64bit";
|
| "vertex-attribute-64bit";
|
||||||
|
|
||||||
declare class GPUDevice extends EventTarget implements GPUObjectBase {
|
declare class GPUDevice extends EventTarget implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
readonly lost: Promise<GPUDeviceLostInfo>;
|
readonly lost: Promise<GPUDeviceLostInfo>;
|
||||||
pushErrorScope(filter: GPUErrorFilter): undefined;
|
pushErrorScope(filter: GPUErrorFilter): undefined;
|
||||||
|
@ -168,7 +174,7 @@ declare class GPUDevice extends EventTarget implements GPUObjectBase {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUBuffer implements GPUObjectBase {
|
declare class GPUBuffer implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
mapAsync(
|
mapAsync(
|
||||||
mode: GPUMapModeFlags,
|
mode: GPUMapModeFlags,
|
||||||
|
@ -208,7 +214,7 @@ declare class GPUMapMode {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUTexture implements GPUObjectBase {
|
declare class GPUTexture implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
createView(descriptor?: GPUTextureViewDescriptor): GPUTextureView;
|
createView(descriptor?: GPUTextureViewDescriptor): GPUTextureView;
|
||||||
destroy(): undefined;
|
destroy(): undefined;
|
||||||
|
@ -235,7 +241,7 @@ declare class GPUTextureUsage {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUTextureView implements GPUObjectBase {
|
declare class GPUTextureView implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUTextureViewDescriptor extends GPUObjectDescriptorBase {
|
declare interface GPUTextureViewDescriptor extends GPUObjectDescriptorBase {
|
||||||
|
@ -300,6 +306,8 @@ declare type GPUTextureFormat =
|
||||||
| "depth24plus"
|
| "depth24plus"
|
||||||
| "depth24plus-stencil8"
|
| "depth24plus-stencil8"
|
||||||
| "depth32float"
|
| "depth32float"
|
||||||
|
| "depth24unorm-stencil8"
|
||||||
|
| "depth32float-stencil8"
|
||||||
| "bc1-rgba-unorm"
|
| "bc1-rgba-unorm"
|
||||||
| "bc1-rgba-unorm-srgb"
|
| "bc1-rgba-unorm-srgb"
|
||||||
| "bc2-rgba-unorm"
|
| "bc2-rgba-unorm"
|
||||||
|
@ -351,12 +359,10 @@ declare type GPUTextureFormat =
|
||||||
| "astc-12x10-unorm"
|
| "astc-12x10-unorm"
|
||||||
| "astc-12x10-unorm-srgb"
|
| "astc-12x10-unorm-srgb"
|
||||||
| "astc-12x12-unorm"
|
| "astc-12x12-unorm"
|
||||||
| "astc-12x12-unorm-srgb"
|
| "astc-12x12-unorm-srgb";
|
||||||
| "depth24unorm-stencil8"
|
|
||||||
| "depth32float-stencil8";
|
|
||||||
|
|
||||||
declare class GPUSampler implements GPUObjectBase {
|
declare class GPUSampler implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUSamplerDescriptor extends GPUObjectDescriptorBase {
|
declare interface GPUSamplerDescriptor extends GPUObjectDescriptorBase {
|
||||||
|
@ -365,7 +371,7 @@ declare interface GPUSamplerDescriptor extends GPUObjectDescriptorBase {
|
||||||
addressModeW?: GPUAddressMode;
|
addressModeW?: GPUAddressMode;
|
||||||
magFilter?: GPUFilterMode;
|
magFilter?: GPUFilterMode;
|
||||||
minFilter?: GPUFilterMode;
|
minFilter?: GPUFilterMode;
|
||||||
mipmapFilter?: GPUFilterMode;
|
mipmapFilter?: GPUMipmapFilterMode;
|
||||||
lodMinClamp?: number;
|
lodMinClamp?: number;
|
||||||
lodMaxClamp?: number;
|
lodMaxClamp?: number;
|
||||||
compare?: GPUCompareFunction;
|
compare?: GPUCompareFunction;
|
||||||
|
@ -376,6 +382,8 @@ declare type GPUAddressMode = "clamp-to-edge" | "repeat" | "mirror-repeat";
|
||||||
|
|
||||||
declare type GPUFilterMode = "nearest" | "linear";
|
declare type GPUFilterMode = "nearest" | "linear";
|
||||||
|
|
||||||
|
declare type GPUMipmapFilterMode = "nearest" | "linear";
|
||||||
|
|
||||||
declare type GPUCompareFunction =
|
declare type GPUCompareFunction =
|
||||||
| "never"
|
| "never"
|
||||||
| "less"
|
| "less"
|
||||||
|
@ -387,7 +395,7 @@ declare type GPUCompareFunction =
|
||||||
| "always";
|
| "always";
|
||||||
|
|
||||||
declare class GPUBindGroupLayout implements GPUObjectBase {
|
declare class GPUBindGroupLayout implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUBindGroupLayoutDescriptor extends GPUObjectDescriptorBase {
|
declare interface GPUBindGroupLayoutDescriptor extends GPUObjectDescriptorBase {
|
||||||
|
@ -450,7 +458,7 @@ declare interface GPUStorageTextureBindingLayout {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUBindGroup implements GPUObjectBase {
|
declare class GPUBindGroup implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUBindGroupDescriptor extends GPUObjectDescriptorBase {
|
declare interface GPUBindGroupDescriptor extends GPUObjectDescriptorBase {
|
||||||
|
@ -475,7 +483,7 @@ declare interface GPUBufferBinding {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUPipelineLayout implements GPUObjectBase {
|
declare class GPUPipelineLayout implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUPipelineLayoutDescriptor extends GPUObjectDescriptorBase {
|
declare interface GPUPipelineLayoutDescriptor extends GPUObjectDescriptorBase {
|
||||||
|
@ -496,7 +504,7 @@ declare interface GPUCompilationInfo {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUShaderModule implements GPUObjectBase {
|
declare class GPUShaderModule implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
compilationInfo(): Promise<GPUCompilationInfo>;
|
compilationInfo(): Promise<GPUCompilationInfo>;
|
||||||
}
|
}
|
||||||
|
@ -506,8 +514,10 @@ declare interface GPUShaderModuleDescriptor extends GPUObjectDescriptorBase {
|
||||||
sourceMap?: any;
|
sourceMap?: any;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
declare type GPUAutoLayoutMode = "auto";
|
||||||
|
|
||||||
declare interface GPUPipelineDescriptorBase extends GPUObjectDescriptorBase {
|
declare interface GPUPipelineDescriptorBase extends GPUObjectDescriptorBase {
|
||||||
layout?: GPUPipelineLayout;
|
layout: GPUPipelineLayout | GPUAutoLayoutMode;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUPipelineBase {
|
declare interface GPUPipelineBase {
|
||||||
|
@ -520,7 +530,7 @@ declare interface GPUProgrammableStage {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUComputePipeline implements GPUObjectBase, GPUPipelineBase {
|
declare class GPUComputePipeline implements GPUObjectBase, GPUPipelineBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
getBindGroupLayout(index: number): GPUBindGroupLayout;
|
getBindGroupLayout(index: number): GPUBindGroupLayout;
|
||||||
}
|
}
|
||||||
|
@ -531,7 +541,7 @@ declare interface GPUComputePipelineDescriptor
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPURenderPipeline implements GPUObjectBase, GPUPipelineBase {
|
declare class GPURenderPipeline implements GPUObjectBase, GPUPipelineBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
getBindGroupLayout(index: number): GPUBindGroupLayout;
|
getBindGroupLayout(index: number): GPUBindGroupLayout;
|
||||||
}
|
}
|
||||||
|
@ -545,13 +555,6 @@ declare interface GPURenderPipelineDescriptor
|
||||||
fragment?: GPUFragmentState;
|
fragment?: GPUFragmentState;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare type GPUPrimitiveTopology =
|
|
||||||
| "point-list"
|
|
||||||
| "line-list"
|
|
||||||
| "line-strip"
|
|
||||||
| "triangle-list"
|
|
||||||
| "triangle-strip";
|
|
||||||
|
|
||||||
declare interface GPUPrimitiveState {
|
declare interface GPUPrimitiveState {
|
||||||
topology?: GPUPrimitiveTopology;
|
topology?: GPUPrimitiveTopology;
|
||||||
stripIndexFormat?: GPUIndexFormat;
|
stripIndexFormat?: GPUIndexFormat;
|
||||||
|
@ -560,6 +563,13 @@ declare interface GPUPrimitiveState {
|
||||||
unclippedDepth?: boolean;
|
unclippedDepth?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
declare type GPUPrimitiveTopology =
|
||||||
|
| "point-list"
|
||||||
|
| "line-list"
|
||||||
|
| "line-strip"
|
||||||
|
| "triangle-list"
|
||||||
|
| "triangle-strip";
|
||||||
|
|
||||||
declare type GPUFrontFace = "ccw" | "cw";
|
declare type GPUFrontFace = "ccw" | "cw";
|
||||||
|
|
||||||
declare type GPUCullMode = "none" | "front" | "back";
|
declare type GPUCullMode = "none" | "front" | "back";
|
||||||
|
@ -571,7 +581,7 @@ declare interface GPUMultisampleState {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUFragmentState extends GPUProgrammableStage {
|
declare interface GPUFragmentState extends GPUProgrammableStage {
|
||||||
targets: GPUColorTargetState[];
|
targets: (GPUColorTargetState | null)[];
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUColorTargetState {
|
declare interface GPUColorTargetState {
|
||||||
|
@ -710,13 +720,13 @@ declare interface GPUVertexAttribute {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUCommandBuffer implements GPUObjectBase {
|
declare class GPUCommandBuffer implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUCommandBufferDescriptor extends GPUObjectDescriptorBase {}
|
declare interface GPUCommandBufferDescriptor extends GPUObjectDescriptorBase {}
|
||||||
|
|
||||||
declare class GPUCommandEncoder implements GPUObjectBase {
|
declare class GPUCommandEncoder implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
beginRenderPass(descriptor: GPURenderPassDescriptor): GPURenderPassEncoder;
|
beginRenderPass(descriptor: GPURenderPassDescriptor): GPURenderPassEncoder;
|
||||||
beginComputePass(
|
beginComputePass(
|
||||||
|
@ -751,8 +761,8 @@ declare class GPUCommandEncoder implements GPUObjectBase {
|
||||||
|
|
||||||
clearBuffer(
|
clearBuffer(
|
||||||
destination: GPUBuffer,
|
destination: GPUBuffer,
|
||||||
destinationOffset: number,
|
destinationOffset?: number,
|
||||||
size: number,
|
size?: number,
|
||||||
): undefined;
|
): undefined;
|
||||||
|
|
||||||
pushDebugGroup(groupLabel: string): undefined;
|
pushDebugGroup(groupLabel: string): undefined;
|
||||||
|
@ -813,7 +823,7 @@ interface GPUProgrammablePassEncoder {
|
||||||
|
|
||||||
declare class GPUComputePassEncoder
|
declare class GPUComputePassEncoder
|
||||||
implements GPUObjectBase, GPUProgrammablePassEncoder {
|
implements GPUObjectBase, GPUProgrammablePassEncoder {
|
||||||
label: string | null;
|
label: string;
|
||||||
setBindGroup(
|
setBindGroup(
|
||||||
index: number,
|
index: number,
|
||||||
bindGroup: GPUBindGroup,
|
bindGroup: GPUBindGroup,
|
||||||
|
@ -830,8 +840,8 @@ declare class GPUComputePassEncoder
|
||||||
popDebugGroup(): undefined;
|
popDebugGroup(): undefined;
|
||||||
insertDebugMarker(markerLabel: string): undefined;
|
insertDebugMarker(markerLabel: string): undefined;
|
||||||
setPipeline(pipeline: GPUComputePipeline): undefined;
|
setPipeline(pipeline: GPUComputePipeline): undefined;
|
||||||
dispatch(x: number, y?: number, z?: number): undefined;
|
dispatchWorkgroups(x: number, y?: number, z?: number): undefined;
|
||||||
dispatchIndirect(
|
dispatchWorkgroupsIndirect(
|
||||||
indirectBuffer: GPUBuffer,
|
indirectBuffer: GPUBuffer,
|
||||||
indirectOffset: number,
|
indirectOffset: number,
|
||||||
): undefined;
|
): undefined;
|
||||||
|
@ -844,7 +854,7 @@ declare class GPUComputePassEncoder
|
||||||
|
|
||||||
writeTimestamp(querySet: GPUQuerySet, queryIndex: number): undefined;
|
writeTimestamp(querySet: GPUQuerySet, queryIndex: number): undefined;
|
||||||
|
|
||||||
endPass(): undefined;
|
end(): undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPUComputePassDescriptor extends GPUObjectDescriptorBase {}
|
declare interface GPUComputePassDescriptor extends GPUObjectDescriptorBase {}
|
||||||
|
@ -888,7 +898,7 @@ interface GPURenderEncoderBase {
|
||||||
|
|
||||||
declare class GPURenderPassEncoder
|
declare class GPURenderPassEncoder
|
||||||
implements GPUObjectBase, GPUProgrammablePassEncoder, GPURenderEncoderBase {
|
implements GPUObjectBase, GPUProgrammablePassEncoder, GPURenderEncoderBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
setBindGroup(
|
setBindGroup(
|
||||||
index: number,
|
index: number,
|
||||||
bindGroup: GPUBindGroup,
|
bindGroup: GPUBindGroup,
|
||||||
|
@ -967,11 +977,11 @@ declare class GPURenderPassEncoder
|
||||||
writeTimestamp(querySet: GPUQuerySet, queryIndex: number): undefined;
|
writeTimestamp(querySet: GPUQuerySet, queryIndex: number): undefined;
|
||||||
|
|
||||||
executeBundles(bundles: GPURenderBundle[]): undefined;
|
executeBundles(bundles: GPURenderBundle[]): undefined;
|
||||||
endPass(): undefined;
|
end(): undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPURenderPassDescriptor extends GPUObjectDescriptorBase {
|
declare interface GPURenderPassDescriptor extends GPUObjectDescriptorBase {
|
||||||
colorAttachments: GPURenderPassColorAttachment[];
|
colorAttachments: (GPURenderPassColorAttachment | null)[];
|
||||||
depthStencilAttachment?: GPURenderPassDepthStencilAttachment;
|
depthStencilAttachment?: GPURenderPassDepthStencilAttachment;
|
||||||
occlusionQuerySet?: GPUQuerySet;
|
occlusionQuerySet?: GPUQuerySet;
|
||||||
}
|
}
|
||||||
|
@ -980,35 +990,38 @@ declare interface GPURenderPassColorAttachment {
|
||||||
view: GPUTextureView;
|
view: GPUTextureView;
|
||||||
resolveTarget?: GPUTextureView;
|
resolveTarget?: GPUTextureView;
|
||||||
|
|
||||||
loadValue: GPULoadOp | GPUColor;
|
clearValue?: GPUColor;
|
||||||
storeOp?: GPUStoreOp;
|
loadOp: GPULoadOp;
|
||||||
|
storeOp: GPUStoreOp;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPURenderPassDepthStencilAttachment {
|
declare interface GPURenderPassDepthStencilAttachment {
|
||||||
view: GPUTextureView;
|
view: GPUTextureView;
|
||||||
|
|
||||||
depthLoadValue: GPULoadOp | number;
|
depthClearValue?: number;
|
||||||
depthStoreOp: GPUStoreOp;
|
depthLoadOp?: GPULoadOp;
|
||||||
|
depthStoreOp?: GPUStoreOp;
|
||||||
depthReadOnly?: boolean;
|
depthReadOnly?: boolean;
|
||||||
|
|
||||||
stencilLoadValue: GPULoadOp | number;
|
stencilClearValue?: number;
|
||||||
stencilStoreOp: GPUStoreOp;
|
stencilLoadOp?: GPULoadOp;
|
||||||
|
stencilStoreOp?: GPUStoreOp;
|
||||||
stencilReadOnly?: boolean;
|
stencilReadOnly?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare type GPULoadOp = "load";
|
declare type GPULoadOp = "load" | "clear";
|
||||||
|
|
||||||
declare type GPUStoreOp = "store" | "discard";
|
declare type GPUStoreOp = "store" | "discard";
|
||||||
|
|
||||||
declare class GPURenderBundle implements GPUObjectBase {
|
declare class GPURenderBundle implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPURenderBundleDescriptor extends GPUObjectDescriptorBase {}
|
declare interface GPURenderBundleDescriptor extends GPUObjectDescriptorBase {}
|
||||||
|
|
||||||
declare class GPURenderBundleEncoder
|
declare class GPURenderBundleEncoder
|
||||||
implements GPUObjectBase, GPUProgrammablePassEncoder, GPURenderEncoderBase {
|
implements GPUObjectBase, GPUProgrammablePassEncoder, GPURenderEncoderBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
draw(
|
draw(
|
||||||
vertexCount: number,
|
vertexCount: number,
|
||||||
instanceCount?: number,
|
instanceCount?: number,
|
||||||
|
@ -1060,7 +1073,7 @@ declare class GPURenderBundleEncoder
|
||||||
}
|
}
|
||||||
|
|
||||||
declare interface GPURenderPassLayout extends GPUObjectDescriptorBase {
|
declare interface GPURenderPassLayout extends GPUObjectDescriptorBase {
|
||||||
colorFormats: GPUTextureFormat[];
|
colorFormats: (GPUTextureFormat | null)[];
|
||||||
depthStencilFormat?: GPUTextureFormat;
|
depthStencilFormat?: GPUTextureFormat;
|
||||||
sampleCount?: number;
|
sampleCount?: number;
|
||||||
}
|
}
|
||||||
|
@ -1071,7 +1084,7 @@ declare interface GPURenderBundleEncoderDescriptor extends GPURenderPassLayout {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUQueue implements GPUObjectBase {
|
declare class GPUQueue implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
submit(commandBuffers: GPUCommandBuffer[]): undefined;
|
submit(commandBuffers: GPUCommandBuffer[]): undefined;
|
||||||
|
|
||||||
|
@ -1094,7 +1107,7 @@ declare class GPUQueue implements GPUObjectBase {
|
||||||
}
|
}
|
||||||
|
|
||||||
declare class GPUQuerySet implements GPUObjectBase {
|
declare class GPUQuerySet implements GPUObjectBase {
|
||||||
label: string | null;
|
label: string;
|
||||||
|
|
||||||
destroy(): undefined;
|
destroy(): undefined;
|
||||||
}
|
}
|
||||||
|
@ -1121,18 +1134,19 @@ declare interface GPUDeviceLostInfo {
|
||||||
readonly message: string;
|
readonly message: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare type GPUErrorFilter = "out-of-memory" | "validation";
|
declare class GPUError {
|
||||||
|
|
||||||
declare class GPUOutOfMemoryError {
|
|
||||||
constructor();
|
|
||||||
}
|
|
||||||
|
|
||||||
declare class GPUValidationError {
|
|
||||||
constructor(message: string);
|
|
||||||
readonly message: string;
|
readonly message: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare type GPUError = GPUOutOfMemoryError | GPUValidationError;
|
declare type GPUErrorFilter = "out-of-memory" | "validation";
|
||||||
|
|
||||||
|
declare class GPUOutOfMemoryError extends GPUError {
|
||||||
|
constructor(message: string);
|
||||||
|
}
|
||||||
|
|
||||||
|
declare class GPUValidationError extends GPUError {
|
||||||
|
constructor(message: string);
|
||||||
|
}
|
||||||
|
|
||||||
declare class GPUUncapturedErrorEvent extends Event {
|
declare class GPUUncapturedErrorEvent extends Event {
|
||||||
constructor(
|
constructor(
|
||||||
|
|
|
@ -1,9 +1,6 @@
|
||||||
struct PrimeIndices {
|
@group(0)
|
||||||
data: [[stride(4)]] array<u32>;
|
@binding(0)
|
||||||
}; // this is used as both input and output for convenience
|
var<storage, read_write> v_indices: array<u32>; // this is used as both input and output for convenience
|
||||||
|
|
||||||
[[group(0), binding(0)]]
|
|
||||||
var<storage, read_write> v_indices: PrimeIndices;
|
|
||||||
|
|
||||||
// The Collatz Conjecture states that for any integer n:
|
// The Collatz Conjecture states that for any integer n:
|
||||||
// If n is even, n = n/2
|
// If n is even, n = n/2
|
||||||
|
@ -34,7 +31,8 @@ fn collatz_iterations(n_base: u32) -> u32{
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
[[stage(compute), workgroup_size(1)]]
|
@compute
|
||||||
fn main([[builtin(global_invocation_id)]] global_id: vec3<u32>) {
|
@workgroup_size(1)
|
||||||
v_indices.data[global_id.x] = collatz_iterations(v_indices.data[global_id.x]);
|
fn main(@builtin(global_invocation_id) global_id: vec3<u32>) {
|
||||||
|
v_indices[global_id.x] = collatz_iterations(v_indices[global_id.x]);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,10 +1,11 @@
|
||||||
[[stage(vertex)]]
|
@vertex
|
||||||
fn vs_main([[builtin(vertex_index)]] in_vertex_index: u32) -> [[builtin(position)]] vec4<f32> {
|
fn vs_main(@builtin(vertex_index) in_vertex_index: u32) -> @builtin(position) vec4<f32> {
|
||||||
let x = f32(i32(in_vertex_index) - 1);
|
let x = f32(i32(in_vertex_index) - 1);
|
||||||
let y = f32(i32(in_vertex_index & 1u) * 2 - 1);
|
let y = f32(i32(in_vertex_index & 1u) * 2 - 1);
|
||||||
return vec4<f32>(x, y, 0.0, 1.0);
|
return vec4<f32>(x, y, 0.0, 1.0);
|
||||||
}
|
}
|
||||||
[[stage(fragment)]]
|
|
||||||
fn fs_main() -> [[location(0)]] vec4<f32> {
|
@fragment
|
||||||
|
fn fs_main() -> @location(0) vec4<f32> {
|
||||||
return vec4<f32>(1.0, 0.0, 0.0, 1.0);
|
return vec4<f32>(1.0, 0.0, 0.0, 1.0);
|
||||||
}
|
}
|
||||||
|
|
|
@ -56,6 +56,7 @@ Deno.test({
|
||||||
storageBuffer.unmap();
|
storageBuffer.unmap();
|
||||||
|
|
||||||
const computePipeline = device.createComputePipeline({
|
const computePipeline = device.createComputePipeline({
|
||||||
|
layout: "auto",
|
||||||
compute: {
|
compute: {
|
||||||
module: shaderModule,
|
module: shaderModule,
|
||||||
entryPoint: "main",
|
entryPoint: "main",
|
||||||
|
@ -81,8 +82,8 @@ Deno.test({
|
||||||
computePass.setPipeline(computePipeline);
|
computePass.setPipeline(computePipeline);
|
||||||
computePass.setBindGroup(0, bindGroup);
|
computePass.setBindGroup(0, bindGroup);
|
||||||
computePass.insertDebugMarker("compute collatz iterations");
|
computePass.insertDebugMarker("compute collatz iterations");
|
||||||
computePass.dispatch(numbers.length);
|
computePass.dispatchWorkgroups(numbers.length);
|
||||||
computePass.endPass();
|
computePass.end();
|
||||||
|
|
||||||
encoder.copyBufferToBuffer(storageBuffer, 0, stagingBuffer, 0, size);
|
encoder.copyBufferToBuffer(storageBuffer, 0, stagingBuffer, 0, size);
|
||||||
|
|
||||||
|
@ -172,13 +173,14 @@ Deno.test({
|
||||||
{
|
{
|
||||||
view,
|
view,
|
||||||
storeOp: "store",
|
storeOp: "store",
|
||||||
loadValue: [0, 1, 0, 1],
|
loadOp: "clear",
|
||||||
|
clearValue: [0, 1, 0, 1],
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
renderPass.setPipeline(renderPipeline);
|
renderPass.setPipeline(renderPipeline);
|
||||||
renderPass.draw(3, 1);
|
renderPass.draw(3, 1);
|
||||||
renderPass.endPass();
|
renderPass.end();
|
||||||
|
|
||||||
encoder.copyTextureToBuffer(
|
encoder.copyTextureToBuffer(
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
# Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
|
# Copyright 2018-2022 the Deno authors. All rights reserved. MIT license.
|
||||||
|
|
||||||
[package]
|
[package]
|
||||||
name = "deno_webgpu"
|
name = "deno_webgpu"
|
||||||
|
@ -14,5 +14,5 @@ description = "WebGPU implementation for Deno"
|
||||||
deno_core = { version = "0.143.0", path = "../../core" }
|
deno_core = { version = "0.143.0", path = "../../core" }
|
||||||
serde = { version = "1.0", features = ["derive"] }
|
serde = { version = "1.0", features = ["derive"] }
|
||||||
tokio = { version = "1.17", features = ["full"] }
|
tokio = { version = "1.17", features = ["full"] }
|
||||||
wgpu-core = { version = "0.12", features = ["trace", "replay", "serde"] }
|
wgpu-core = { version = "0.13", features = ["trace", "replay", "serde"] }
|
||||||
wgpu-types = { version = "0.12", features = ["trace", "replay", "serde"] }
|
wgpu-types = { version = "0.13", features = ["trace", "replay", "serde"] }
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
MIT License
|
MIT License
|
||||||
|
|
||||||
Copyright 2018-2021 the Deno authors
|
Copyright 2018-2022 the Deno authors
|
||||||
|
|
||||||
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||||
this software and associated documentation files (the "Software"), to deal in
|
this software and associated documentation files (the "Software"), to deal in
|
||||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -120,6 +120,7 @@
|
||||||
"texture-compression-astc",
|
"texture-compression-astc",
|
||||||
"timestamp-query",
|
"timestamp-query",
|
||||||
"indirect-first-instance",
|
"indirect-first-instance",
|
||||||
|
"shader-f16",
|
||||||
// extended from spec
|
// extended from spec
|
||||||
"mappable-primary-buffers",
|
"mappable-primary-buffers",
|
||||||
"texture-binding-array",
|
"texture-binding-array",
|
||||||
|
@ -341,6 +342,8 @@
|
||||||
"depth24plus",
|
"depth24plus",
|
||||||
"depth24plus-stencil8",
|
"depth24plus-stencil8",
|
||||||
"depth32float",
|
"depth32float",
|
||||||
|
"depth24unorm-stencil8",
|
||||||
|
"depth32float-stencil8",
|
||||||
"bc1-rgba-unorm",
|
"bc1-rgba-unorm",
|
||||||
"bc1-rgba-unorm-srgb",
|
"bc1-rgba-unorm-srgb",
|
||||||
"bc2-rgba-unorm",
|
"bc2-rgba-unorm",
|
||||||
|
@ -393,8 +396,6 @@
|
||||||
"astc-12x10-unorm-srgb",
|
"astc-12x10-unorm-srgb",
|
||||||
"astc-12x12-unorm",
|
"astc-12x12-unorm",
|
||||||
"astc-12x12-unorm-srgb",
|
"astc-12x12-unorm-srgb",
|
||||||
"depth24unorm-stencil8",
|
|
||||||
"depth32float-stencil8",
|
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -539,6 +540,15 @@
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
|
|
||||||
|
// ENUM: GPUMipmapFilterMode
|
||||||
|
webidl.converters["GPUMipmapFilterMode"] = webidl.createEnumConverter(
|
||||||
|
"GPUMipmapFilterMode",
|
||||||
|
[
|
||||||
|
"nearest",
|
||||||
|
"linear",
|
||||||
|
],
|
||||||
|
);
|
||||||
|
|
||||||
// ENUM: GPUCompareFunction
|
// ENUM: GPUCompareFunction
|
||||||
webidl.converters["GPUCompareFunction"] = webidl.createEnumConverter(
|
webidl.converters["GPUCompareFunction"] = webidl.createEnumConverter(
|
||||||
"GPUCompareFunction",
|
"GPUCompareFunction",
|
||||||
|
@ -583,7 +593,7 @@
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: "mipmapFilter",
|
key: "mipmapFilter",
|
||||||
converter: webidl.converters["GPUFilterMode"],
|
converter: webidl.converters["GPUMipmapFilterMode"],
|
||||||
defaultValue: "nearest",
|
defaultValue: "nearest",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -935,9 +945,26 @@
|
||||||
// GPUCompilationInfo.prototype,
|
// GPUCompilationInfo.prototype,
|
||||||
// );
|
// );
|
||||||
|
|
||||||
|
webidl.converters["GPUAutoLayoutMode"] = webidl.createEnumConverter(
|
||||||
|
"GPUAutoLayoutMode",
|
||||||
|
[
|
||||||
|
"auto",
|
||||||
|
],
|
||||||
|
);
|
||||||
|
|
||||||
|
webidl.converters["GPUPipelineLayout or GPUAutoLayoutMode"] = (V, opts) => {
|
||||||
|
if (typeof V === "object") {
|
||||||
|
return webidl.converters["GPUPipelineLayout"](V, opts);
|
||||||
|
}
|
||||||
|
return webidl.converters["GPUAutoLayoutMode"](V, opts);
|
||||||
|
};
|
||||||
|
|
||||||
// DICTIONARY: GPUPipelineDescriptorBase
|
// DICTIONARY: GPUPipelineDescriptorBase
|
||||||
const dictMembersGPUPipelineDescriptorBase = [
|
const dictMembersGPUPipelineDescriptorBase = [
|
||||||
{ key: "layout", converter: webidl.converters["GPUPipelineLayout"] },
|
{
|
||||||
|
key: "layout",
|
||||||
|
converter: webidl.converters["GPUPipelineLayout or GPUAutoLayoutMode"],
|
||||||
|
},
|
||||||
];
|
];
|
||||||
webidl.converters["GPUPipelineDescriptorBase"] = webidl
|
webidl.converters["GPUPipelineDescriptorBase"] = webidl
|
||||||
.createDictionaryConverter(
|
.createDictionaryConverter(
|
||||||
|
@ -1427,7 +1454,9 @@
|
||||||
{
|
{
|
||||||
key: "targets",
|
key: "targets",
|
||||||
converter: webidl.createSequenceConverter(
|
converter: webidl.createSequenceConverter(
|
||||||
webidl.converters["GPUColorTargetState"],
|
webidl.createNullableConverter(
|
||||||
|
webidl.converters["GPUColorTargetState"],
|
||||||
|
),
|
||||||
),
|
),
|
||||||
required: true,
|
required: true,
|
||||||
},
|
},
|
||||||
|
@ -1675,6 +1704,7 @@
|
||||||
// ENUM: GPULoadOp
|
// ENUM: GPULoadOp
|
||||||
webidl.converters["GPULoadOp"] = webidl.createEnumConverter("GPULoadOp", [
|
webidl.converters["GPULoadOp"] = webidl.createEnumConverter("GPULoadOp", [
|
||||||
"load",
|
"load",
|
||||||
|
"clear",
|
||||||
]);
|
]);
|
||||||
|
|
||||||
// DICTIONARY: GPUColorDict
|
// DICTIONARY: GPUColorDict
|
||||||
|
@ -1724,8 +1754,12 @@
|
||||||
},
|
},
|
||||||
{ key: "resolveTarget", converter: webidl.converters["GPUTextureView"] },
|
{ key: "resolveTarget", converter: webidl.converters["GPUTextureView"] },
|
||||||
{
|
{
|
||||||
key: "loadValue",
|
key: "clearValue",
|
||||||
converter: webidl.converters.any, /** put union here! **/
|
converter: webidl.converters["GPUColor"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
key: "loadOp",
|
||||||
|
converter: webidl.converters["GPULoadOp"],
|
||||||
required: true,
|
required: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -1748,14 +1782,17 @@
|
||||||
required: true,
|
required: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: "depthLoadValue",
|
key: "depthClearValue",
|
||||||
converter: webidl.converters.any, /** put union here! **/
|
converter: webidl.converters["float"],
|
||||||
required: true,
|
defaultValue: 0,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
key: "depthLoadOp",
|
||||||
|
converter: webidl.converters["GPULoadOp"],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: "depthStoreOp",
|
key: "depthStoreOp",
|
||||||
converter: webidl.converters["GPUStoreOp"],
|
converter: webidl.converters["GPUStoreOp"],
|
||||||
required: true,
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: "depthReadOnly",
|
key: "depthReadOnly",
|
||||||
|
@ -1763,14 +1800,17 @@
|
||||||
defaultValue: false,
|
defaultValue: false,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: "stencilLoadValue",
|
key: "stencilClearValue",
|
||||||
converter: webidl.converters.any, /** put union here! **/
|
converter: webidl.converters["GPUStencilValue"],
|
||||||
required: true,
|
defaultValue: 0,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
key: "stencilLoadOp",
|
||||||
|
converter: webidl.converters["GPULoadOp"],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: "stencilStoreOp",
|
key: "stencilStoreOp",
|
||||||
converter: webidl.converters["GPUStoreOp"],
|
converter: webidl.converters["GPUStoreOp"],
|
||||||
required: true,
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: "stencilReadOnly",
|
key: "stencilReadOnly",
|
||||||
|
@ -1795,7 +1835,9 @@
|
||||||
{
|
{
|
||||||
key: "colorAttachments",
|
key: "colorAttachments",
|
||||||
converter: webidl.createSequenceConverter(
|
converter: webidl.createSequenceConverter(
|
||||||
webidl.converters["GPURenderPassColorAttachment"],
|
webidl.createNullableConverter(
|
||||||
|
webidl.converters["GPURenderPassColorAttachment"],
|
||||||
|
),
|
||||||
),
|
),
|
||||||
required: true,
|
required: true,
|
||||||
},
|
},
|
||||||
|
@ -1840,7 +1882,7 @@
|
||||||
{
|
{
|
||||||
key: "colorFormats",
|
key: "colorFormats",
|
||||||
converter: webidl.createSequenceConverter(
|
converter: webidl.createSequenceConverter(
|
||||||
webidl.converters["GPUTextureFormat"],
|
webidl.createNullableConverter(webidl.converters["GPUTextureFormat"]),
|
||||||
),
|
),
|
||||||
required: true,
|
required: true,
|
||||||
},
|
},
|
||||||
|
|
|
@ -2,11 +2,11 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::convert::{TryFrom, TryInto};
|
|
||||||
|
|
||||||
use super::error::WebGpuResult;
|
use super::error::WebGpuResult;
|
||||||
|
|
||||||
|
@ -122,7 +122,7 @@ impl From<GpuStorageTextureAccess> for wgpu_types::StorageTextureAccess {
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
struct GpuBindGroupLayoutEntry {
|
pub struct GpuBindGroupLayoutEntry {
|
||||||
binding: u32,
|
binding: u32,
|
||||||
visibility: u32,
|
visibility: u32,
|
||||||
#[serde(flatten)]
|
#[serde(flatten)]
|
||||||
|
@ -138,13 +138,9 @@ enum GpuBindingType {
|
||||||
StorageTexture(GpuStorageTextureBindingLayout),
|
StorageTexture(GpuStorageTextureBindingLayout),
|
||||||
}
|
}
|
||||||
|
|
||||||
impl TryFrom<GpuBindingType> for wgpu_types::BindingType {
|
impl From<GpuBindingType> for wgpu_types::BindingType {
|
||||||
type Error = AnyError;
|
fn from(binding_type: GpuBindingType) -> wgpu_types::BindingType {
|
||||||
|
match binding_type {
|
||||||
fn try_from(
|
|
||||||
binding_type: GpuBindingType,
|
|
||||||
) -> Result<wgpu_types::BindingType, Self::Error> {
|
|
||||||
let binding_type = match binding_type {
|
|
||||||
GpuBindingType::Buffer(buffer) => wgpu_types::BindingType::Buffer {
|
GpuBindingType::Buffer(buffer) => wgpu_types::BindingType::Buffer {
|
||||||
ty: buffer.r#type.into(),
|
ty: buffer.r#type.into(),
|
||||||
has_dynamic_offset: buffer.has_dynamic_offset,
|
has_dynamic_offset: buffer.has_dynamic_offset,
|
||||||
|
@ -165,44 +161,38 @@ impl TryFrom<GpuBindingType> for wgpu_types::BindingType {
|
||||||
view_dimension: storage_texture.view_dimension,
|
view_dimension: storage_texture.view_dimension,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
Ok(binding_type)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CreateBindGroupLayoutArgs {
|
|
||||||
device_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
entries: Vec<GpuBindGroupLayoutEntry>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_create_bind_group_layout(
|
pub fn op_webgpu_create_bind_group_layout(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CreateBindGroupLayoutArgs,
|
device_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
|
entries: Vec<GpuBindGroupLayoutEntry>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let device_resource = state
|
let device_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let mut entries = vec![];
|
let entries = entries
|
||||||
|
.into_iter()
|
||||||
for entry in args.entries {
|
.map(|entry| {
|
||||||
entries.push(wgpu_types::BindGroupLayoutEntry {
|
wgpu_types::BindGroupLayoutEntry {
|
||||||
binding: entry.binding,
|
binding: entry.binding,
|
||||||
visibility: wgpu_types::ShaderStages::from_bits(entry.visibility)
|
visibility: wgpu_types::ShaderStages::from_bits(entry.visibility)
|
||||||
.unwrap(),
|
.unwrap(),
|
||||||
ty: entry.binding_type.try_into()?,
|
ty: entry.binding_type.into(),
|
||||||
count: None, // native-only
|
count: None, // native-only
|
||||||
});
|
}
|
||||||
}
|
})
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
let descriptor = wgpu_core::binding_model::BindGroupLayoutDescriptor {
|
let descriptor = wgpu_core::binding_model::BindGroupLayoutDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
entries: Cow::from(entries),
|
entries: Cow::from(entries),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -213,35 +203,30 @@ pub fn op_webgpu_create_bind_group_layout(
|
||||||
) => state, WebGpuBindGroupLayout)
|
) => state, WebGpuBindGroupLayout)
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CreatePipelineLayoutArgs {
|
|
||||||
device_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
bind_group_layouts: Vec<u32>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_create_pipeline_layout(
|
pub fn op_webgpu_create_pipeline_layout(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CreatePipelineLayoutArgs,
|
device_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
|
bind_group_layouts: Vec<u32>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let device_resource = state
|
let device_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let mut bind_group_layouts = vec![];
|
let bind_group_layouts = bind_group_layouts
|
||||||
|
.into_iter()
|
||||||
for rid in &args.bind_group_layouts {
|
.map(|rid| {
|
||||||
let bind_group_layout =
|
let bind_group_layout =
|
||||||
state.resource_table.get::<WebGpuBindGroupLayout>(*rid)?;
|
state.resource_table.get::<WebGpuBindGroupLayout>(rid)?;
|
||||||
bind_group_layouts.push(bind_group_layout.0);
|
Ok(bind_group_layout.0)
|
||||||
}
|
})
|
||||||
|
.collect::<Result<Vec<_>, AnyError>>()?;
|
||||||
|
|
||||||
let descriptor = wgpu_core::binding_model::PipelineLayoutDescriptor {
|
let descriptor = wgpu_core::binding_model::PipelineLayoutDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
bind_group_layouts: Cow::from(bind_group_layouts),
|
bind_group_layouts: Cow::from(bind_group_layouts),
|
||||||
push_constant_ranges: Default::default(),
|
push_constant_ranges: Default::default(),
|
||||||
};
|
};
|
||||||
|
@ -255,7 +240,7 @@ pub fn op_webgpu_create_pipeline_layout(
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
struct GpuBindGroupEntry {
|
pub struct GpuBindGroupEntry {
|
||||||
binding: u32,
|
binding: u32,
|
||||||
kind: String,
|
kind: String,
|
||||||
resource: ResourceId,
|
resource: ResourceId,
|
||||||
|
@ -263,73 +248,68 @@ struct GpuBindGroupEntry {
|
||||||
size: Option<u64>,
|
size: Option<u64>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_create_bind_group(
|
||||||
pub struct CreateBindGroupArgs {
|
state: &mut OpState,
|
||||||
device_rid: ResourceId,
|
device_rid: ResourceId,
|
||||||
label: Option<String>,
|
label: Option<String>,
|
||||||
layout: ResourceId,
|
layout: ResourceId,
|
||||||
entries: Vec<GpuBindGroupEntry>,
|
entries: Vec<GpuBindGroupEntry>,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_create_bind_group(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: CreateBindGroupArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let device_resource = state
|
let device_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let mut entries = vec![];
|
let entries = entries
|
||||||
|
.into_iter()
|
||||||
|
.map(|entry| {
|
||||||
|
Ok(wgpu_core::binding_model::BindGroupEntry {
|
||||||
|
binding: entry.binding,
|
||||||
|
resource: match entry.kind.as_str() {
|
||||||
|
"GPUSampler" => {
|
||||||
|
let sampler_resource =
|
||||||
|
state
|
||||||
|
.resource_table
|
||||||
|
.get::<super::sampler::WebGpuSampler>(entry.resource)?;
|
||||||
|
wgpu_core::binding_model::BindingResource::Sampler(
|
||||||
|
sampler_resource.0,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
"GPUTextureView" => {
|
||||||
|
let texture_view_resource =
|
||||||
|
state
|
||||||
|
.resource_table
|
||||||
|
.get::<super::texture::WebGpuTextureView>(entry.resource)?;
|
||||||
|
wgpu_core::binding_model::BindingResource::TextureView(
|
||||||
|
texture_view_resource.0,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
"GPUBufferBinding" => {
|
||||||
|
let buffer_resource =
|
||||||
|
state
|
||||||
|
.resource_table
|
||||||
|
.get::<super::buffer::WebGpuBuffer>(entry.resource)?;
|
||||||
|
wgpu_core::binding_model::BindingResource::Buffer(
|
||||||
|
wgpu_core::binding_model::BufferBinding {
|
||||||
|
buffer_id: buffer_resource.0,
|
||||||
|
offset: entry.offset.unwrap_or(0),
|
||||||
|
size: std::num::NonZeroU64::new(entry.size.unwrap_or(0)),
|
||||||
|
},
|
||||||
|
)
|
||||||
|
}
|
||||||
|
_ => unreachable!(),
|
||||||
|
},
|
||||||
|
})
|
||||||
|
})
|
||||||
|
.collect::<Result<Vec<_>, AnyError>>()?;
|
||||||
|
|
||||||
for entry in &args.entries {
|
let bind_group_layout =
|
||||||
let e = wgpu_core::binding_model::BindGroupEntry {
|
state.resource_table.get::<WebGpuBindGroupLayout>(layout)?;
|
||||||
binding: entry.binding,
|
|
||||||
resource: match entry.kind.as_str() {
|
|
||||||
"GPUSampler" => {
|
|
||||||
let sampler_resource =
|
|
||||||
state
|
|
||||||
.resource_table
|
|
||||||
.get::<super::sampler::WebGpuSampler>(entry.resource)?;
|
|
||||||
wgpu_core::binding_model::BindingResource::Sampler(sampler_resource.0)
|
|
||||||
}
|
|
||||||
"GPUTextureView" => {
|
|
||||||
let texture_view_resource =
|
|
||||||
state
|
|
||||||
.resource_table
|
|
||||||
.get::<super::texture::WebGpuTextureView>(entry.resource)?;
|
|
||||||
wgpu_core::binding_model::BindingResource::TextureView(
|
|
||||||
texture_view_resource.0,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
"GPUBufferBinding" => {
|
|
||||||
let buffer_resource =
|
|
||||||
state
|
|
||||||
.resource_table
|
|
||||||
.get::<super::buffer::WebGpuBuffer>(entry.resource)?;
|
|
||||||
wgpu_core::binding_model::BindingResource::Buffer(
|
|
||||||
wgpu_core::binding_model::BufferBinding {
|
|
||||||
buffer_id: buffer_resource.0,
|
|
||||||
offset: entry.offset.unwrap_or(0),
|
|
||||||
size: std::num::NonZeroU64::new(entry.size.unwrap_or(0)),
|
|
||||||
},
|
|
||||||
)
|
|
||||||
}
|
|
||||||
_ => unreachable!(),
|
|
||||||
},
|
|
||||||
};
|
|
||||||
entries.push(e);
|
|
||||||
}
|
|
||||||
|
|
||||||
let bind_group_layout = state
|
|
||||||
.resource_table
|
|
||||||
.get::<WebGpuBindGroupLayout>(args.layout)?;
|
|
||||||
|
|
||||||
let descriptor = wgpu_core::binding_model::BindGroupDescriptor {
|
let descriptor = wgpu_core::binding_model::BindGroupDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
layout: bind_group_layout.0,
|
layout: bind_group_layout.0,
|
||||||
entries: Cow::from(entries),
|
entries: Cow::from(entries),
|
||||||
};
|
};
|
||||||
|
|
|
@ -4,14 +4,13 @@ use deno_core::error::type_error;
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::futures::channel::oneshot;
|
use deno_core::futures::channel::oneshot;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
|
||||||
use deno_core::OpState;
|
use deno_core::OpState;
|
||||||
use deno_core::Resource;
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::ZeroCopyBuf;
|
use deno_core::ZeroCopyBuf;
|
||||||
use serde::Deserialize;
|
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
|
use std::convert::TryFrom;
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
|
@ -32,33 +31,27 @@ impl Resource for WebGpuBufferMapped {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_create_buffer(
|
||||||
pub struct CreateBufferArgs {
|
state: &mut OpState,
|
||||||
device_rid: ResourceId,
|
device_rid: ResourceId,
|
||||||
label: Option<String>,
|
label: Option<String>,
|
||||||
size: u64,
|
size: u64,
|
||||||
usage: u32,
|
usage: u32,
|
||||||
mapped_at_creation: bool,
|
mapped_at_creation: bool,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_create_buffer(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: CreateBufferArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let device_resource = state
|
let device_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let descriptor = wgpu_core::resource::BufferDescriptor {
|
let descriptor = wgpu_core::resource::BufferDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
size: args.size,
|
size,
|
||||||
usage: wgpu_types::BufferUsages::from_bits(args.usage)
|
usage: wgpu_types::BufferUsages::from_bits(usage)
|
||||||
.ok_or_else(|| type_error("usage is not valid"))?,
|
.ok_or_else(|| type_error("usage is not valid"))?,
|
||||||
mapped_at_creation: args.mapped_at_creation,
|
mapped_at_creation,
|
||||||
};
|
};
|
||||||
|
|
||||||
gfx_put!(device => instance.device_create_buffer(
|
gfx_put!(device => instance.device_create_buffer(
|
||||||
|
@ -68,20 +61,14 @@ pub fn op_webgpu_create_buffer(
|
||||||
) => state, WebGpuBuffer)
|
) => state, WebGpuBuffer)
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub async fn op_webgpu_buffer_get_map_async(
|
||||||
pub struct BufferGetMapAsyncArgs {
|
state: Rc<RefCell<OpState>>,
|
||||||
buffer_rid: ResourceId,
|
buffer_rid: ResourceId,
|
||||||
device_rid: ResourceId,
|
device_rid: ResourceId,
|
||||||
mode: u32,
|
mode: u32,
|
||||||
offset: u64,
|
offset: u64,
|
||||||
size: u64,
|
size: u64,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub async fn op_webgpu_buffer_get_map_async(
|
|
||||||
state: Rc<RefCell<OpState>>,
|
|
||||||
args: BufferGetMapAsyncArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let (sender, receiver) = oneshot::channel::<Result<(), AnyError>>();
|
let (sender, receiver) = oneshot::channel::<Result<(), AnyError>>();
|
||||||
|
|
||||||
|
@ -90,47 +77,36 @@ pub async fn op_webgpu_buffer_get_map_async(
|
||||||
let state_ = state.borrow();
|
let state_ = state.borrow();
|
||||||
let instance = state_.borrow::<super::Instance>();
|
let instance = state_.borrow::<super::Instance>();
|
||||||
let buffer_resource =
|
let buffer_resource =
|
||||||
state_.resource_table.get::<WebGpuBuffer>(args.buffer_rid)?;
|
state_.resource_table.get::<WebGpuBuffer>(buffer_rid)?;
|
||||||
let buffer = buffer_resource.0;
|
let buffer = buffer_resource.0;
|
||||||
let device_resource = state_
|
let device_resource = state_
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
device = device_resource.0;
|
device = device_resource.0;
|
||||||
|
|
||||||
let boxed_sender = Box::new(sender);
|
let callback = Box::new(move |status| {
|
||||||
let sender_ptr = Box::into_raw(boxed_sender) as *mut u8;
|
sender
|
||||||
|
|
||||||
extern "C" fn buffer_map_future_wrapper(
|
|
||||||
status: wgpu_core::resource::BufferMapAsyncStatus,
|
|
||||||
user_data: *mut u8,
|
|
||||||
) {
|
|
||||||
let sender_ptr = user_data as *mut oneshot::Sender<Result<(), AnyError>>;
|
|
||||||
// TODO(bartlomieju):
|
|
||||||
#[allow(clippy::undocumented_unsafe_blocks)]
|
|
||||||
let boxed_sender = unsafe { Box::from_raw(sender_ptr) };
|
|
||||||
boxed_sender
|
|
||||||
.send(match status {
|
.send(match status {
|
||||||
wgpu_core::resource::BufferMapAsyncStatus::Success => Ok(()),
|
wgpu_core::resource::BufferMapAsyncStatus::Success => Ok(()),
|
||||||
_ => unreachable!(), // TODO
|
_ => unreachable!(), // TODO
|
||||||
})
|
})
|
||||||
.unwrap();
|
.unwrap();
|
||||||
}
|
});
|
||||||
|
|
||||||
// TODO(lucacasonato): error handling
|
// TODO(lucacasonato): error handling
|
||||||
let maybe_err = gfx_select!(buffer => instance.buffer_map_async(
|
let maybe_err = gfx_select!(buffer => instance.buffer_map_async(
|
||||||
buffer,
|
buffer,
|
||||||
args.offset..(args.offset + args.size),
|
offset..(offset + size),
|
||||||
wgpu_core::resource::BufferMapOperation {
|
wgpu_core::resource::BufferMapOperation {
|
||||||
host: match args.mode {
|
host: match mode {
|
||||||
1 => wgpu_core::device::HostMap::Read,
|
1 => wgpu_core::device::HostMap::Read,
|
||||||
2 => wgpu_core::device::HostMap::Write,
|
2 => wgpu_core::device::HostMap::Write,
|
||||||
_ => unreachable!(),
|
_ => unreachable!(),
|
||||||
},
|
},
|
||||||
callback: buffer_map_future_wrapper,
|
callback: wgpu_core::resource::BufferMapCallback::from_rust(callback),
|
||||||
user_data: sender_ptr,
|
}
|
||||||
}
|
))
|
||||||
))
|
.err();
|
||||||
.err();
|
|
||||||
|
|
||||||
if maybe_err.is_some() {
|
if maybe_err.is_some() {
|
||||||
return Ok(WebGpuResult::maybe_err(maybe_err));
|
return Ok(WebGpuResult::maybe_err(maybe_err));
|
||||||
|
@ -144,7 +120,7 @@ pub async fn op_webgpu_buffer_get_map_async(
|
||||||
{
|
{
|
||||||
let state = state.borrow();
|
let state = state.borrow();
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
gfx_select!(device => instance.device_poll(device, false)).unwrap()
|
gfx_select!(device => instance.device_poll(device, wgpu_types::Maintain::Wait)).unwrap();
|
||||||
}
|
}
|
||||||
tokio::time::sleep(Duration::from_millis(10)).await;
|
tokio::time::sleep(Duration::from_millis(10)).await;
|
||||||
}
|
}
|
||||||
|
@ -163,39 +139,32 @@ pub async fn op_webgpu_buffer_get_map_async(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct BufferGetMappedRangeArgs {
|
|
||||||
buffer_rid: ResourceId,
|
|
||||||
offset: u64,
|
|
||||||
size: Option<u64>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_buffer_get_mapped_range(
|
pub fn op_webgpu_buffer_get_mapped_range(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: BufferGetMappedRangeArgs,
|
buffer_rid: ResourceId,
|
||||||
mut zero_copy: ZeroCopyBuf,
|
offset: u64,
|
||||||
|
size: Option<u64>,
|
||||||
|
mut buf: ZeroCopyBuf,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let buffer_resource =
|
let buffer_resource = state.resource_table.get::<WebGpuBuffer>(buffer_rid)?;
|
||||||
state.resource_table.get::<WebGpuBuffer>(args.buffer_rid)?;
|
|
||||||
let buffer = buffer_resource.0;
|
let buffer = buffer_resource.0;
|
||||||
|
|
||||||
let (slice_pointer, range_size) =
|
let (slice_pointer, range_size) =
|
||||||
gfx_select!(buffer => instance.buffer_get_mapped_range(
|
gfx_select!(buffer => instance.buffer_get_mapped_range(
|
||||||
buffer,
|
buffer,
|
||||||
args.offset,
|
offset,
|
||||||
args.size
|
size
|
||||||
))
|
))
|
||||||
.map_err(|e| DomExceptionOperationError::new(&e.to_string()))?;
|
.map_err(|e| DomExceptionOperationError::new(&e.to_string()))?;
|
||||||
|
|
||||||
// TODO(bartlomieju):
|
// TODO(crowlKats):
|
||||||
#[allow(clippy::undocumented_unsafe_blocks)]
|
#[allow(clippy::undocumented_unsafe_blocks)]
|
||||||
let slice = unsafe {
|
let slice = unsafe {
|
||||||
std::slice::from_raw_parts_mut(slice_pointer, range_size as usize)
|
std::slice::from_raw_parts_mut(slice_pointer, range_size as usize)
|
||||||
};
|
};
|
||||||
zero_copy.copy_from_slice(slice);
|
buf.copy_from_slice(slice);
|
||||||
|
|
||||||
let rid = state
|
let rid = state
|
||||||
.resource_table
|
.resource_table
|
||||||
|
@ -204,35 +173,27 @@ pub fn op_webgpu_buffer_get_mapped_range(
|
||||||
Ok(WebGpuResult::rid(rid))
|
Ok(WebGpuResult::rid(rid))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct BufferUnmapArgs {
|
|
||||||
buffer_rid: ResourceId,
|
|
||||||
mapped_rid: ResourceId,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_buffer_unmap(
|
pub fn op_webgpu_buffer_unmap(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: BufferUnmapArgs,
|
buffer_rid: ResourceId,
|
||||||
zero_copy: Option<ZeroCopyBuf>,
|
mapped_rid: ResourceId,
|
||||||
|
buf: Option<ZeroCopyBuf>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let mapped_resource = state
|
let mapped_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.take::<WebGpuBufferMapped>(args.mapped_rid)?;
|
.take::<WebGpuBufferMapped>(mapped_rid)?;
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let buffer_resource =
|
let buffer_resource = state.resource_table.get::<WebGpuBuffer>(buffer_rid)?;
|
||||||
state.resource_table.get::<WebGpuBuffer>(args.buffer_rid)?;
|
|
||||||
let buffer = buffer_resource.0;
|
let buffer = buffer_resource.0;
|
||||||
|
|
||||||
let slice_pointer = mapped_resource.0;
|
if let Some(buf) = buf {
|
||||||
let size = mapped_resource.1;
|
// TODO(crowlKats):
|
||||||
|
|
||||||
if let Some(buffer) = zero_copy {
|
|
||||||
// TODO(bartlomieju):
|
|
||||||
#[allow(clippy::undocumented_unsafe_blocks)]
|
#[allow(clippy::undocumented_unsafe_blocks)]
|
||||||
let slice = unsafe { std::slice::from_raw_parts_mut(slice_pointer, size) };
|
let slice = unsafe {
|
||||||
slice.copy_from_slice(&buffer);
|
std::slice::from_raw_parts_mut(mapped_resource.0, mapped_resource.1)
|
||||||
|
};
|
||||||
|
slice.copy_from_slice(&buf);
|
||||||
}
|
}
|
||||||
|
|
||||||
gfx_ok!(buffer => instance.buffer_unmap(buffer))
|
gfx_ok!(buffer => instance.buffer_unmap(buffer))
|
||||||
|
|
|
@ -2,9 +2,10 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::ZeroCopyBuf;
|
use deno_core::ZeroCopyBuf;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
|
@ -33,7 +34,7 @@ impl Resource for WebGpuRenderBundle {
|
||||||
pub struct CreateRenderBundleEncoderArgs {
|
pub struct CreateRenderBundleEncoderArgs {
|
||||||
device_rid: ResourceId,
|
device_rid: ResourceId,
|
||||||
label: Option<String>,
|
label: Option<String>,
|
||||||
color_formats: Vec<wgpu_types::TextureFormat>,
|
color_formats: Vec<Option<wgpu_types::TextureFormat>>,
|
||||||
depth_stencil_format: Option<wgpu_types::TextureFormat>,
|
depth_stencil_format: Option<wgpu_types::TextureFormat>,
|
||||||
sample_count: u32,
|
sample_count: u32,
|
||||||
depth_read_only: bool,
|
depth_read_only: bool,
|
||||||
|
@ -50,25 +51,17 @@ pub fn op_webgpu_create_render_bundle_encoder(
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(args.device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let mut color_formats = vec![];
|
let depth_stencil = args.depth_stencil_format.map(|format| {
|
||||||
|
wgpu_types::RenderBundleDepthStencil {
|
||||||
for format in args.color_formats {
|
|
||||||
color_formats.push(format);
|
|
||||||
}
|
|
||||||
|
|
||||||
let depth_stencil = if let Some(format) = args.depth_stencil_format {
|
|
||||||
Some(wgpu_types::RenderBundleDepthStencil {
|
|
||||||
format,
|
format,
|
||||||
depth_read_only: args.depth_read_only,
|
depth_read_only: args.depth_read_only,
|
||||||
stencil_read_only: args.stencil_read_only,
|
stencil_read_only: args.stencil_read_only,
|
||||||
})
|
}
|
||||||
} else {
|
});
|
||||||
None
|
|
||||||
};
|
|
||||||
|
|
||||||
let descriptor = wgpu_core::command::RenderBundleEncoderDescriptor {
|
let descriptor = wgpu_core::command::RenderBundleEncoderDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: args.label.map(Cow::from),
|
||||||
color_formats: Cow::from(color_formats),
|
color_formats: Cow::from(args.color_formats),
|
||||||
sample_count: args.sample_count,
|
sample_count: args.sample_count,
|
||||||
depth_stencil,
|
depth_stencil,
|
||||||
multiview: None,
|
multiview: None,
|
||||||
|
@ -93,22 +86,16 @@ pub fn op_webgpu_create_render_bundle_encoder(
|
||||||
Ok(WebGpuResult::rid_err(rid, maybe_err))
|
Ok(WebGpuResult::rid_err(rid, maybe_err))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderBundleEncoderFinishArgs {
|
|
||||||
render_bundle_encoder_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_bundle_encoder_finish(
|
pub fn op_webgpu_render_bundle_encoder_finish(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderBundleEncoderFinishArgs,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.take::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.take::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
let render_bundle_encoder = Rc::try_unwrap(render_bundle_encoder_resource)
|
let render_bundle_encoder = Rc::try_unwrap(render_bundle_encoder_resource)
|
||||||
.ok()
|
.ok()
|
||||||
.expect("unwrapping render_bundle_encoder_resource should succeed")
|
.expect("unwrapping render_bundle_encoder_resource should succeed")
|
||||||
|
@ -119,48 +106,42 @@ pub fn op_webgpu_render_bundle_encoder_finish(
|
||||||
gfx_put!(render_bundle_encoder.parent() => instance.render_bundle_encoder_finish(
|
gfx_put!(render_bundle_encoder.parent() => instance.render_bundle_encoder_finish(
|
||||||
render_bundle_encoder,
|
render_bundle_encoder,
|
||||||
&wgpu_core::command::RenderBundleDescriptor {
|
&wgpu_core::command::RenderBundleDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
},
|
},
|
||||||
std::marker::PhantomData
|
std::marker::PhantomData
|
||||||
) => state, WebGpuRenderBundle)
|
) => state, WebGpuRenderBundle)
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_bundle_encoder_set_bind_group(
|
||||||
pub struct RenderBundleEncoderSetBindGroupArgs {
|
state: &mut OpState,
|
||||||
render_bundle_encoder_rid: ResourceId,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
index: u32,
|
index: u32,
|
||||||
bind_group: ResourceId,
|
bind_group: ResourceId,
|
||||||
dynamic_offsets_data: ZeroCopyBuf,
|
dynamic_offsets_data: ZeroCopyBuf,
|
||||||
dynamic_offsets_data_start: usize,
|
dynamic_offsets_data_start: usize,
|
||||||
dynamic_offsets_data_length: usize,
|
dynamic_offsets_data_length: usize,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_bundle_encoder_set_bind_group(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderBundleEncoderSetBindGroupArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let bind_group_resource =
|
let bind_group_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::binding::WebGpuBindGroup>(args.bind_group)?;
|
.get::<super::binding::WebGpuBindGroup>(bind_group)?;
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
// Align the data
|
// Align the data
|
||||||
assert!(args.dynamic_offsets_data.len() % std::mem::size_of::<u32>() == 0);
|
assert!(dynamic_offsets_data.len() % std::mem::size_of::<u32>() == 0);
|
||||||
let (prefix, dynamic_offsets_data, suffix) =
|
let (prefix, dynamic_offsets_data, suffix) =
|
||||||
// SAFETY: A u8 to u32 cast is safe because we asserted that the length is a
|
// SAFETY: A u8 to u32 cast is safe because we asserted that the length is a
|
||||||
// multiple of 4.
|
// multiple of 4.
|
||||||
unsafe { args.dynamic_offsets_data.align_to::<u32>() };
|
unsafe { dynamic_offsets_data.align_to::<u32>() };
|
||||||
assert!(prefix.is_empty());
|
assert!(prefix.is_empty());
|
||||||
assert!(suffix.is_empty());
|
assert!(suffix.is_empty());
|
||||||
|
|
||||||
let start = args.dynamic_offsets_data_start;
|
let start = dynamic_offsets_data_start;
|
||||||
let len = args.dynamic_offsets_data_length;
|
let len = dynamic_offsets_data_length;
|
||||||
|
|
||||||
// Assert that length and start are both in bounds
|
// Assert that length and start are both in bounds
|
||||||
assert!(start <= dynamic_offsets_data.len());
|
assert!(start <= dynamic_offsets_data.len());
|
||||||
|
@ -173,7 +154,7 @@ pub fn op_webgpu_render_bundle_encoder_set_bind_group(
|
||||||
unsafe {
|
unsafe {
|
||||||
wgpu_core::command::bundle_ffi::wgpu_render_bundle_set_bind_group(
|
wgpu_core::command::bundle_ffi::wgpu_render_bundle_set_bind_group(
|
||||||
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
||||||
args.index,
|
index,
|
||||||
bind_group_resource.0,
|
bind_group_resource.0,
|
||||||
dynamic_offsets_data.as_ptr(),
|
dynamic_offsets_data.as_ptr(),
|
||||||
dynamic_offsets_data.len(),
|
dynamic_offsets_data.len(),
|
||||||
|
@ -183,24 +164,18 @@ pub fn op_webgpu_render_bundle_encoder_set_bind_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderBundleEncoderPushDebugGroupArgs {
|
|
||||||
render_bundle_encoder_rid: ResourceId,
|
|
||||||
group_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_bundle_encoder_push_debug_group(
|
pub fn op_webgpu_render_bundle_encoder_push_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderBundleEncoderPushDebugGroupArgs,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
|
group_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
let label = std::ffi::CString::new(args.group_label).unwrap();
|
let label = std::ffi::CString::new(group_label).unwrap();
|
||||||
// SAFETY: the string the raw pointer points to lives longer than the below
|
// SAFETY: the string the raw pointer points to lives longer than the below
|
||||||
// function invocation.
|
// function invocation.
|
||||||
unsafe {
|
unsafe {
|
||||||
|
@ -213,21 +188,15 @@ pub fn op_webgpu_render_bundle_encoder_push_debug_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderBundleEncoderPopDebugGroupArgs {
|
|
||||||
render_bundle_encoder_rid: ResourceId,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_bundle_encoder_pop_debug_group(
|
pub fn op_webgpu_render_bundle_encoder_pop_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderBundleEncoderPopDebugGroupArgs,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::bundle_ffi::wgpu_render_bundle_pop_debug_group(
|
wgpu_core::command::bundle_ffi::wgpu_render_bundle_pop_debug_group(
|
||||||
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
||||||
|
@ -236,24 +205,18 @@ pub fn op_webgpu_render_bundle_encoder_pop_debug_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderBundleEncoderInsertDebugMarkerArgs {
|
|
||||||
render_bundle_encoder_rid: ResourceId,
|
|
||||||
marker_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_bundle_encoder_insert_debug_marker(
|
pub fn op_webgpu_render_bundle_encoder_insert_debug_marker(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderBundleEncoderInsertDebugMarkerArgs,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
|
marker_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
let label = std::ffi::CString::new(args.marker_label).unwrap();
|
let label = std::ffi::CString::new(marker_label).unwrap();
|
||||||
// SAFETY: the string the raw pointer points to lives longer than the below
|
// SAFETY: the string the raw pointer points to lives longer than the below
|
||||||
// function invocation.
|
// function invocation.
|
||||||
unsafe {
|
unsafe {
|
||||||
|
@ -266,26 +229,20 @@ pub fn op_webgpu_render_bundle_encoder_insert_debug_marker(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderBundleEncoderSetPipelineArgs {
|
|
||||||
render_bundle_encoder_rid: ResourceId,
|
|
||||||
pipeline: ResourceId,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_bundle_encoder_set_pipeline(
|
pub fn op_webgpu_render_bundle_encoder_set_pipeline(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderBundleEncoderSetPipelineArgs,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
|
pipeline: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pipeline_resource =
|
let render_pipeline_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::pipeline::WebGpuRenderPipeline>(args.pipeline)?;
|
.get::<super::pipeline::WebGpuRenderPipeline>(pipeline)?;
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::bundle_ffi::wgpu_render_bundle_set_pipeline(
|
wgpu_core::command::bundle_ffi::wgpu_render_bundle_set_pipeline(
|
||||||
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
||||||
|
@ -295,165 +252,135 @@ pub fn op_webgpu_render_bundle_encoder_set_pipeline(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_bundle_encoder_set_index_buffer(
|
||||||
pub struct RenderBundleEncoderSetIndexBufferArgs {
|
state: &mut OpState,
|
||||||
render_bundle_encoder_rid: ResourceId,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
buffer: ResourceId,
|
buffer: ResourceId,
|
||||||
index_format: wgpu_types::IndexFormat,
|
index_format: wgpu_types::IndexFormat,
|
||||||
offset: u64,
|
offset: u64,
|
||||||
size: u64,
|
size: u64,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_bundle_encoder_set_index_buffer(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderBundleEncoderSetIndexBufferArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(buffer)?;
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
render_bundle_encoder_resource
|
render_bundle_encoder_resource
|
||||||
.0
|
.0
|
||||||
.borrow_mut()
|
.borrow_mut()
|
||||||
.set_index_buffer(
|
.set_index_buffer(
|
||||||
buffer_resource.0,
|
buffer_resource.0,
|
||||||
args.index_format,
|
index_format,
|
||||||
args.offset,
|
offset,
|
||||||
std::num::NonZeroU64::new(args.size),
|
std::num::NonZeroU64::new(size),
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_bundle_encoder_set_vertex_buffer(
|
||||||
pub struct RenderBundleEncoderSetVertexBufferArgs {
|
state: &mut OpState,
|
||||||
render_bundle_encoder_rid: ResourceId,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
slot: u32,
|
slot: u32,
|
||||||
buffer: ResourceId,
|
buffer: ResourceId,
|
||||||
offset: u64,
|
offset: u64,
|
||||||
size: u64,
|
size: u64,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_bundle_encoder_set_vertex_buffer(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderBundleEncoderSetVertexBufferArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(buffer)?;
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::bundle_ffi::wgpu_render_bundle_set_vertex_buffer(
|
wgpu_core::command::bundle_ffi::wgpu_render_bundle_set_vertex_buffer(
|
||||||
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
||||||
args.slot,
|
slot,
|
||||||
buffer_resource.0,
|
buffer_resource.0,
|
||||||
args.offset,
|
offset,
|
||||||
std::num::NonZeroU64::new(args.size),
|
std::num::NonZeroU64::new(size),
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderBundleEncoderDrawArgs {
|
|
||||||
render_bundle_encoder_rid: ResourceId,
|
|
||||||
vertex_count: u32,
|
|
||||||
instance_count: u32,
|
|
||||||
first_vertex: u32,
|
|
||||||
first_instance: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_bundle_encoder_draw(
|
pub fn op_webgpu_render_bundle_encoder_draw(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderBundleEncoderDrawArgs,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
|
vertex_count: u32,
|
||||||
|
instance_count: u32,
|
||||||
|
first_vertex: u32,
|
||||||
|
first_instance: u32,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::bundle_ffi::wgpu_render_bundle_draw(
|
wgpu_core::command::bundle_ffi::wgpu_render_bundle_draw(
|
||||||
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
||||||
args.vertex_count,
|
vertex_count,
|
||||||
args.instance_count,
|
instance_count,
|
||||||
args.first_vertex,
|
first_vertex,
|
||||||
args.first_instance,
|
first_instance,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_bundle_encoder_draw_indexed(
|
||||||
pub struct RenderBundleEncoderDrawIndexedArgs {
|
state: &mut OpState,
|
||||||
render_bundle_encoder_rid: ResourceId,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
index_count: u32,
|
index_count: u32,
|
||||||
instance_count: u32,
|
instance_count: u32,
|
||||||
first_index: u32,
|
first_index: u32,
|
||||||
base_vertex: i32,
|
base_vertex: i32,
|
||||||
first_instance: u32,
|
first_instance: u32,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_bundle_encoder_draw_indexed(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderBundleEncoderDrawIndexedArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::bundle_ffi::wgpu_render_bundle_draw_indexed(
|
wgpu_core::command::bundle_ffi::wgpu_render_bundle_draw_indexed(
|
||||||
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
||||||
args.index_count,
|
index_count,
|
||||||
args.instance_count,
|
instance_count,
|
||||||
args.first_index,
|
first_index,
|
||||||
args.base_vertex,
|
base_vertex,
|
||||||
args.first_instance,
|
first_instance,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderBundleEncoderDrawIndirectArgs {
|
|
||||||
render_bundle_encoder_rid: ResourceId,
|
|
||||||
indirect_buffer: ResourceId,
|
|
||||||
indirect_offset: u64,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_bundle_encoder_draw_indirect(
|
pub fn op_webgpu_render_bundle_encoder_draw_indirect(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderBundleEncoderDrawIndirectArgs,
|
render_bundle_encoder_rid: ResourceId,
|
||||||
|
indirect_buffer: ResourceId,
|
||||||
|
indirect_offset: u64,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.indirect_buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(indirect_buffer)?;
|
||||||
let render_bundle_encoder_resource =
|
let render_bundle_encoder_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderBundleEncoder>(args.render_bundle_encoder_rid)?;
|
.get::<WebGpuRenderBundleEncoder>(render_bundle_encoder_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::bundle_ffi::wgpu_render_bundle_draw_indirect(
|
wgpu_core::command::bundle_ffi::wgpu_render_bundle_draw_indirect(
|
||||||
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
&mut render_bundle_encoder_resource.0.borrow_mut(),
|
||||||
buffer_resource.0,
|
buffer_resource.0,
|
||||||
args.indirect_offset,
|
indirect_offset,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
|
|
|
@ -2,8 +2,9 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
|
@ -29,27 +30,20 @@ impl Resource for WebGpuCommandBuffer {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CreateCommandEncoderArgs {
|
|
||||||
device_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
_measure_execution_time: Option<bool>, // not yet implemented
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_create_command_encoder(
|
pub fn op_webgpu_create_command_encoder(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CreateCommandEncoderArgs,
|
device_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let device_resource = state
|
let device_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let descriptor = wgpu_types::CommandEncoderDescriptor {
|
let descriptor = wgpu_types::CommandEncoderDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
};
|
};
|
||||||
|
|
||||||
gfx_put!(device => instance.device_create_command_encoder(
|
gfx_put!(device => instance.device_create_command_encoder(
|
||||||
|
@ -64,134 +58,104 @@ pub fn op_webgpu_create_command_encoder(
|
||||||
pub struct GpuRenderPassColorAttachment {
|
pub struct GpuRenderPassColorAttachment {
|
||||||
view: ResourceId,
|
view: ResourceId,
|
||||||
resolve_target: Option<ResourceId>,
|
resolve_target: Option<ResourceId>,
|
||||||
load_op: GpuLoadOp<wgpu_types::Color>,
|
clear_value: Option<wgpu_types::Color>,
|
||||||
|
load_op: wgpu_core::command::LoadOp,
|
||||||
store_op: wgpu_core::command::StoreOp,
|
store_op: wgpu_core::command::StoreOp,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "kebab-case")]
|
|
||||||
enum GpuLoadOp<T> {
|
|
||||||
Load,
|
|
||||||
Clear(T),
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
struct GpuRenderPassDepthStencilAttachment {
|
pub struct GpuRenderPassDepthStencilAttachment {
|
||||||
view: ResourceId,
|
view: ResourceId,
|
||||||
depth_load_op: GpuLoadOp<f32>,
|
depth_clear_value: f32,
|
||||||
|
depth_load_op: wgpu_core::command::LoadOp,
|
||||||
depth_store_op: wgpu_core::command::StoreOp,
|
depth_store_op: wgpu_core::command::StoreOp,
|
||||||
depth_read_only: bool,
|
depth_read_only: bool,
|
||||||
stencil_load_op: GpuLoadOp<u32>,
|
stencil_clear_value: u32,
|
||||||
|
stencil_load_op: wgpu_core::command::LoadOp,
|
||||||
stencil_store_op: wgpu_core::command::StoreOp,
|
stencil_store_op: wgpu_core::command::StoreOp,
|
||||||
stencil_read_only: bool,
|
stencil_read_only: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderBeginRenderPassArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
color_attachments: Vec<GpuRenderPassColorAttachment>,
|
|
||||||
depth_stencil_attachment: Option<GpuRenderPassDepthStencilAttachment>,
|
|
||||||
_occlusion_query_set: Option<u32>, // not yet implemented
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_begin_render_pass(
|
pub fn op_webgpu_command_encoder_begin_render_pass(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderBeginRenderPassArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
|
color_attachments: Vec<Option<GpuRenderPassColorAttachment>>,
|
||||||
|
depth_stencil_attachment: Option<GpuRenderPassDepthStencilAttachment>,
|
||||||
|
_occlusion_query_set: Option<u32>, // not yet implemented
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
|
|
||||||
let mut color_attachments = vec![];
|
let color_attachments = color_attachments
|
||||||
|
.into_iter()
|
||||||
|
.map(|color_attachment| {
|
||||||
|
let rp_at = if let Some(at) = color_attachment.as_ref() {
|
||||||
|
let texture_view_resource =
|
||||||
|
state
|
||||||
|
.resource_table
|
||||||
|
.get::<super::texture::WebGpuTextureView>(at.view)?;
|
||||||
|
|
||||||
for color_attachment in args.color_attachments {
|
let resolve_target = at
|
||||||
let texture_view_resource =
|
.resolve_target
|
||||||
state
|
.map(|rid| {
|
||||||
.resource_table
|
state
|
||||||
.get::<super::texture::WebGpuTextureView>(color_attachment.view)?;
|
.resource_table
|
||||||
|
.get::<super::texture::WebGpuTextureView>(rid)
|
||||||
|
})
|
||||||
|
.transpose()?
|
||||||
|
.map(|texture| texture.0);
|
||||||
|
|
||||||
let resolve_target = color_attachment
|
Some(wgpu_core::command::RenderPassColorAttachment {
|
||||||
.resolve_target
|
view: texture_view_resource.0,
|
||||||
.map(|rid| {
|
resolve_target,
|
||||||
state
|
channel: wgpu_core::command::PassChannel {
|
||||||
.resource_table
|
load_op: at.load_op,
|
||||||
.get::<super::texture::WebGpuTextureView>(rid)
|
store_op: at.store_op,
|
||||||
})
|
clear_value: at.clear_value.unwrap_or_default(),
|
||||||
.transpose()?
|
read_only: false,
|
||||||
.map(|texture| texture.0);
|
},
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
};
|
||||||
|
Ok(rp_at)
|
||||||
|
})
|
||||||
|
.collect::<Result<Vec<_>, AnyError>>()?;
|
||||||
|
|
||||||
let attachment = wgpu_core::command::RenderPassColorAttachment {
|
let mut processed_depth_stencil_attachment = None;
|
||||||
view: texture_view_resource.0,
|
|
||||||
resolve_target,
|
|
||||||
channel: match color_attachment.load_op {
|
|
||||||
GpuLoadOp::Load => wgpu_core::command::PassChannel {
|
|
||||||
load_op: wgpu_core::command::LoadOp::Load,
|
|
||||||
store_op: color_attachment.store_op,
|
|
||||||
clear_value: Default::default(),
|
|
||||||
read_only: false,
|
|
||||||
},
|
|
||||||
GpuLoadOp::Clear(color) => wgpu_core::command::PassChannel {
|
|
||||||
load_op: wgpu_core::command::LoadOp::Clear,
|
|
||||||
store_op: color_attachment.store_op,
|
|
||||||
clear_value: color,
|
|
||||||
read_only: false,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
};
|
|
||||||
|
|
||||||
color_attachments.push(attachment)
|
if let Some(attachment) = depth_stencil_attachment {
|
||||||
}
|
|
||||||
|
|
||||||
let mut depth_stencil_attachment = None;
|
|
||||||
|
|
||||||
if let Some(attachment) = args.depth_stencil_attachment {
|
|
||||||
let texture_view_resource =
|
let texture_view_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::texture::WebGpuTextureView>(attachment.view)?;
|
.get::<super::texture::WebGpuTextureView>(attachment.view)?;
|
||||||
|
|
||||||
depth_stencil_attachment =
|
processed_depth_stencil_attachment =
|
||||||
Some(wgpu_core::command::RenderPassDepthStencilAttachment {
|
Some(wgpu_core::command::RenderPassDepthStencilAttachment {
|
||||||
view: texture_view_resource.0,
|
view: texture_view_resource.0,
|
||||||
depth: match attachment.depth_load_op {
|
depth: wgpu_core::command::PassChannel {
|
||||||
GpuLoadOp::Load => wgpu_core::command::PassChannel {
|
load_op: attachment.depth_load_op,
|
||||||
load_op: wgpu_core::command::LoadOp::Load,
|
store_op: attachment.depth_store_op,
|
||||||
store_op: attachment.depth_store_op,
|
clear_value: attachment.depth_clear_value,
|
||||||
clear_value: 0.0,
|
read_only: attachment.depth_read_only,
|
||||||
read_only: attachment.depth_read_only,
|
|
||||||
},
|
|
||||||
GpuLoadOp::Clear(value) => wgpu_core::command::PassChannel {
|
|
||||||
load_op: wgpu_core::command::LoadOp::Clear,
|
|
||||||
store_op: attachment.depth_store_op,
|
|
||||||
clear_value: value,
|
|
||||||
read_only: attachment.depth_read_only,
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
stencil: match attachment.stencil_load_op {
|
stencil: wgpu_core::command::PassChannel {
|
||||||
GpuLoadOp::Load => wgpu_core::command::PassChannel {
|
load_op: attachment.stencil_load_op,
|
||||||
load_op: wgpu_core::command::LoadOp::Load,
|
store_op: attachment.stencil_store_op,
|
||||||
store_op: attachment.stencil_store_op,
|
clear_value: attachment.stencil_clear_value,
|
||||||
clear_value: 0,
|
read_only: attachment.stencil_read_only,
|
||||||
read_only: attachment.stencil_read_only,
|
|
||||||
},
|
|
||||||
GpuLoadOp::Clear(value) => wgpu_core::command::PassChannel {
|
|
||||||
load_op: wgpu_core::command::LoadOp::Clear,
|
|
||||||
store_op: attachment.stencil_store_op,
|
|
||||||
clear_value: value,
|
|
||||||
read_only: attachment.stencil_read_only,
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
let descriptor = wgpu_core::command::RenderPassDescriptor {
|
let descriptor = wgpu_core::command::RenderPassDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
color_attachments: Cow::from(color_attachments),
|
color_attachments: Cow::from(color_attachments),
|
||||||
depth_stencil_attachment: depth_stencil_attachment.as_ref(),
|
depth_stencil_attachment: processed_depth_stencil_attachment.as_ref(),
|
||||||
};
|
};
|
||||||
|
|
||||||
let render_pass = wgpu_core::command::RenderPass::new(
|
let render_pass = wgpu_core::command::RenderPass::new(
|
||||||
|
@ -208,24 +172,18 @@ pub fn op_webgpu_command_encoder_begin_render_pass(
|
||||||
Ok(WebGpuResult::rid(rid))
|
Ok(WebGpuResult::rid(rid))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderBeginComputePassArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_begin_compute_pass(
|
pub fn op_webgpu_command_encoder_begin_compute_pass(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderBeginComputePassArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
|
|
||||||
let descriptor = wgpu_core::command::ComputePassDescriptor {
|
let descriptor = wgpu_core::command::ComputePassDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
};
|
};
|
||||||
|
|
||||||
let compute_pass = wgpu_core::command::ComputePass::new(
|
let compute_pass = wgpu_core::command::ComputePass::new(
|
||||||
|
@ -242,45 +200,38 @@ pub fn op_webgpu_command_encoder_begin_compute_pass(
|
||||||
Ok(WebGpuResult::rid(rid))
|
Ok(WebGpuResult::rid(rid))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_command_encoder_copy_buffer_to_buffer(
|
||||||
pub struct CommandEncoderCopyBufferToBufferArgs {
|
state: &mut OpState,
|
||||||
command_encoder_rid: ResourceId,
|
command_encoder_rid: ResourceId,
|
||||||
source: ResourceId,
|
source: ResourceId,
|
||||||
source_offset: u64,
|
source_offset: u64,
|
||||||
destination: ResourceId,
|
destination: ResourceId,
|
||||||
destination_offset: u64,
|
destination_offset: u64,
|
||||||
size: u64,
|
size: u64,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_command_encoder_copy_buffer_to_buffer(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: CommandEncoderCopyBufferToBufferArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let source_buffer_resource =
|
let source_buffer_resource = state
|
||||||
state
|
.resource_table
|
||||||
.resource_table
|
.get::<super::buffer::WebGpuBuffer>(source)?;
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.source)?;
|
|
||||||
let source_buffer = source_buffer_resource.0;
|
let source_buffer = source_buffer_resource.0;
|
||||||
let destination_buffer_resource =
|
let destination_buffer_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.destination)?;
|
.get::<super::buffer::WebGpuBuffer>(destination)?;
|
||||||
let destination_buffer = destination_buffer_resource.0;
|
let destination_buffer = destination_buffer_resource.0;
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_copy_buffer_to_buffer(
|
gfx_ok!(command_encoder => instance.command_encoder_copy_buffer_to_buffer(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
source_buffer,
|
source_buffer,
|
||||||
args.source_offset,
|
source_offset,
|
||||||
destination_buffer,
|
destination_buffer,
|
||||||
args.destination_offset,
|
destination_offset,
|
||||||
args.size
|
size
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -302,342 +253,277 @@ pub struct GpuImageCopyTexture {
|
||||||
pub aspect: wgpu_types::TextureAspect,
|
pub aspect: wgpu_types::TextureAspect,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_command_encoder_copy_buffer_to_texture(
|
||||||
pub struct CommandEncoderCopyBufferToTextureArgs {
|
state: &mut OpState,
|
||||||
command_encoder_rid: ResourceId,
|
command_encoder_rid: ResourceId,
|
||||||
source: GpuImageCopyBuffer,
|
source: GpuImageCopyBuffer,
|
||||||
destination: GpuImageCopyTexture,
|
destination: GpuImageCopyTexture,
|
||||||
copy_size: wgpu_types::Extent3d,
|
copy_size: wgpu_types::Extent3d,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_command_encoder_copy_buffer_to_texture(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: CommandEncoderCopyBufferToTextureArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let source_buffer_resource =
|
let source_buffer_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.source.buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(source.buffer)?;
|
||||||
let destination_texture_resource =
|
let destination_texture_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::texture::WebGpuTexture>(args.destination.texture)?;
|
.get::<super::texture::WebGpuTexture>(destination.texture)?;
|
||||||
|
|
||||||
let source = wgpu_core::command::ImageCopyBuffer {
|
let source = wgpu_core::command::ImageCopyBuffer {
|
||||||
buffer: source_buffer_resource.0,
|
buffer: source_buffer_resource.0,
|
||||||
layout: wgpu_types::ImageDataLayout {
|
layout: wgpu_types::ImageDataLayout {
|
||||||
offset: args.source.offset,
|
offset: source.offset,
|
||||||
bytes_per_row: NonZeroU32::new(args.source.bytes_per_row.unwrap_or(0)),
|
bytes_per_row: NonZeroU32::new(source.bytes_per_row.unwrap_or(0)),
|
||||||
rows_per_image: NonZeroU32::new(args.source.rows_per_image.unwrap_or(0)),
|
rows_per_image: NonZeroU32::new(source.rows_per_image.unwrap_or(0)),
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
let destination = wgpu_core::command::ImageCopyTexture {
|
let destination = wgpu_core::command::ImageCopyTexture {
|
||||||
texture: destination_texture_resource.0,
|
texture: destination_texture_resource.0,
|
||||||
mip_level: args.destination.mip_level,
|
mip_level: destination.mip_level,
|
||||||
origin: args.destination.origin,
|
origin: destination.origin,
|
||||||
aspect: args.destination.aspect,
|
aspect: destination.aspect,
|
||||||
};
|
};
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_copy_buffer_to_texture(
|
gfx_ok!(command_encoder => instance.command_encoder_copy_buffer_to_texture(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
&source,
|
&source,
|
||||||
&destination,
|
&destination,
|
||||||
&args.copy_size
|
©_size
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderCopyTextureToBufferArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
source: GpuImageCopyTexture,
|
|
||||||
destination: GpuImageCopyBuffer,
|
|
||||||
copy_size: wgpu_types::Extent3d,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_copy_texture_to_buffer(
|
pub fn op_webgpu_command_encoder_copy_texture_to_buffer(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderCopyTextureToBufferArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
source: GpuImageCopyTexture,
|
||||||
|
destination: GpuImageCopyBuffer,
|
||||||
|
copy_size: wgpu_types::Extent3d,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let source_texture_resource =
|
let source_texture_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::texture::WebGpuTexture>(args.source.texture)?;
|
.get::<super::texture::WebGpuTexture>(source.texture)?;
|
||||||
let destination_buffer_resource =
|
let destination_buffer_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.destination.buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(destination.buffer)?;
|
||||||
|
|
||||||
let source = wgpu_core::command::ImageCopyTexture {
|
let source = wgpu_core::command::ImageCopyTexture {
|
||||||
texture: source_texture_resource.0,
|
texture: source_texture_resource.0,
|
||||||
mip_level: args.source.mip_level,
|
mip_level: source.mip_level,
|
||||||
origin: args.source.origin,
|
origin: source.origin,
|
||||||
aspect: args.source.aspect,
|
aspect: source.aspect,
|
||||||
};
|
};
|
||||||
let destination = wgpu_core::command::ImageCopyBuffer {
|
let destination = wgpu_core::command::ImageCopyBuffer {
|
||||||
buffer: destination_buffer_resource.0,
|
buffer: destination_buffer_resource.0,
|
||||||
layout: wgpu_types::ImageDataLayout {
|
layout: wgpu_types::ImageDataLayout {
|
||||||
offset: args.destination.offset,
|
offset: destination.offset,
|
||||||
bytes_per_row: NonZeroU32::new(
|
bytes_per_row: NonZeroU32::new(destination.bytes_per_row.unwrap_or(0)),
|
||||||
args.destination.bytes_per_row.unwrap_or(0),
|
rows_per_image: NonZeroU32::new(destination.rows_per_image.unwrap_or(0)),
|
||||||
),
|
|
||||||
rows_per_image: NonZeroU32::new(
|
|
||||||
args.destination.rows_per_image.unwrap_or(0),
|
|
||||||
),
|
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_copy_texture_to_buffer(
|
gfx_ok!(command_encoder => instance.command_encoder_copy_texture_to_buffer(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
&source,
|
&source,
|
||||||
&destination,
|
&destination,
|
||||||
&args.copy_size
|
©_size
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderCopyTextureToTextureArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
source: GpuImageCopyTexture,
|
|
||||||
destination: GpuImageCopyTexture,
|
|
||||||
copy_size: wgpu_types::Extent3d,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_copy_texture_to_texture(
|
pub fn op_webgpu_command_encoder_copy_texture_to_texture(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderCopyTextureToTextureArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
source: GpuImageCopyTexture,
|
||||||
|
destination: GpuImageCopyTexture,
|
||||||
|
copy_size: wgpu_types::Extent3d,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let source_texture_resource =
|
let source_texture_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::texture::WebGpuTexture>(args.source.texture)?;
|
.get::<super::texture::WebGpuTexture>(source.texture)?;
|
||||||
let destination_texture_resource =
|
let destination_texture_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::texture::WebGpuTexture>(args.destination.texture)?;
|
.get::<super::texture::WebGpuTexture>(destination.texture)?;
|
||||||
|
|
||||||
let source = wgpu_core::command::ImageCopyTexture {
|
let source = wgpu_core::command::ImageCopyTexture {
|
||||||
texture: source_texture_resource.0,
|
texture: source_texture_resource.0,
|
||||||
mip_level: args.source.mip_level,
|
mip_level: source.mip_level,
|
||||||
origin: args.source.origin,
|
origin: source.origin,
|
||||||
aspect: args.source.aspect,
|
aspect: source.aspect,
|
||||||
};
|
};
|
||||||
let destination = wgpu_core::command::ImageCopyTexture {
|
let destination = wgpu_core::command::ImageCopyTexture {
|
||||||
texture: destination_texture_resource.0,
|
texture: destination_texture_resource.0,
|
||||||
mip_level: args.destination.mip_level,
|
mip_level: destination.mip_level,
|
||||||
origin: args.destination.origin,
|
origin: destination.origin,
|
||||||
aspect: args.destination.aspect,
|
aspect: destination.aspect,
|
||||||
};
|
};
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_copy_texture_to_texture(
|
gfx_ok!(command_encoder => instance.command_encoder_copy_texture_to_texture(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
&source,
|
&source,
|
||||||
&destination,
|
&destination,
|
||||||
&args.copy_size
|
©_size
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderClearBufferArgs {
|
|
||||||
command_encoder_rid: u32,
|
|
||||||
destination_rid: u32,
|
|
||||||
destination_offset: u64,
|
|
||||||
size: u64,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_clear_buffer(
|
pub fn op_webgpu_command_encoder_clear_buffer(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderClearBufferArgs,
|
command_encoder_rid: u32,
|
||||||
|
buffer_rid: u32,
|
||||||
|
offset: u64,
|
||||||
|
size: u64,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let destination_resource = state
|
let destination_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.destination_rid)?;
|
.get::<super::buffer::WebGpuBuffer>(buffer_rid)?;
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_clear_buffer(
|
gfx_ok!(command_encoder => instance.command_encoder_clear_buffer(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
destination_resource.0,
|
destination_resource.0,
|
||||||
args.destination_offset,
|
offset,
|
||||||
std::num::NonZeroU64::new(args.size)
|
std::num::NonZeroU64::new(size)
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderPushDebugGroupArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
group_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_push_debug_group(
|
pub fn op_webgpu_command_encoder_push_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderPushDebugGroupArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
group_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance
|
gfx_ok!(command_encoder => instance.command_encoder_push_debug_group(command_encoder, &group_label))
|
||||||
.command_encoder_push_debug_group(command_encoder, &args.group_label))
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderPopDebugGroupArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_pop_debug_group(
|
pub fn op_webgpu_command_encoder_pop_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderPopDebugGroupArgs,
|
command_encoder_rid: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_pop_debug_group(command_encoder))
|
gfx_ok!(command_encoder => instance.command_encoder_pop_debug_group(command_encoder))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderInsertDebugMarkerArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
marker_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_insert_debug_marker(
|
pub fn op_webgpu_command_encoder_insert_debug_marker(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderInsertDebugMarkerArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
marker_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_insert_debug_marker(
|
gfx_ok!(command_encoder => instance.command_encoder_insert_debug_marker(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
&args.marker_label
|
&marker_label
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderWriteTimestampArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
query_set: ResourceId,
|
|
||||||
query_index: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_write_timestamp(
|
pub fn op_webgpu_command_encoder_write_timestamp(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderWriteTimestampArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
query_set: ResourceId,
|
||||||
|
query_index: u32,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let query_set_resource = state
|
let query_set_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuQuerySet>(args.query_set)?;
|
.get::<super::WebGpuQuerySet>(query_set)?;
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_write_timestamp(
|
gfx_ok!(command_encoder => instance.command_encoder_write_timestamp(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
query_set_resource.0,
|
query_set_resource.0,
|
||||||
args.query_index
|
query_index
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_command_encoder_resolve_query_set(
|
||||||
pub struct CommandEncoderResolveQuerySetArgs {
|
state: &mut OpState,
|
||||||
command_encoder_rid: ResourceId,
|
command_encoder_rid: ResourceId,
|
||||||
query_set: ResourceId,
|
query_set: ResourceId,
|
||||||
first_query: u32,
|
first_query: u32,
|
||||||
query_count: u32,
|
query_count: u32,
|
||||||
destination: ResourceId,
|
destination: ResourceId,
|
||||||
destination_offset: u64,
|
destination_offset: u64,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_command_encoder_resolve_query_set(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: CommandEncoderResolveQuerySetArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.get::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let query_set_resource = state
|
let query_set_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuQuerySet>(args.query_set)?;
|
.get::<super::WebGpuQuerySet>(query_set)?;
|
||||||
let destination_resource = state
|
let destination_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.destination)?;
|
.get::<super::buffer::WebGpuBuffer>(destination)?;
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_resolve_query_set(
|
gfx_ok!(command_encoder => instance.command_encoder_resolve_query_set(
|
||||||
command_encoder,
|
command_encoder,
|
||||||
query_set_resource.0,
|
query_set_resource.0,
|
||||||
args.first_query,
|
first_query,
|
||||||
args.query_count,
|
query_count,
|
||||||
destination_resource.0,
|
destination_resource.0,
|
||||||
args.destination_offset
|
destination_offset
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CommandEncoderFinishArgs {
|
|
||||||
command_encoder_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_command_encoder_finish(
|
pub fn op_webgpu_command_encoder_finish(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CommandEncoderFinishArgs,
|
command_encoder_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.take::<WebGpuCommandEncoder>(args.command_encoder_rid)?;
|
.take::<WebGpuCommandEncoder>(command_encoder_rid)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
|
|
||||||
let descriptor = wgpu_types::CommandBufferDescriptor {
|
let descriptor = wgpu_types::CommandBufferDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
};
|
};
|
||||||
|
|
||||||
gfx_put!(command_encoder => instance.command_encoder_finish(
|
gfx_put!(command_encoder => instance.command_encoder_finish(
|
||||||
|
|
|
@ -2,10 +2,10 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::ZeroCopyBuf;
|
use deno_core::ZeroCopyBuf;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
|
|
||||||
|
@ -20,25 +20,19 @@ impl Resource for WebGpuComputePass {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct ComputePassSetPipelineArgs {
|
|
||||||
compute_pass_rid: ResourceId,
|
|
||||||
pipeline: ResourceId,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_compute_pass_set_pipeline(
|
pub fn op_webgpu_compute_pass_set_pipeline(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: ComputePassSetPipelineArgs,
|
compute_pass_rid: ResourceId,
|
||||||
|
pipeline: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let compute_pipeline_resource =
|
let compute_pipeline_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::pipeline::WebGpuComputePipeline>(args.pipeline)?;
|
.get::<super::pipeline::WebGpuComputePipeline>(pipeline)?;
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_set_pipeline(
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_set_pipeline(
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
|
@ -48,106 +42,82 @@ pub fn op_webgpu_compute_pass_set_pipeline(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_compute_pass_dispatch_workgroups(
|
||||||
pub struct ComputePassDispatchArgs {
|
state: &mut OpState,
|
||||||
compute_pass_rid: ResourceId,
|
compute_pass_rid: ResourceId,
|
||||||
x: u32,
|
x: u32,
|
||||||
y: u32,
|
y: u32,
|
||||||
z: u32,
|
z: u32,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_compute_pass_dispatch(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: ComputePassDispatchArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_dispatch(
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_dispatch_workgroups(
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
args.x,
|
x,
|
||||||
args.y,
|
y,
|
||||||
args.z,
|
z,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_compute_pass_dispatch_workgroups_indirect(
|
||||||
pub struct ComputePassDispatchIndirectArgs {
|
state: &mut OpState,
|
||||||
compute_pass_rid: ResourceId,
|
compute_pass_rid: ResourceId,
|
||||||
indirect_buffer: ResourceId,
|
indirect_buffer: ResourceId,
|
||||||
indirect_offset: u64,
|
indirect_offset: u64,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_compute_pass_dispatch_indirect(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: ComputePassDispatchIndirectArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.indirect_buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(indirect_buffer)?;
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_dispatch_indirect(
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_dispatch_workgroups_indirect(
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
|
||||||
buffer_resource.0,
|
|
||||||
args.indirect_offset,
|
|
||||||
);
|
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct ComputePassBeginPipelineStatisticsQueryArgs {
|
|
||||||
compute_pass_rid: ResourceId,
|
|
||||||
query_set: ResourceId,
|
|
||||||
query_index: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_compute_pass_begin_pipeline_statistics_query(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: ComputePassBeginPipelineStatisticsQueryArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
|
||||||
let compute_pass_resource = state
|
|
||||||
.resource_table
|
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
|
||||||
let query_set_resource = state
|
|
||||||
.resource_table
|
|
||||||
.get::<super::WebGpuQuerySet>(args.query_set)?;
|
|
||||||
|
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_begin_pipeline_statistics_query(
|
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
query_set_resource.0,
|
buffer_resource.0,
|
||||||
args.query_index,
|
indirect_offset,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_compute_pass_begin_pipeline_statistics_query(
|
||||||
pub struct ComputePassEndPipelineStatisticsQueryArgs {
|
state: &mut OpState,
|
||||||
compute_pass_rid: ResourceId,
|
compute_pass_rid: ResourceId,
|
||||||
|
query_set: ResourceId,
|
||||||
|
query_index: u32,
|
||||||
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
|
let compute_pass_resource = state
|
||||||
|
.resource_table
|
||||||
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
let query_set_resource = state
|
||||||
|
.resource_table
|
||||||
|
.get::<super::WebGpuQuerySet>(query_set)?;
|
||||||
|
|
||||||
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_begin_pipeline_statistics_query(
|
||||||
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
|
query_set_resource.0,
|
||||||
|
query_index,
|
||||||
|
);
|
||||||
|
|
||||||
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_compute_pass_end_pipeline_statistics_query(
|
pub fn op_webgpu_compute_pass_end_pipeline_statistics_query(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: ComputePassEndPipelineStatisticsQueryArgs,
|
compute_pass_rid: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_end_pipeline_statistics_query(
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_end_pipeline_statistics_query(
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
|
@ -156,56 +126,44 @@ pub fn op_webgpu_compute_pass_end_pipeline_statistics_query(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct ComputePassWriteTimestampArgs {
|
|
||||||
compute_pass_rid: ResourceId,
|
|
||||||
query_set: ResourceId,
|
|
||||||
query_index: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_compute_pass_write_timestamp(
|
pub fn op_webgpu_compute_pass_write_timestamp(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: ComputePassWriteTimestampArgs,
|
compute_pass_rid: ResourceId,
|
||||||
|
query_set: ResourceId,
|
||||||
|
query_index: u32,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
let query_set_resource = state
|
let query_set_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuQuerySet>(args.query_set)?;
|
.get::<super::WebGpuQuerySet>(query_set)?;
|
||||||
|
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_write_timestamp(
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_write_timestamp(
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
query_set_resource.0,
|
query_set_resource.0,
|
||||||
args.query_index,
|
query_index,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_compute_pass_end(
|
||||||
pub struct ComputePassEndPassArgs {
|
state: &mut OpState,
|
||||||
command_encoder_rid: ResourceId,
|
command_encoder_rid: ResourceId,
|
||||||
compute_pass_rid: ResourceId,
|
compute_pass_rid: ResourceId,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_compute_pass_end_pass(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: ComputePassEndPassArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::command_encoder::WebGpuCommandEncoder>(
|
.get::<super::command_encoder::WebGpuCommandEncoder>(
|
||||||
args.command_encoder_rid,
|
command_encoder_rid,
|
||||||
)?;
|
)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.take::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.take::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
let compute_pass = &compute_pass_resource.0.borrow();
|
let compute_pass = &compute_pass_resource.0.borrow();
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
|
|
||||||
|
@ -215,41 +173,35 @@ pub fn op_webgpu_compute_pass_end_pass(
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_compute_pass_set_bind_group(
|
||||||
pub struct ComputePassSetBindGroupArgs {
|
state: &mut OpState,
|
||||||
compute_pass_rid: ResourceId,
|
compute_pass_rid: ResourceId,
|
||||||
index: u32,
|
index: u32,
|
||||||
bind_group: ResourceId,
|
bind_group: ResourceId,
|
||||||
dynamic_offsets_data: ZeroCopyBuf,
|
dynamic_offsets_data: ZeroCopyBuf,
|
||||||
dynamic_offsets_data_start: usize,
|
dynamic_offsets_data_start: usize,
|
||||||
dynamic_offsets_data_length: usize,
|
dynamic_offsets_data_length: usize,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_compute_pass_set_bind_group(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: ComputePassSetBindGroupArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let bind_group_resource =
|
let bind_group_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::binding::WebGpuBindGroup>(args.bind_group)?;
|
.get::<super::binding::WebGpuBindGroup>(bind_group)?;
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
// Align the data
|
// Align the data
|
||||||
assert!(args.dynamic_offsets_data_start % std::mem::size_of::<u32>() == 0);
|
assert!(dynamic_offsets_data_start % std::mem::size_of::<u32>() == 0);
|
||||||
let (prefix, dynamic_offsets_data, suffix) =
|
let (prefix, dynamic_offsets_data, suffix) =
|
||||||
// SAFETY: A u8 to u32 cast is safe because we asserted that the length is a
|
// SAFETY: A u8 to u32 cast is safe because we asserted that the length is a
|
||||||
// multiple of 4.
|
// multiple of 4.
|
||||||
unsafe { args.dynamic_offsets_data.align_to::<u32>() };
|
unsafe { dynamic_offsets_data.align_to::<u32>() };
|
||||||
assert!(prefix.is_empty());
|
assert!(prefix.is_empty());
|
||||||
assert!(suffix.is_empty());
|
assert!(suffix.is_empty());
|
||||||
|
|
||||||
let start = args.dynamic_offsets_data_start;
|
let start = dynamic_offsets_data_start;
|
||||||
let len = args.dynamic_offsets_data_length;
|
let len = dynamic_offsets_data_length;
|
||||||
|
|
||||||
// Assert that length and start are both in bounds
|
// Assert that length and start are both in bounds
|
||||||
assert!(start <= dynamic_offsets_data.len());
|
assert!(start <= dynamic_offsets_data.len());
|
||||||
|
@ -262,7 +214,7 @@ pub fn op_webgpu_compute_pass_set_bind_group(
|
||||||
unsafe {
|
unsafe {
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_set_bind_group(
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_set_bind_group(
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
args.index,
|
index,
|
||||||
bind_group_resource.0,
|
bind_group_resource.0,
|
||||||
dynamic_offsets_data.as_ptr(),
|
dynamic_offsets_data.as_ptr(),
|
||||||
dynamic_offsets_data.len(),
|
dynamic_offsets_data.len(),
|
||||||
|
@ -272,23 +224,17 @@ pub fn op_webgpu_compute_pass_set_bind_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct ComputePassPushDebugGroupArgs {
|
|
||||||
compute_pass_rid: ResourceId,
|
|
||||||
group_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_compute_pass_push_debug_group(
|
pub fn op_webgpu_compute_pass_push_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: ComputePassPushDebugGroupArgs,
|
compute_pass_rid: ResourceId,
|
||||||
|
group_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
let label = std::ffi::CString::new(args.group_label).unwrap();
|
let label = std::ffi::CString::new(group_label).unwrap();
|
||||||
// SAFETY: the string the raw pointer points to lives longer than the below
|
// SAFETY: the string the raw pointer points to lives longer than the below
|
||||||
// function invocation.
|
// function invocation.
|
||||||
unsafe {
|
unsafe {
|
||||||
|
@ -302,20 +248,14 @@ pub fn op_webgpu_compute_pass_push_debug_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct ComputePassPopDebugGroupArgs {
|
|
||||||
compute_pass_rid: ResourceId,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_compute_pass_pop_debug_group(
|
pub fn op_webgpu_compute_pass_pop_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: ComputePassPopDebugGroupArgs,
|
compute_pass_rid: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::compute_ffi::wgpu_compute_pass_pop_debug_group(
|
wgpu_core::command::compute_ffi::wgpu_compute_pass_pop_debug_group(
|
||||||
&mut compute_pass_resource.0.borrow_mut(),
|
&mut compute_pass_resource.0.borrow_mut(),
|
||||||
|
@ -324,23 +264,17 @@ pub fn op_webgpu_compute_pass_pop_debug_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct ComputePassInsertDebugMarkerArgs {
|
|
||||||
compute_pass_rid: ResourceId,
|
|
||||||
marker_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_compute_pass_insert_debug_marker(
|
pub fn op_webgpu_compute_pass_insert_debug_marker(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: ComputePassInsertDebugMarkerArgs,
|
compute_pass_rid: ResourceId,
|
||||||
|
marker_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let compute_pass_resource = state
|
let compute_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePass>(args.compute_pass_rid)?;
|
.get::<WebGpuComputePass>(compute_pass_rid)?;
|
||||||
|
|
||||||
let label = std::ffi::CString::new(args.marker_label).unwrap();
|
let label = std::ffi::CString::new(marker_label).unwrap();
|
||||||
// SAFETY: the string the raw pointer points to lives longer than the below
|
// SAFETY: the string the raw pointer points to lives longer than the below
|
||||||
// function invocation.
|
// function invocation.
|
||||||
unsafe {
|
unsafe {
|
||||||
|
|
|
@ -3,7 +3,9 @@ use deno_core::error::AnyError;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use serde::Serialize;
|
use serde::Serialize;
|
||||||
use std::convert::From;
|
use std::convert::From;
|
||||||
|
use std::error::Error;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
use std::fmt::Write;
|
||||||
use wgpu_core::binding_model::CreateBindGroupError;
|
use wgpu_core::binding_model::CreateBindGroupError;
|
||||||
use wgpu_core::binding_model::CreateBindGroupLayoutError;
|
use wgpu_core::binding_model::CreateBindGroupLayoutError;
|
||||||
use wgpu_core::binding_model::CreatePipelineLayoutError;
|
use wgpu_core::binding_model::CreatePipelineLayoutError;
|
||||||
|
@ -29,6 +31,20 @@ use wgpu_core::resource::CreateSamplerError;
|
||||||
use wgpu_core::resource::CreateTextureError;
|
use wgpu_core::resource::CreateTextureError;
|
||||||
use wgpu_core::resource::CreateTextureViewError;
|
use wgpu_core::resource::CreateTextureViewError;
|
||||||
|
|
||||||
|
fn fmt_err(err: &(dyn Error + 'static)) -> String {
|
||||||
|
let mut output = err.to_string();
|
||||||
|
|
||||||
|
let mut e = err.source();
|
||||||
|
while let Some(source) = e {
|
||||||
|
// No error possible, unwrap is fine here.
|
||||||
|
// https://github.com/rust-lang/rust/blob/1.47.0/library/alloc/src/string.rs#L2414-L2427
|
||||||
|
write!(output, ": {source}").unwrap();
|
||||||
|
e = source.source();
|
||||||
|
}
|
||||||
|
|
||||||
|
output
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Serialize)]
|
#[derive(Serialize)]
|
||||||
pub struct WebGpuResult {
|
pub struct WebGpuResult {
|
||||||
pub rid: Option<ResourceId>,
|
pub rid: Option<ResourceId>,
|
||||||
|
@ -49,14 +65,14 @@ impl WebGpuResult {
|
||||||
) -> Self {
|
) -> Self {
|
||||||
Self {
|
Self {
|
||||||
rid: Some(rid),
|
rid: Some(rid),
|
||||||
err: err.map(|e| e.into()),
|
err: err.map(Into::into),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn maybe_err<T: Into<WebGpuError>>(err: Option<T>) -> Self {
|
pub fn maybe_err<T: Into<WebGpuError>>(err: Option<T>) -> Self {
|
||||||
Self {
|
Self {
|
||||||
rid: None,
|
rid: None,
|
||||||
err: err.map(|e| e.into()),
|
err: err.map(Into::into),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -82,7 +98,7 @@ impl From<CreateBufferError> for WebGpuError {
|
||||||
match err {
|
match err {
|
||||||
CreateBufferError::Device(err) => err.into(),
|
CreateBufferError::Device(err) => err.into(),
|
||||||
CreateBufferError::AccessError(err) => err.into(),
|
CreateBufferError::AccessError(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -92,7 +108,7 @@ impl From<DeviceError> for WebGpuError {
|
||||||
match err {
|
match err {
|
||||||
DeviceError::Lost => WebGpuError::Lost,
|
DeviceError::Lost => WebGpuError::Lost,
|
||||||
DeviceError::OutOfMemory => WebGpuError::OutOfMemory,
|
DeviceError::OutOfMemory => WebGpuError::OutOfMemory,
|
||||||
DeviceError::Invalid => WebGpuError::Validation(err.to_string()),
|
DeviceError::Invalid => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -101,7 +117,7 @@ impl From<BufferAccessError> for WebGpuError {
|
||||||
fn from(err: BufferAccessError) -> Self {
|
fn from(err: BufferAccessError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
BufferAccessError::Device(err) => err.into(),
|
BufferAccessError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -110,7 +126,7 @@ impl From<CreateBindGroupLayoutError> for WebGpuError {
|
||||||
fn from(err: CreateBindGroupLayoutError) -> Self {
|
fn from(err: CreateBindGroupLayoutError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateBindGroupLayoutError::Device(err) => err.into(),
|
CreateBindGroupLayoutError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -119,7 +135,7 @@ impl From<CreatePipelineLayoutError> for WebGpuError {
|
||||||
fn from(err: CreatePipelineLayoutError) -> Self {
|
fn from(err: CreatePipelineLayoutError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreatePipelineLayoutError::Device(err) => err.into(),
|
CreatePipelineLayoutError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -128,44 +144,44 @@ impl From<CreateBindGroupError> for WebGpuError {
|
||||||
fn from(err: CreateBindGroupError) -> Self {
|
fn from(err: CreateBindGroupError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateBindGroupError::Device(err) => err.into(),
|
CreateBindGroupError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<RenderBundleError> for WebGpuError {
|
impl From<RenderBundleError> for WebGpuError {
|
||||||
fn from(err: RenderBundleError) -> Self {
|
fn from(err: RenderBundleError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<CreateRenderBundleError> for WebGpuError {
|
impl From<CreateRenderBundleError> for WebGpuError {
|
||||||
fn from(err: CreateRenderBundleError) -> Self {
|
fn from(err: CreateRenderBundleError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<CopyError> for WebGpuError {
|
impl From<CopyError> for WebGpuError {
|
||||||
fn from(err: CopyError) -> Self {
|
fn from(err: CopyError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<CommandEncoderError> for WebGpuError {
|
impl From<CommandEncoderError> for WebGpuError {
|
||||||
fn from(err: CommandEncoderError) -> Self {
|
fn from(err: CommandEncoderError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<QueryError> for WebGpuError {
|
impl From<QueryError> for WebGpuError {
|
||||||
fn from(err: QueryError) -> Self {
|
fn from(err: QueryError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<ComputePassError> for WebGpuError {
|
impl From<ComputePassError> for WebGpuError {
|
||||||
fn from(err: ComputePassError) -> Self {
|
fn from(err: ComputePassError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -173,14 +189,14 @@ impl From<CreateComputePipelineError> for WebGpuError {
|
||||||
fn from(err: CreateComputePipelineError) -> Self {
|
fn from(err: CreateComputePipelineError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateComputePipelineError::Device(err) => err.into(),
|
CreateComputePipelineError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<GetBindGroupLayoutError> for WebGpuError {
|
impl From<GetBindGroupLayoutError> for WebGpuError {
|
||||||
fn from(err: GetBindGroupLayoutError) -> Self {
|
fn from(err: GetBindGroupLayoutError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -188,14 +204,14 @@ impl From<CreateRenderPipelineError> for WebGpuError {
|
||||||
fn from(err: CreateRenderPipelineError) -> Self {
|
fn from(err: CreateRenderPipelineError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateRenderPipelineError::Device(err) => err.into(),
|
CreateRenderPipelineError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<RenderPassError> for WebGpuError {
|
impl From<RenderPassError> for WebGpuError {
|
||||||
fn from(err: RenderPassError) -> Self {
|
fn from(err: RenderPassError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -203,7 +219,7 @@ impl From<CreateSamplerError> for WebGpuError {
|
||||||
fn from(err: CreateSamplerError) -> Self {
|
fn from(err: CreateSamplerError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateSamplerError::Device(err) => err.into(),
|
CreateSamplerError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -212,7 +228,7 @@ impl From<CreateShaderModuleError> for WebGpuError {
|
||||||
fn from(err: CreateShaderModuleError) -> Self {
|
fn from(err: CreateShaderModuleError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateShaderModuleError::Device(err) => err.into(),
|
CreateShaderModuleError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -221,14 +237,14 @@ impl From<CreateTextureError> for WebGpuError {
|
||||||
fn from(err: CreateTextureError) -> Self {
|
fn from(err: CreateTextureError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateTextureError::Device(err) => err.into(),
|
CreateTextureError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<CreateTextureViewError> for WebGpuError {
|
impl From<CreateTextureViewError> for WebGpuError {
|
||||||
fn from(err: CreateTextureViewError) -> Self {
|
fn from(err: CreateTextureViewError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -236,7 +252,7 @@ impl From<CreateQuerySetError> for WebGpuError {
|
||||||
fn from(err: CreateQuerySetError) -> Self {
|
fn from(err: CreateQuerySetError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
CreateQuerySetError::Device(err) => err.into(),
|
CreateQuerySetError::Device(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -245,7 +261,7 @@ impl From<QueueSubmitError> for WebGpuError {
|
||||||
fn from(err: QueueSubmitError) -> Self {
|
fn from(err: QueueSubmitError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
QueueSubmitError::Queue(err) => err.into(),
|
QueueSubmitError::Queue(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -254,14 +270,14 @@ impl From<QueueWriteError> for WebGpuError {
|
||||||
fn from(err: QueueWriteError) -> Self {
|
fn from(err: QueueWriteError) -> Self {
|
||||||
match err {
|
match err {
|
||||||
QueueWriteError::Queue(err) => err.into(),
|
QueueWriteError::Queue(err) => err.into(),
|
||||||
err => WebGpuError::Validation(err.to_string()),
|
err => WebGpuError::Validation(fmt_err(&err)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<ClearError> for WebGpuError {
|
impl From<ClearError> for WebGpuError {
|
||||||
fn from(err: ClearError) -> Self {
|
fn from(err: ClearError) -> Self {
|
||||||
WebGpuError::Validation(err.to_string())
|
WebGpuError::Validation(fmt_err(&err))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -3,9 +3,7 @@
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::include_js_files;
|
use deno_core::include_js_files;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
|
||||||
use deno_core::Extension;
|
use deno_core::Extension;
|
||||||
use deno_core::OpDecl;
|
|
||||||
use deno_core::OpState;
|
use deno_core::OpState;
|
||||||
use deno_core::Resource;
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
|
@ -14,10 +12,10 @@ use serde::Serialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
use std::collections::HashSet;
|
use std::collections::HashSet;
|
||||||
|
use std::convert::TryFrom;
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
pub use wgpu_core;
|
pub use wgpu_core;
|
||||||
pub use wgpu_types;
|
pub use wgpu_types;
|
||||||
use wgpu_types::PowerPreference;
|
|
||||||
|
|
||||||
use error::DomExceptionOperationError;
|
use error::DomExceptionOperationError;
|
||||||
use error::WebGpuResult;
|
use error::WebGpuResult;
|
||||||
|
@ -130,6 +128,12 @@ fn deserialize_features(features: &wgpu_types::Features) -> Vec<&'static str> {
|
||||||
if features.contains(wgpu_types::Features::DEPTH_CLIP_CONTROL) {
|
if features.contains(wgpu_types::Features::DEPTH_CLIP_CONTROL) {
|
||||||
return_features.push("depth-clip-control");
|
return_features.push("depth-clip-control");
|
||||||
}
|
}
|
||||||
|
if features.contains(wgpu_types::Features::DEPTH24UNORM_STENCIL8) {
|
||||||
|
return_features.push("depth24unorm-stencil8");
|
||||||
|
}
|
||||||
|
if features.contains(wgpu_types::Features::DEPTH32FLOAT_STENCIL8) {
|
||||||
|
return_features.push("depth32float-stencil8");
|
||||||
|
}
|
||||||
if features.contains(wgpu_types::Features::PIPELINE_STATISTICS_QUERY) {
|
if features.contains(wgpu_types::Features::PIPELINE_STATISTICS_QUERY) {
|
||||||
return_features.push("pipeline-statistics-query");
|
return_features.push("pipeline-statistics-query");
|
||||||
}
|
}
|
||||||
|
@ -148,6 +152,9 @@ fn deserialize_features(features: &wgpu_types::Features) -> Vec<&'static str> {
|
||||||
if features.contains(wgpu_types::Features::INDIRECT_FIRST_INSTANCE) {
|
if features.contains(wgpu_types::Features::INDIRECT_FIRST_INSTANCE) {
|
||||||
return_features.push("indirect-first-instance");
|
return_features.push("indirect-first-instance");
|
||||||
}
|
}
|
||||||
|
if features.contains(wgpu_types::Features::SHADER_FLOAT16) {
|
||||||
|
return_features.push("shader-f16")
|
||||||
|
}
|
||||||
|
|
||||||
// extended from spec
|
// extended from spec
|
||||||
if features.contains(wgpu_types::Features::MAPPABLE_PRIMARY_BUFFERS) {
|
if features.contains(wgpu_types::Features::MAPPABLE_PRIMARY_BUFFERS) {
|
||||||
|
@ -172,18 +179,6 @@ fn deserialize_features(features: &wgpu_types::Features) -> Vec<&'static str> {
|
||||||
) {
|
) {
|
||||||
return_features.push("uniform-buffer-and-storage-buffer-texture-non-uniform-indexing");
|
return_features.push("uniform-buffer-and-storage-buffer-texture-non-uniform-indexing");
|
||||||
}
|
}
|
||||||
if features.contains(wgpu_types::Features::UNSIZED_BINDING_ARRAY) {
|
|
||||||
return_features.push("unsized-binding-array");
|
|
||||||
}
|
|
||||||
if features.contains(wgpu_types::Features::MULTI_DRAW_INDIRECT) {
|
|
||||||
return_features.push("multi-draw-indirect");
|
|
||||||
}
|
|
||||||
if features.contains(wgpu_types::Features::MULTI_DRAW_INDIRECT_COUNT) {
|
|
||||||
return_features.push("multi-draw-indirect-count");
|
|
||||||
}
|
|
||||||
if features.contains(wgpu_types::Features::PUSH_CONSTANTS) {
|
|
||||||
return_features.push("push-constants");
|
|
||||||
}
|
|
||||||
if features.contains(wgpu_types::Features::ADDRESS_MODE_CLAMP_TO_BORDER) {
|
if features.contains(wgpu_types::Features::ADDRESS_MODE_CLAMP_TO_BORDER) {
|
||||||
return_features.push("address-mode-clamp-to-border");
|
return_features.push("address-mode-clamp-to-border");
|
||||||
}
|
}
|
||||||
|
@ -198,32 +193,22 @@ fn deserialize_features(features: &wgpu_types::Features) -> Vec<&'static str> {
|
||||||
if features.contains(wgpu_types::Features::VERTEX_ATTRIBUTE_64BIT) {
|
if features.contains(wgpu_types::Features::VERTEX_ATTRIBUTE_64BIT) {
|
||||||
return_features.push("vertex-attribute-64bit");
|
return_features.push("vertex-attribute-64bit");
|
||||||
}
|
}
|
||||||
if features.contains(wgpu_types::Features::CONSERVATIVE_RASTERIZATION) {
|
|
||||||
return_features.push("conservative-rasterization");
|
|
||||||
}
|
|
||||||
if features.contains(wgpu_types::Features::VERTEX_WRITABLE_STORAGE) {
|
if features.contains(wgpu_types::Features::VERTEX_WRITABLE_STORAGE) {
|
||||||
return_features.push("vertex-writable-storage");
|
return_features.push("vertex-writable-storage");
|
||||||
}
|
}
|
||||||
if features.contains(wgpu_types::Features::CLEAR_COMMANDS) {
|
if features.contains(wgpu_types::Features::CLEAR_TEXTURE) {
|
||||||
return_features.push("clear-texture");
|
return_features.push("clear-texture");
|
||||||
}
|
}
|
||||||
if features.contains(wgpu_types::Features::SPIRV_SHADER_PASSTHROUGH) {
|
|
||||||
return_features.push("spirv-shader-passthrough");
|
|
||||||
}
|
|
||||||
if features.contains(wgpu_types::Features::SHADER_PRIMITIVE_INDEX) {
|
if features.contains(wgpu_types::Features::SHADER_PRIMITIVE_INDEX) {
|
||||||
return_features.push("shader-primitive-index");
|
return_features.push("shader-primitive-index");
|
||||||
}
|
}
|
||||||
|
if features.contains(wgpu_types::Features::PARTIALLY_BOUND_BINDING_ARRAY) {
|
||||||
|
return_features.push("shader-primitive-index");
|
||||||
|
}
|
||||||
|
|
||||||
return_features
|
return_features
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RequestAdapterArgs {
|
|
||||||
power_preference: Option<wgpu_types::PowerPreference>,
|
|
||||||
force_fallback_adapter: bool,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Serialize)]
|
#[derive(Serialize)]
|
||||||
#[serde(untagged)]
|
#[serde(untagged)]
|
||||||
pub enum GpuAdapterDeviceOrErr {
|
pub enum GpuAdapterDeviceOrErr {
|
||||||
|
@ -235,7 +220,6 @@ pub enum GpuAdapterDeviceOrErr {
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
pub struct GpuAdapterDevice {
|
pub struct GpuAdapterDevice {
|
||||||
rid: ResourceId,
|
rid: ResourceId,
|
||||||
name: Option<String>,
|
|
||||||
limits: wgpu_types::Limits,
|
limits: wgpu_types::Limits,
|
||||||
features: Vec<&'static str>,
|
features: Vec<&'static str>,
|
||||||
is_software: bool,
|
is_software: bool,
|
||||||
|
@ -244,15 +228,15 @@ pub struct GpuAdapterDevice {
|
||||||
#[op]
|
#[op]
|
||||||
pub async fn op_webgpu_request_adapter(
|
pub async fn op_webgpu_request_adapter(
|
||||||
state: Rc<RefCell<OpState>>,
|
state: Rc<RefCell<OpState>>,
|
||||||
args: RequestAdapterArgs,
|
power_preference: Option<wgpu_types::PowerPreference>,
|
||||||
|
force_fallback_adapter: bool,
|
||||||
) -> Result<GpuAdapterDeviceOrErr, AnyError> {
|
) -> Result<GpuAdapterDeviceOrErr, AnyError> {
|
||||||
let mut state = state.borrow_mut();
|
let mut state = state.borrow_mut();
|
||||||
check_unstable(&state, "navigator.gpu.requestAdapter");
|
check_unstable(&state, "navigator.gpu.requestAdapter");
|
||||||
let backends = std::env::var("DENO_WEBGPU_BACKEND")
|
let backends = std::env::var("DENO_WEBGPU_BACKEND").map_or_else(
|
||||||
.ok()
|
|_| wgpu_types::Backends::all(),
|
||||||
.map_or_else(wgpu_types::Backends::all, |s| {
|
|s| wgpu_core::instance::parse_backends_from_comma_list(&s),
|
||||||
wgpu_core::instance::parse_backends_from_comma_list(&s)
|
);
|
||||||
});
|
|
||||||
let instance = if let Some(instance) = state.try_borrow::<Instance>() {
|
let instance = if let Some(instance) = state.try_borrow::<Instance>() {
|
||||||
instance
|
instance
|
||||||
} else {
|
} else {
|
||||||
|
@ -265,11 +249,8 @@ pub async fn op_webgpu_request_adapter(
|
||||||
};
|
};
|
||||||
|
|
||||||
let descriptor = wgpu_core::instance::RequestAdapterOptions {
|
let descriptor = wgpu_core::instance::RequestAdapterOptions {
|
||||||
power_preference: match args.power_preference {
|
power_preference: power_preference.unwrap_or_default(),
|
||||||
Some(power_preference) => power_preference,
|
force_fallback_adapter,
|
||||||
None => PowerPreference::default(),
|
|
||||||
},
|
|
||||||
force_fallback_adapter: args.force_fallback_adapter,
|
|
||||||
compatible_surface: None, // windowless
|
compatible_surface: None, // windowless
|
||||||
};
|
};
|
||||||
let res = instance.request_adapter(
|
let res = instance.request_adapter(
|
||||||
|
@ -287,7 +268,6 @@ pub async fn op_webgpu_request_adapter(
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
let name = gfx_select!(adapter => instance.adapter_get_info(adapter))?.name;
|
|
||||||
let adapter_features =
|
let adapter_features =
|
||||||
gfx_select!(adapter => instance.adapter_features(adapter))?;
|
gfx_select!(adapter => instance.adapter_features(adapter))?;
|
||||||
let features = deserialize_features(&adapter_features);
|
let features = deserialize_features(&adapter_features);
|
||||||
|
@ -298,22 +278,12 @@ pub async fn op_webgpu_request_adapter(
|
||||||
|
|
||||||
Ok(GpuAdapterDeviceOrErr::Features(GpuAdapterDevice {
|
Ok(GpuAdapterDeviceOrErr::Features(GpuAdapterDevice {
|
||||||
rid,
|
rid,
|
||||||
name: Some(name),
|
|
||||||
features,
|
features,
|
||||||
limits: adapter_limits,
|
limits: adapter_limits,
|
||||||
is_software: false,
|
is_software: false,
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RequestDeviceArgs {
|
|
||||||
adapter_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
required_features: Option<GpuRequiredFeatures>,
|
|
||||||
required_limits: Option<wgpu_types::Limits>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
pub struct GpuRequiredFeatures(HashSet<String>);
|
pub struct GpuRequiredFeatures(HashSet<String>);
|
||||||
|
|
||||||
|
@ -324,6 +294,14 @@ impl From<GpuRequiredFeatures> for wgpu_types::Features {
|
||||||
wgpu_types::Features::DEPTH_CLIP_CONTROL,
|
wgpu_types::Features::DEPTH_CLIP_CONTROL,
|
||||||
required_features.0.contains("depth-clip-control"),
|
required_features.0.contains("depth-clip-control"),
|
||||||
);
|
);
|
||||||
|
features.set(
|
||||||
|
wgpu_types::Features::DEPTH24UNORM_STENCIL8,
|
||||||
|
required_features.0.contains("depth24unorm-stencil8"),
|
||||||
|
);
|
||||||
|
features.set(
|
||||||
|
wgpu_types::Features::DEPTH32FLOAT_STENCIL8,
|
||||||
|
required_features.0.contains("depth32float-stencil8"),
|
||||||
|
);
|
||||||
features.set(
|
features.set(
|
||||||
wgpu_types::Features::PIPELINE_STATISTICS_QUERY,
|
wgpu_types::Features::PIPELINE_STATISTICS_QUERY,
|
||||||
required_features.0.contains("pipeline-statistics-query"),
|
required_features.0.contains("pipeline-statistics-query"),
|
||||||
|
@ -348,6 +326,10 @@ impl From<GpuRequiredFeatures> for wgpu_types::Features {
|
||||||
wgpu_types::Features::INDIRECT_FIRST_INSTANCE,
|
wgpu_types::Features::INDIRECT_FIRST_INSTANCE,
|
||||||
required_features.0.contains("indirect-first-instance"),
|
required_features.0.contains("indirect-first-instance"),
|
||||||
);
|
);
|
||||||
|
features.set(
|
||||||
|
wgpu_types::Features::SHADER_FLOAT16,
|
||||||
|
required_features.0.contains("shader-f16"),
|
||||||
|
);
|
||||||
|
|
||||||
// extended from spec
|
// extended from spec
|
||||||
features.set(
|
features.set(
|
||||||
|
@ -380,22 +362,6 @@ impl From<GpuRequiredFeatures> for wgpu_types::Features {
|
||||||
.0
|
.0
|
||||||
.contains("uniform-buffer-and-storage-buffer-texture-non-uniform-indexing"),
|
.contains("uniform-buffer-and-storage-buffer-texture-non-uniform-indexing"),
|
||||||
);
|
);
|
||||||
features.set(
|
|
||||||
wgpu_types::Features::UNSIZED_BINDING_ARRAY,
|
|
||||||
required_features.0.contains("unsized-binding-array"),
|
|
||||||
);
|
|
||||||
features.set(
|
|
||||||
wgpu_types::Features::MULTI_DRAW_INDIRECT,
|
|
||||||
required_features.0.contains("multi-draw-indirect"),
|
|
||||||
);
|
|
||||||
features.set(
|
|
||||||
wgpu_types::Features::MULTI_DRAW_INDIRECT_COUNT,
|
|
||||||
required_features.0.contains("multi-draw-indirect-count"),
|
|
||||||
);
|
|
||||||
features.set(
|
|
||||||
wgpu_types::Features::PUSH_CONSTANTS,
|
|
||||||
required_features.0.contains("push-constants"),
|
|
||||||
);
|
|
||||||
features.set(
|
features.set(
|
||||||
wgpu_types::Features::ADDRESS_MODE_CLAMP_TO_BORDER,
|
wgpu_types::Features::ADDRESS_MODE_CLAMP_TO_BORDER,
|
||||||
required_features.0.contains("address-mode-clamp-to-border"),
|
required_features.0.contains("address-mode-clamp-to-border"),
|
||||||
|
@ -414,26 +380,24 @@ impl From<GpuRequiredFeatures> for wgpu_types::Features {
|
||||||
wgpu_types::Features::VERTEX_ATTRIBUTE_64BIT,
|
wgpu_types::Features::VERTEX_ATTRIBUTE_64BIT,
|
||||||
required_features.0.contains("vertex-attribute-64bit"),
|
required_features.0.contains("vertex-attribute-64bit"),
|
||||||
);
|
);
|
||||||
features.set(
|
|
||||||
wgpu_types::Features::CONSERVATIVE_RASTERIZATION,
|
|
||||||
required_features.0.contains("conservative-rasterization"),
|
|
||||||
);
|
|
||||||
features.set(
|
features.set(
|
||||||
wgpu_types::Features::VERTEX_WRITABLE_STORAGE,
|
wgpu_types::Features::VERTEX_WRITABLE_STORAGE,
|
||||||
required_features.0.contains("vertex-writable-storage"),
|
required_features.0.contains("vertex-writable-storage"),
|
||||||
);
|
);
|
||||||
features.set(
|
features.set(
|
||||||
wgpu_types::Features::CLEAR_COMMANDS,
|
wgpu_types::Features::CLEAR_TEXTURE,
|
||||||
required_features.0.contains("clear-commands"),
|
required_features.0.contains("clear-commands"),
|
||||||
);
|
);
|
||||||
features.set(
|
|
||||||
wgpu_types::Features::SPIRV_SHADER_PASSTHROUGH,
|
|
||||||
required_features.0.contains("spirv-shader-passthrough"),
|
|
||||||
);
|
|
||||||
features.set(
|
features.set(
|
||||||
wgpu_types::Features::SHADER_PRIMITIVE_INDEX,
|
wgpu_types::Features::SHADER_PRIMITIVE_INDEX,
|
||||||
required_features.0.contains("shader-primitive-index"),
|
required_features.0.contains("shader-primitive-index"),
|
||||||
);
|
);
|
||||||
|
features.set(
|
||||||
|
wgpu_types::Features::PARTIALLY_BOUND_BINDING_ARRAY,
|
||||||
|
required_features
|
||||||
|
.0
|
||||||
|
.contains("partially-bound-binding-array"),
|
||||||
|
);
|
||||||
|
|
||||||
features
|
features
|
||||||
}
|
}
|
||||||
|
@ -442,19 +406,21 @@ impl From<GpuRequiredFeatures> for wgpu_types::Features {
|
||||||
#[op]
|
#[op]
|
||||||
pub async fn op_webgpu_request_device(
|
pub async fn op_webgpu_request_device(
|
||||||
state: Rc<RefCell<OpState>>,
|
state: Rc<RefCell<OpState>>,
|
||||||
args: RequestDeviceArgs,
|
adapter_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
|
required_features: Option<GpuRequiredFeatures>,
|
||||||
|
required_limits: Option<wgpu_types::Limits>,
|
||||||
) -> Result<GpuAdapterDevice, AnyError> {
|
) -> Result<GpuAdapterDevice, AnyError> {
|
||||||
let mut state = state.borrow_mut();
|
let mut state = state.borrow_mut();
|
||||||
let adapter_resource = state
|
let adapter_resource =
|
||||||
.resource_table
|
state.resource_table.get::<WebGpuAdapter>(adapter_rid)?;
|
||||||
.get::<WebGpuAdapter>(args.adapter_rid)?;
|
|
||||||
let adapter = adapter_resource.0;
|
let adapter = adapter_resource.0;
|
||||||
let instance = state.borrow::<Instance>();
|
let instance = state.borrow::<Instance>();
|
||||||
|
|
||||||
let descriptor = wgpu_types::DeviceDescriptor {
|
let descriptor = wgpu_types::DeviceDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
features: args.required_features.map(Into::into).unwrap_or_default(),
|
features: required_features.map(Into::into).unwrap_or_default(),
|
||||||
limits: args.required_limits.map(Into::into).unwrap_or_default(),
|
limits: required_limits.map(Into::into).unwrap_or_default(),
|
||||||
};
|
};
|
||||||
|
|
||||||
let (device, maybe_err) = gfx_select!(adapter => instance.adapter_request_device(
|
let (device, maybe_err) = gfx_select!(adapter => instance.adapter_request_device(
|
||||||
|
@ -476,7 +442,6 @@ pub async fn op_webgpu_request_device(
|
||||||
|
|
||||||
Ok(GpuAdapterDevice {
|
Ok(GpuAdapterDevice {
|
||||||
rid,
|
rid,
|
||||||
name: None,
|
|
||||||
features,
|
features,
|
||||||
limits,
|
limits,
|
||||||
// TODO(lucacasonato): report correctly from wgpu
|
// TODO(lucacasonato): report correctly from wgpu
|
||||||
|
@ -484,6 +449,36 @@ pub async fn op_webgpu_request_device(
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Serialize)]
|
||||||
|
#[serde(rename_all = "camelCase")]
|
||||||
|
pub struct GPUAdapterInfo {
|
||||||
|
vendor: String,
|
||||||
|
architecture: String,
|
||||||
|
device: String,
|
||||||
|
description: String,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[op]
|
||||||
|
pub async fn op_webgpu_request_adapter_info(
|
||||||
|
state: Rc<RefCell<OpState>>,
|
||||||
|
adapter_rid: ResourceId,
|
||||||
|
) -> Result<GPUAdapterInfo, AnyError> {
|
||||||
|
let state = state.borrow_mut();
|
||||||
|
let adapter_resource =
|
||||||
|
state.resource_table.get::<WebGpuAdapter>(adapter_rid)?;
|
||||||
|
let adapter = adapter_resource.0;
|
||||||
|
let instance = state.borrow::<Instance>();
|
||||||
|
|
||||||
|
let info = gfx_select!(adapter => instance.adapter_get_info(adapter))?;
|
||||||
|
|
||||||
|
Ok(GPUAdapterInfo {
|
||||||
|
vendor: info.vendor.to_string(),
|
||||||
|
architecture: String::new(), // TODO(#2170)
|
||||||
|
device: info.device.to_string(),
|
||||||
|
description: info.name,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
pub struct CreateQuerySetArgs {
|
pub struct CreateQuerySetArgs {
|
||||||
|
@ -562,11 +557,12 @@ pub fn op_webgpu_create_query_set(
|
||||||
) => state, WebGpuQuerySet)
|
) => state, WebGpuQuerySet)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn declare_webgpu_ops() -> Vec<OpDecl> {
|
fn declare_webgpu_ops() -> Vec<deno_core::OpDecl> {
|
||||||
vec![
|
vec![
|
||||||
// Request device/adapter
|
// Request device/adapter
|
||||||
op_webgpu_request_adapter::decl(),
|
op_webgpu_request_adapter::decl(),
|
||||||
op_webgpu_request_device::decl(),
|
op_webgpu_request_device::decl(),
|
||||||
|
op_webgpu_request_adapter_info::decl(),
|
||||||
// Query Set
|
// Query Set
|
||||||
op_webgpu_create_query_set::decl(),
|
op_webgpu_create_query_set::decl(),
|
||||||
// buffer
|
// buffer
|
||||||
|
@ -615,7 +611,7 @@ fn declare_webgpu_ops() -> Vec<OpDecl> {
|
||||||
render_pass::op_webgpu_render_pass_end_pipeline_statistics_query::decl(),
|
render_pass::op_webgpu_render_pass_end_pipeline_statistics_query::decl(),
|
||||||
render_pass::op_webgpu_render_pass_write_timestamp::decl(),
|
render_pass::op_webgpu_render_pass_write_timestamp::decl(),
|
||||||
render_pass::op_webgpu_render_pass_execute_bundles::decl(),
|
render_pass::op_webgpu_render_pass_execute_bundles::decl(),
|
||||||
render_pass::op_webgpu_render_pass_end_pass::decl(),
|
render_pass::op_webgpu_render_pass_end::decl(),
|
||||||
render_pass::op_webgpu_render_pass_set_bind_group::decl(),
|
render_pass::op_webgpu_render_pass_set_bind_group::decl(),
|
||||||
render_pass::op_webgpu_render_pass_push_debug_group::decl(),
|
render_pass::op_webgpu_render_pass_push_debug_group::decl(),
|
||||||
render_pass::op_webgpu_render_pass_pop_debug_group::decl(),
|
render_pass::op_webgpu_render_pass_pop_debug_group::decl(),
|
||||||
|
@ -629,13 +625,13 @@ fn declare_webgpu_ops() -> Vec<OpDecl> {
|
||||||
render_pass::op_webgpu_render_pass_draw_indexed_indirect::decl(),
|
render_pass::op_webgpu_render_pass_draw_indexed_indirect::decl(),
|
||||||
// compute_pass
|
// compute_pass
|
||||||
compute_pass::op_webgpu_compute_pass_set_pipeline::decl(),
|
compute_pass::op_webgpu_compute_pass_set_pipeline::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_dispatch::decl(),
|
compute_pass::op_webgpu_compute_pass_dispatch_workgroups::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_dispatch_indirect::decl(),
|
compute_pass::op_webgpu_compute_pass_dispatch_workgroups_indirect::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_begin_pipeline_statistics_query::decl(
|
compute_pass::op_webgpu_compute_pass_begin_pipeline_statistics_query::decl(
|
||||||
),
|
),
|
||||||
compute_pass::op_webgpu_compute_pass_end_pipeline_statistics_query::decl(),
|
compute_pass::op_webgpu_compute_pass_end_pipeline_statistics_query::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_write_timestamp::decl(),
|
compute_pass::op_webgpu_compute_pass_write_timestamp::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_end_pass::decl(),
|
compute_pass::op_webgpu_compute_pass_end::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_set_bind_group::decl(),
|
compute_pass::op_webgpu_compute_pass_set_bind_group::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_push_debug_group::decl(),
|
compute_pass::op_webgpu_compute_pass_push_debug_group::decl(),
|
||||||
compute_pass::op_webgpu_compute_pass_pop_debug_group::decl(),
|
compute_pass::op_webgpu_compute_pass_pop_debug_group::decl(),
|
||||||
|
|
|
@ -2,12 +2,12 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use serde::Serialize;
|
use serde::Serialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::convert::{TryFrom, TryInto};
|
|
||||||
|
|
||||||
use super::error::WebGpuError;
|
use super::error::WebGpuError;
|
||||||
use super::error::WebGpuResult;
|
use super::error::WebGpuResult;
|
||||||
|
@ -43,59 +43,69 @@ impl Resource for WebGpuRenderPipeline {
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
struct GpuProgrammableStage {
|
pub enum GPUAutoLayoutMode {
|
||||||
|
Auto,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Deserialize)]
|
||||||
|
#[serde(untagged)]
|
||||||
|
pub enum GPUPipelineLayoutOrGPUAutoLayoutMode {
|
||||||
|
Layout(ResourceId),
|
||||||
|
Auto(GPUAutoLayoutMode),
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Deserialize)]
|
||||||
|
#[serde(rename_all = "camelCase")]
|
||||||
|
pub struct GpuProgrammableStage {
|
||||||
module: ResourceId,
|
module: ResourceId,
|
||||||
entry_point: String,
|
entry_point: String,
|
||||||
// constants: HashMap<String, GPUPipelineConstantValue>
|
// constants: HashMap<String, GPUPipelineConstantValue>
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct CreateComputePipelineArgs {
|
|
||||||
device_rid: ResourceId,
|
|
||||||
label: Option<String>,
|
|
||||||
layout: Option<ResourceId>,
|
|
||||||
compute: GpuProgrammableStage,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_create_compute_pipeline(
|
pub fn op_webgpu_create_compute_pipeline(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: CreateComputePipelineArgs,
|
device_rid: ResourceId,
|
||||||
|
label: Option<String>,
|
||||||
|
layout: GPUPipelineLayoutOrGPUAutoLayoutMode,
|
||||||
|
compute: GpuProgrammableStage,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let device_resource = state
|
let device_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let pipeline_layout = if let Some(rid) = args.layout {
|
let pipeline_layout = match layout {
|
||||||
let id = state.resource_table.get::<WebGpuPipelineLayout>(rid)?;
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Layout(rid) => {
|
||||||
Some(id.0)
|
let id = state.resource_table.get::<WebGpuPipelineLayout>(rid)?;
|
||||||
} else {
|
Some(id.0)
|
||||||
None
|
}
|
||||||
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Auto(GPUAutoLayoutMode::Auto) => None,
|
||||||
};
|
};
|
||||||
|
|
||||||
let compute_shader_module_resource =
|
let compute_shader_module_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::shader::WebGpuShaderModule>(args.compute.module)?;
|
.get::<super::shader::WebGpuShaderModule>(compute.module)?;
|
||||||
|
|
||||||
let descriptor = wgpu_core::pipeline::ComputePipelineDescriptor {
|
let descriptor = wgpu_core::pipeline::ComputePipelineDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
layout: pipeline_layout,
|
layout: pipeline_layout,
|
||||||
stage: wgpu_core::pipeline::ProgrammableStageDescriptor {
|
stage: wgpu_core::pipeline::ProgrammableStageDescriptor {
|
||||||
module: compute_shader_module_resource.0,
|
module: compute_shader_module_resource.0,
|
||||||
entry_point: Cow::from(args.compute.entry_point),
|
entry_point: Cow::from(compute.entry_point),
|
||||||
// TODO(lucacasonato): support args.compute.constants
|
// TODO(lucacasonato): support args.compute.constants
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
let implicit_pipelines = match args.layout {
|
let implicit_pipelines = match layout {
|
||||||
Some(_) => None,
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Layout(_) => None,
|
||||||
None => Some(wgpu_core::device::ImplicitPipelineIds {
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Auto(GPUAutoLayoutMode::Auto) => {
|
||||||
root_id: std::marker::PhantomData,
|
Some(wgpu_core::device::ImplicitPipelineIds {
|
||||||
group_ids: &[std::marker::PhantomData; MAX_BIND_GROUPS],
|
root_id: std::marker::PhantomData,
|
||||||
}),
|
group_ids: &[std::marker::PhantomData; MAX_BIND_GROUPS],
|
||||||
|
})
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
let (compute_pipeline, maybe_err) = gfx_select!(device => instance.device_create_compute_pipeline(
|
let (compute_pipeline, maybe_err) = gfx_select!(device => instance.device_create_compute_pipeline(
|
||||||
|
@ -112,13 +122,6 @@ pub fn op_webgpu_create_compute_pipeline(
|
||||||
Ok(WebGpuResult::rid_err(rid, maybe_err))
|
Ok(WebGpuResult::rid_err(rid, maybe_err))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct ComputePipelineGetBindGroupLayoutArgs {
|
|
||||||
compute_pipeline_rid: ResourceId,
|
|
||||||
index: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Serialize)]
|
#[derive(Serialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
pub struct PipelineLayout {
|
pub struct PipelineLayout {
|
||||||
|
@ -130,15 +133,16 @@ pub struct PipelineLayout {
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_compute_pipeline_get_bind_group_layout(
|
pub fn op_webgpu_compute_pipeline_get_bind_group_layout(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: ComputePipelineGetBindGroupLayoutArgs,
|
compute_pipeline_rid: ResourceId,
|
||||||
|
index: u32,
|
||||||
) -> Result<PipelineLayout, AnyError> {
|
) -> Result<PipelineLayout, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let compute_pipeline_resource = state
|
let compute_pipeline_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuComputePipeline>(args.compute_pipeline_rid)?;
|
.get::<WebGpuComputePipeline>(compute_pipeline_rid)?;
|
||||||
let compute_pipeline = compute_pipeline_resource.0;
|
let compute_pipeline = compute_pipeline_resource.0;
|
||||||
|
|
||||||
let (bind_group_layout, maybe_err) = gfx_select!(compute_pipeline => instance.compute_pipeline_get_bind_group_layout(compute_pipeline, args.index, std::marker::PhantomData));
|
let (bind_group_layout, maybe_err) = gfx_select!(compute_pipeline => instance.compute_pipeline_get_bind_group_layout(compute_pipeline, index, std::marker::PhantomData));
|
||||||
|
|
||||||
let label = gfx_select!(bind_group_layout => instance.bind_group_layout_label(bind_group_layout));
|
let label = gfx_select!(bind_group_layout => instance.bind_group_layout_label(bind_group_layout));
|
||||||
|
|
||||||
|
@ -210,12 +214,9 @@ struct GpuDepthStencilState {
|
||||||
depth_bias_clamp: f32,
|
depth_bias_clamp: f32,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl TryFrom<GpuDepthStencilState> for wgpu_types::DepthStencilState {
|
impl From<GpuDepthStencilState> for wgpu_types::DepthStencilState {
|
||||||
type Error = AnyError;
|
fn from(state: GpuDepthStencilState) -> wgpu_types::DepthStencilState {
|
||||||
fn try_from(
|
wgpu_types::DepthStencilState {
|
||||||
state: GpuDepthStencilState,
|
|
||||||
) -> Result<wgpu_types::DepthStencilState, AnyError> {
|
|
||||||
Ok(wgpu_types::DepthStencilState {
|
|
||||||
format: state.format,
|
format: state.format,
|
||||||
depth_write_enabled: state.depth_write_enabled,
|
depth_write_enabled: state.depth_write_enabled,
|
||||||
depth_compare: state.depth_compare,
|
depth_compare: state.depth_compare,
|
||||||
|
@ -230,7 +231,7 @@ impl TryFrom<GpuDepthStencilState> for wgpu_types::DepthStencilState {
|
||||||
slope_scale: state.depth_bias_slope_scale,
|
slope_scale: state.depth_bias_slope_scale,
|
||||||
clamp: state.depth_bias_clamp,
|
clamp: state.depth_bias_clamp,
|
||||||
},
|
},
|
||||||
})
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -285,7 +286,7 @@ impl From<GpuMultisampleState> for wgpu_types::MultisampleState {
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
struct GpuFragmentState {
|
struct GpuFragmentState {
|
||||||
targets: Vec<wgpu_types::ColorTargetState>,
|
targets: Vec<Option<wgpu_types::ColorTargetState>>,
|
||||||
module: u32,
|
module: u32,
|
||||||
entry_point: String,
|
entry_point: String,
|
||||||
// TODO(lucacasonato): constants
|
// TODO(lucacasonato): constants
|
||||||
|
@ -296,7 +297,7 @@ struct GpuFragmentState {
|
||||||
pub struct CreateRenderPipelineArgs {
|
pub struct CreateRenderPipelineArgs {
|
||||||
device_rid: ResourceId,
|
device_rid: ResourceId,
|
||||||
label: Option<String>,
|
label: Option<String>,
|
||||||
layout: Option<ResourceId>,
|
layout: GPUPipelineLayoutOrGPUAutoLayoutMode,
|
||||||
vertex: GpuVertexState,
|
vertex: GpuVertexState,
|
||||||
primitive: GpuPrimitiveState,
|
primitive: GpuPrimitiveState,
|
||||||
depth_stencil: Option<GpuDepthStencilState>,
|
depth_stencil: Option<GpuDepthStencilState>,
|
||||||
|
@ -315,12 +316,13 @@ pub fn op_webgpu_create_render_pipeline(
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(args.device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let layout = if let Some(rid) = args.layout {
|
let layout = match args.layout {
|
||||||
let pipeline_layout_resource =
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Layout(rid) => {
|
||||||
state.resource_table.get::<WebGpuPipelineLayout>(rid)?;
|
let pipeline_layout_resource =
|
||||||
Some(pipeline_layout_resource.0)
|
state.resource_table.get::<WebGpuPipelineLayout>(rid)?;
|
||||||
} else {
|
Some(pipeline_layout_resource.0)
|
||||||
None
|
}
|
||||||
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Auto(GPUAutoLayoutMode::Auto) => None,
|
||||||
};
|
};
|
||||||
|
|
||||||
let vertex_shader_module_resource =
|
let vertex_shader_module_resource =
|
||||||
|
@ -334,18 +336,12 @@ pub fn op_webgpu_create_render_pipeline(
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::shader::WebGpuShaderModule>(fragment.module)?;
|
.get::<super::shader::WebGpuShaderModule>(fragment.module)?;
|
||||||
|
|
||||||
let mut targets = Vec::with_capacity(fragment.targets.len());
|
|
||||||
|
|
||||||
for target in fragment.targets {
|
|
||||||
targets.push(target);
|
|
||||||
}
|
|
||||||
|
|
||||||
Some(wgpu_core::pipeline::FragmentState {
|
Some(wgpu_core::pipeline::FragmentState {
|
||||||
stage: wgpu_core::pipeline::ProgrammableStageDescriptor {
|
stage: wgpu_core::pipeline::ProgrammableStageDescriptor {
|
||||||
module: fragment_shader_module_resource.0,
|
module: fragment_shader_module_resource.0,
|
||||||
entry_point: Cow::from(fragment.entry_point),
|
entry_point: Cow::from(fragment.entry_point),
|
||||||
},
|
},
|
||||||
targets: Cow::from(targets),
|
targets: Cow::from(fragment.targets),
|
||||||
})
|
})
|
||||||
} else {
|
} else {
|
||||||
None
|
None
|
||||||
|
@ -370,18 +366,20 @@ pub fn op_webgpu_create_render_pipeline(
|
||||||
buffers: Cow::Owned(vertex_buffers),
|
buffers: Cow::Owned(vertex_buffers),
|
||||||
},
|
},
|
||||||
primitive: args.primitive.into(),
|
primitive: args.primitive.into(),
|
||||||
depth_stencil: args.depth_stencil.map(TryInto::try_into).transpose()?,
|
depth_stencil: args.depth_stencil.map(Into::into),
|
||||||
multisample: args.multisample,
|
multisample: args.multisample,
|
||||||
fragment,
|
fragment,
|
||||||
multiview: None,
|
multiview: None,
|
||||||
};
|
};
|
||||||
|
|
||||||
let implicit_pipelines = match args.layout {
|
let implicit_pipelines = match args.layout {
|
||||||
Some(_) => None,
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Layout(_) => None,
|
||||||
None => Some(wgpu_core::device::ImplicitPipelineIds {
|
GPUPipelineLayoutOrGPUAutoLayoutMode::Auto(GPUAutoLayoutMode::Auto) => {
|
||||||
root_id: std::marker::PhantomData,
|
Some(wgpu_core::device::ImplicitPipelineIds {
|
||||||
group_ids: &[std::marker::PhantomData; MAX_BIND_GROUPS],
|
root_id: std::marker::PhantomData,
|
||||||
}),
|
group_ids: &[std::marker::PhantomData; MAX_BIND_GROUPS],
|
||||||
|
})
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
let (render_pipeline, maybe_err) = gfx_select!(device => instance.device_create_render_pipeline(
|
let (render_pipeline, maybe_err) = gfx_select!(device => instance.device_create_render_pipeline(
|
||||||
|
@ -398,25 +396,19 @@ pub fn op_webgpu_create_render_pipeline(
|
||||||
Ok(WebGpuResult::rid_err(rid, maybe_err))
|
Ok(WebGpuResult::rid_err(rid, maybe_err))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPipelineGetBindGroupLayoutArgs {
|
|
||||||
render_pipeline_rid: ResourceId,
|
|
||||||
index: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pipeline_get_bind_group_layout(
|
pub fn op_webgpu_render_pipeline_get_bind_group_layout(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPipelineGetBindGroupLayoutArgs,
|
render_pipeline_rid: ResourceId,
|
||||||
|
index: u32,
|
||||||
) -> Result<PipelineLayout, AnyError> {
|
) -> Result<PipelineLayout, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let render_pipeline_resource = state
|
let render_pipeline_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPipeline>(args.render_pipeline_rid)?;
|
.get::<WebGpuRenderPipeline>(render_pipeline_rid)?;
|
||||||
let render_pipeline = render_pipeline_resource.0;
|
let render_pipeline = render_pipeline_resource.0;
|
||||||
|
|
||||||
let (bind_group_layout, maybe_err) = gfx_select!(render_pipeline => instance.render_pipeline_get_bind_group_layout(render_pipeline, args.index, std::marker::PhantomData));
|
let (bind_group_layout, maybe_err) = gfx_select!(render_pipeline => instance.render_pipeline_get_bind_group_layout(render_pipeline, index, std::marker::PhantomData));
|
||||||
|
|
||||||
let label = gfx_select!(bind_group_layout => instance.bind_group_layout_label(bind_group_layout));
|
let label = gfx_select!(bind_group_layout => instance.bind_group_layout_label(bind_group_layout));
|
||||||
|
|
||||||
|
|
|
@ -13,42 +13,40 @@ use super::error::WebGpuResult;
|
||||||
|
|
||||||
type WebGpuQueue = super::WebGpuDevice;
|
type WebGpuQueue = super::WebGpuDevice;
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct QueueSubmitArgs {
|
|
||||||
queue_rid: ResourceId,
|
|
||||||
command_buffers: Vec<ResourceId>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_queue_submit(
|
pub fn op_webgpu_queue_submit(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: QueueSubmitArgs,
|
queue_rid: ResourceId,
|
||||||
|
command_buffers: Vec<ResourceId>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let queue_resource =
|
let queue_resource = state.resource_table.get::<WebGpuQueue>(queue_rid)?;
|
||||||
state.resource_table.get::<WebGpuQueue>(args.queue_rid)?;
|
|
||||||
let queue = queue_resource.0;
|
let queue = queue_resource.0;
|
||||||
|
|
||||||
let mut ids = vec![];
|
let ids = command_buffers
|
||||||
|
.iter()
|
||||||
for rid in args.command_buffers {
|
.map(|rid| {
|
||||||
let buffer_resource =
|
let buffer_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::command_encoder::WebGpuCommandBuffer>(rid)?;
|
.get::<super::command_encoder::WebGpuCommandBuffer>(*rid)?;
|
||||||
ids.push(buffer_resource.0);
|
Ok(buffer_resource.0)
|
||||||
}
|
})
|
||||||
|
.collect::<Result<Vec<_>, AnyError>>()?;
|
||||||
|
|
||||||
let maybe_err =
|
let maybe_err =
|
||||||
gfx_select!(queue => instance.queue_submit(queue, &ids)).err();
|
gfx_select!(queue => instance.queue_submit(queue, &ids)).err();
|
||||||
|
|
||||||
|
for rid in command_buffers {
|
||||||
|
state.resource_table.close(rid)?;
|
||||||
|
}
|
||||||
|
|
||||||
Ok(WebGpuResult::maybe_err(maybe_err))
|
Ok(WebGpuResult::maybe_err(maybe_err))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[derive(Deserialize)]
|
||||||
#[serde(rename_all = "camelCase")]
|
#[serde(rename_all = "camelCase")]
|
||||||
struct GpuImageDataLayout {
|
pub struct GpuImageDataLayout {
|
||||||
offset: u64,
|
offset: u64,
|
||||||
bytes_per_row: Option<u32>,
|
bytes_per_row: Option<u32>,
|
||||||
rows_per_image: Option<u32>,
|
rows_per_image: Option<u32>,
|
||||||
|
@ -64,39 +62,32 @@ impl From<GpuImageDataLayout> for wgpu_types::ImageDataLayout {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_write_buffer(
|
||||||
pub struct QueueWriteBufferArgs {
|
state: &mut OpState,
|
||||||
queue_rid: ResourceId,
|
queue_rid: ResourceId,
|
||||||
buffer: ResourceId,
|
buffer: ResourceId,
|
||||||
buffer_offset: u64,
|
buffer_offset: u64,
|
||||||
data_offset: usize,
|
data_offset: usize,
|
||||||
size: Option<usize>,
|
size: Option<usize>,
|
||||||
}
|
buf: ZeroCopyBuf,
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_write_buffer(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: QueueWriteBufferArgs,
|
|
||||||
zero_copy: ZeroCopyBuf,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(buffer)?;
|
||||||
let buffer = buffer_resource.0;
|
let buffer = buffer_resource.0;
|
||||||
let queue_resource =
|
let queue_resource = state.resource_table.get::<WebGpuQueue>(queue_rid)?;
|
||||||
state.resource_table.get::<WebGpuQueue>(args.queue_rid)?;
|
|
||||||
let queue = queue_resource.0;
|
let queue = queue_resource.0;
|
||||||
|
|
||||||
let data = match args.size {
|
let data = match size {
|
||||||
Some(size) => &zero_copy[args.data_offset..(args.data_offset + size)],
|
Some(size) => &buf[data_offset..(data_offset + size)],
|
||||||
None => &zero_copy[args.data_offset..],
|
None => &buf[data_offset..],
|
||||||
};
|
};
|
||||||
let maybe_err = gfx_select!(queue => instance.queue_write_buffer(
|
let maybe_err = gfx_select!(queue => instance.queue_write_buffer(
|
||||||
queue,
|
queue,
|
||||||
buffer,
|
buffer,
|
||||||
args.buffer_offset,
|
buffer_offset,
|
||||||
data
|
data
|
||||||
))
|
))
|
||||||
.err();
|
.err();
|
||||||
|
@ -104,42 +95,35 @@ pub fn op_webgpu_write_buffer(
|
||||||
Ok(WebGpuResult::maybe_err(maybe_err))
|
Ok(WebGpuResult::maybe_err(maybe_err))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_write_texture(
|
||||||
pub struct QueueWriteTextureArgs {
|
state: &mut OpState,
|
||||||
queue_rid: ResourceId,
|
queue_rid: ResourceId,
|
||||||
destination: super::command_encoder::GpuImageCopyTexture,
|
destination: super::command_encoder::GpuImageCopyTexture,
|
||||||
data_layout: GpuImageDataLayout,
|
data_layout: GpuImageDataLayout,
|
||||||
size: wgpu_types::Extent3d,
|
size: wgpu_types::Extent3d,
|
||||||
}
|
buf: ZeroCopyBuf,
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_write_texture(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: QueueWriteTextureArgs,
|
|
||||||
zero_copy: ZeroCopyBuf,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let texture_resource = state
|
let texture_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::texture::WebGpuTexture>(args.destination.texture)?;
|
.get::<super::texture::WebGpuTexture>(destination.texture)?;
|
||||||
let queue_resource =
|
let queue_resource = state.resource_table.get::<WebGpuQueue>(queue_rid)?;
|
||||||
state.resource_table.get::<WebGpuQueue>(args.queue_rid)?;
|
|
||||||
let queue = queue_resource.0;
|
let queue = queue_resource.0;
|
||||||
|
|
||||||
let destination = wgpu_core::command::ImageCopyTexture {
|
let destination = wgpu_core::command::ImageCopyTexture {
|
||||||
texture: texture_resource.0,
|
texture: texture_resource.0,
|
||||||
mip_level: args.destination.mip_level,
|
mip_level: destination.mip_level,
|
||||||
origin: args.destination.origin,
|
origin: destination.origin,
|
||||||
aspect: args.destination.aspect,
|
aspect: destination.aspect,
|
||||||
};
|
};
|
||||||
let data_layout = args.data_layout.into();
|
let data_layout = data_layout.into();
|
||||||
|
|
||||||
gfx_ok!(queue => instance.queue_write_texture(
|
gfx_ok!(queue => instance.queue_write_texture(
|
||||||
queue,
|
queue,
|
||||||
&destination,
|
&destination,
|
||||||
&*zero_copy,
|
&*buf,
|
||||||
&data_layout,
|
&data_layout,
|
||||||
&args.size
|
&size
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,9 +3,10 @@
|
||||||
use deno_core::error::type_error;
|
use deno_core::error::type_error;
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::ZeroCopyBuf;
|
use deno_core::ZeroCopyBuf;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
|
@ -55,127 +56,97 @@ pub fn op_webgpu_render_pass_set_viewport(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_pass_set_scissor_rect(
|
||||||
pub struct RenderPassSetScissorRectArgs {
|
state: &mut OpState,
|
||||||
render_pass_rid: ResourceId,
|
render_pass_rid: ResourceId,
|
||||||
x: u32,
|
x: u32,
|
||||||
y: u32,
|
y: u32,
|
||||||
width: u32,
|
width: u32,
|
||||||
height: u32,
|
height: u32,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_pass_set_scissor_rect(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderPassSetScissorRectArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_set_scissor_rect(
|
wgpu_core::command::render_ffi::wgpu_render_pass_set_scissor_rect(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
args.x,
|
x,
|
||||||
args.y,
|
y,
|
||||||
args.width,
|
width,
|
||||||
args.height,
|
height,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassSetBlendConstantArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
color: wgpu_types::Color,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_set_blend_constant(
|
pub fn op_webgpu_render_pass_set_blend_constant(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassSetBlendConstantArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
color: wgpu_types::Color,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_set_blend_constant(
|
wgpu_core::command::render_ffi::wgpu_render_pass_set_blend_constant(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
&args.color,
|
&color,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassSetStencilReferenceArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
reference: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_set_stencil_reference(
|
pub fn op_webgpu_render_pass_set_stencil_reference(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassSetStencilReferenceArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
reference: u32,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_set_stencil_reference(
|
wgpu_core::command::render_ffi::wgpu_render_pass_set_stencil_reference(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
args.reference,
|
reference,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassBeginPipelineStatisticsQueryArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
query_set: u32,
|
|
||||||
query_index: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_begin_pipeline_statistics_query(
|
pub fn op_webgpu_render_pass_begin_pipeline_statistics_query(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassBeginPipelineStatisticsQueryArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
query_set: u32,
|
||||||
|
query_index: u32,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
let query_set_resource = state
|
let query_set_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuQuerySet>(args.query_set)?;
|
.get::<super::WebGpuQuerySet>(query_set)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_begin_pipeline_statistics_query(
|
wgpu_core::command::render_ffi::wgpu_render_pass_begin_pipeline_statistics_query(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
query_set_resource.0,
|
query_set_resource.0,
|
||||||
args.query_index,
|
query_index,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassEndPipelineStatisticsQueryArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_end_pipeline_statistics_query(
|
pub fn op_webgpu_render_pass_end_pipeline_statistics_query(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassEndPipelineStatisticsQueryArgs,
|
render_pass_rid: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_end_pipeline_statistics_query(
|
wgpu_core::command::render_ffi::wgpu_render_pass_end_pipeline_statistics_query(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
|
@ -184,136 +155,113 @@ pub fn op_webgpu_render_pass_end_pipeline_statistics_query(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassWriteTimestampArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
query_set: u32,
|
|
||||||
query_index: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_write_timestamp(
|
pub fn op_webgpu_render_pass_write_timestamp(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassWriteTimestampArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
query_set: u32,
|
||||||
|
query_index: u32,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
let query_set_resource = state
|
let query_set_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuQuerySet>(args.query_set)?;
|
.get::<super::WebGpuQuerySet>(query_set)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_write_timestamp(
|
wgpu_core::command::render_ffi::wgpu_render_pass_write_timestamp(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
query_set_resource.0,
|
query_set_resource.0,
|
||||||
args.query_index,
|
query_index,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassExecuteBundlesArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
bundles: Vec<u32>,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_execute_bundles(
|
pub fn op_webgpu_render_pass_execute_bundles(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassExecuteBundlesArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
bundles: Vec<u32>,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let mut render_bundle_ids = vec![];
|
let bundles = bundles
|
||||||
|
.iter()
|
||||||
for rid in &args.bundles {
|
.map(|rid| {
|
||||||
let render_bundle_resource =
|
let render_bundle_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::bundle::WebGpuRenderBundle>(*rid)?;
|
.get::<super::bundle::WebGpuRenderBundle>(*rid)?;
|
||||||
render_bundle_ids.push(render_bundle_resource.0);
|
Ok(render_bundle_resource.0)
|
||||||
}
|
})
|
||||||
|
.collect::<Result<Vec<_>, AnyError>>()?;
|
||||||
|
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
// SAFETY: the raw pointer and length are of the same slice, and that slice
|
// SAFETY: the raw pointer and length are of the same slice, and that slice
|
||||||
// lives longer than the below function invocation.
|
// lives longer than the below function invocation.
|
||||||
unsafe {
|
unsafe {
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_execute_bundles(
|
wgpu_core::command::render_ffi::wgpu_render_pass_execute_bundles(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
render_bundle_ids.as_ptr(),
|
bundles.as_ptr(),
|
||||||
render_bundle_ids.len(),
|
bundles.len(),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_pass_end(
|
||||||
pub struct RenderPassEndPassArgs {
|
state: &mut OpState,
|
||||||
command_encoder_rid: ResourceId,
|
command_encoder_rid: ResourceId,
|
||||||
render_pass_rid: ResourceId,
|
render_pass_rid: ResourceId,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_pass_end_pass(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderPassEndPassArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let command_encoder_resource = state
|
let command_encoder_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::command_encoder::WebGpuCommandEncoder>(
|
.get::<super::command_encoder::WebGpuCommandEncoder>(
|
||||||
args.command_encoder_rid,
|
command_encoder_rid,
|
||||||
)?;
|
)?;
|
||||||
let command_encoder = command_encoder_resource.0;
|
let command_encoder = command_encoder_resource.0;
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.take::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.take::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
let render_pass = &render_pass_resource.0.borrow();
|
let render_pass = &render_pass_resource.0.borrow();
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
|
|
||||||
gfx_ok!(command_encoder => instance.command_encoder_run_render_pass(command_encoder, render_pass))
|
gfx_ok!(command_encoder => instance.command_encoder_run_render_pass(command_encoder, render_pass))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_pass_set_bind_group(
|
||||||
pub struct RenderPassSetBindGroupArgs {
|
state: &mut OpState,
|
||||||
render_pass_rid: ResourceId,
|
render_pass_rid: ResourceId,
|
||||||
index: u32,
|
index: u32,
|
||||||
bind_group: u32,
|
bind_group: u32,
|
||||||
dynamic_offsets_data: ZeroCopyBuf,
|
dynamic_offsets_data: ZeroCopyBuf,
|
||||||
dynamic_offsets_data_start: usize,
|
dynamic_offsets_data_start: usize,
|
||||||
dynamic_offsets_data_length: usize,
|
dynamic_offsets_data_length: usize,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_pass_set_bind_group(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderPassSetBindGroupArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let bind_group_resource =
|
let bind_group_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::binding::WebGpuBindGroup>(args.bind_group)?;
|
.get::<super::binding::WebGpuBindGroup>(bind_group)?;
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
// Align the data
|
// Align the data
|
||||||
assert!(args.dynamic_offsets_data_start % std::mem::size_of::<u32>() == 0);
|
assert_eq!(dynamic_offsets_data_start % std::mem::size_of::<u32>(), 0);
|
||||||
let (prefix, dynamic_offsets_data, suffix) =
|
let (prefix, dynamic_offsets_data, suffix) =
|
||||||
// SAFETY: A u8 to u32 cast is safe because we asserted that the length is a
|
// SAFETY: A u8 to u32 cast is safe because we asserted that the length is a
|
||||||
// multiple of 4.
|
// multiple of 4.
|
||||||
unsafe { args.dynamic_offsets_data.align_to::<u32>() };
|
unsafe { dynamic_offsets_data.align_to::<u32>() };
|
||||||
assert!(prefix.is_empty());
|
assert!(prefix.is_empty());
|
||||||
assert!(suffix.is_empty());
|
assert!(suffix.is_empty());
|
||||||
|
|
||||||
let start = args.dynamic_offsets_data_start;
|
let start = dynamic_offsets_data_start;
|
||||||
let len = args.dynamic_offsets_data_length;
|
let len = dynamic_offsets_data_length;
|
||||||
|
|
||||||
// Assert that length and start are both in bounds
|
// Assert that length and start are both in bounds
|
||||||
assert!(start <= dynamic_offsets_data.len());
|
assert!(start <= dynamic_offsets_data.len());
|
||||||
|
@ -326,7 +274,7 @@ pub fn op_webgpu_render_pass_set_bind_group(
|
||||||
unsafe {
|
unsafe {
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_set_bind_group(
|
wgpu_core::command::render_ffi::wgpu_render_pass_set_bind_group(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
args.index,
|
index,
|
||||||
bind_group_resource.0,
|
bind_group_resource.0,
|
||||||
dynamic_offsets_data.as_ptr(),
|
dynamic_offsets_data.as_ptr(),
|
||||||
dynamic_offsets_data.len(),
|
dynamic_offsets_data.len(),
|
||||||
|
@ -336,23 +284,17 @@ pub fn op_webgpu_render_pass_set_bind_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassPushDebugGroupArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
group_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_push_debug_group(
|
pub fn op_webgpu_render_pass_push_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassPushDebugGroupArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
group_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
let label = std::ffi::CString::new(args.group_label).unwrap();
|
let label = std::ffi::CString::new(group_label).unwrap();
|
||||||
// SAFETY: the string the raw pointer points to lives longer than the below
|
// SAFETY: the string the raw pointer points to lives longer than the below
|
||||||
// function invocation.
|
// function invocation.
|
||||||
unsafe {
|
unsafe {
|
||||||
|
@ -366,20 +308,14 @@ pub fn op_webgpu_render_pass_push_debug_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassPopDebugGroupArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_pop_debug_group(
|
pub fn op_webgpu_render_pass_pop_debug_group(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassPopDebugGroupArgs,
|
render_pass_rid: ResourceId,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_pop_debug_group(
|
wgpu_core::command::render_ffi::wgpu_render_pass_pop_debug_group(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
|
@ -388,23 +324,17 @@ pub fn op_webgpu_render_pass_pop_debug_group(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassInsertDebugMarkerArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
marker_label: String,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_insert_debug_marker(
|
pub fn op_webgpu_render_pass_insert_debug_marker(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassInsertDebugMarkerArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
marker_label: String,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
let label = std::ffi::CString::new(args.marker_label).unwrap();
|
let label = std::ffi::CString::new(marker_label).unwrap();
|
||||||
// SAFETY: the string the raw pointer points to lives longer than the below
|
// SAFETY: the string the raw pointer points to lives longer than the below
|
||||||
// function invocation.
|
// function invocation.
|
||||||
unsafe {
|
unsafe {
|
||||||
|
@ -418,25 +348,19 @@ pub fn op_webgpu_render_pass_insert_debug_marker(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassSetPipelineArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
pipeline: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_set_pipeline(
|
pub fn op_webgpu_render_pass_set_pipeline(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassSetPipelineArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
pipeline: u32,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pipeline_resource =
|
let render_pipeline_resource =
|
||||||
state
|
state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::pipeline::WebGpuRenderPipeline>(args.pipeline)?;
|
.get::<super::pipeline::WebGpuRenderPipeline>(pipeline)?;
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_set_pipeline(
|
wgpu_core::command::render_ffi::wgpu_render_pass_set_pipeline(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
|
@ -446,29 +370,23 @@ pub fn op_webgpu_render_pass_set_pipeline(
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_pass_set_index_buffer(
|
||||||
pub struct RenderPassSetIndexBufferArgs {
|
state: &mut OpState,
|
||||||
render_pass_rid: ResourceId,
|
render_pass_rid: ResourceId,
|
||||||
buffer: u32,
|
buffer: u32,
|
||||||
index_format: wgpu_types::IndexFormat,
|
index_format: wgpu_types::IndexFormat,
|
||||||
offset: u64,
|
offset: u64,
|
||||||
size: Option<u64>,
|
size: Option<u64>,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_pass_set_index_buffer(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderPassSetIndexBufferArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(buffer)?;
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
let size = if let Some(size) = args.size {
|
let size = if let Some(size) = size {
|
||||||
Some(
|
Some(
|
||||||
std::num::NonZeroU64::new(size)
|
std::num::NonZeroU64::new(size)
|
||||||
.ok_or_else(|| type_error("size must be larger than 0"))?,
|
.ok_or_else(|| type_error("size must be larger than 0"))?,
|
||||||
|
@ -479,37 +397,31 @@ pub fn op_webgpu_render_pass_set_index_buffer(
|
||||||
|
|
||||||
render_pass_resource.0.borrow_mut().set_index_buffer(
|
render_pass_resource.0.borrow_mut().set_index_buffer(
|
||||||
buffer_resource.0,
|
buffer_resource.0,
|
||||||
args.index_format,
|
index_format,
|
||||||
args.offset,
|
offset,
|
||||||
size,
|
size,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_pass_set_vertex_buffer(
|
||||||
pub struct RenderPassSetVertexBufferArgs {
|
state: &mut OpState,
|
||||||
render_pass_rid: ResourceId,
|
render_pass_rid: ResourceId,
|
||||||
slot: u32,
|
slot: u32,
|
||||||
buffer: u32,
|
buffer: u32,
|
||||||
offset: u64,
|
offset: u64,
|
||||||
size: Option<u64>,
|
size: Option<u64>,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_pass_set_vertex_buffer(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderPassSetVertexBufferArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(buffer)?;
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
let size = if let Some(size) = args.size {
|
let size = if let Some(size) = size {
|
||||||
Some(
|
Some(
|
||||||
std::num::NonZeroU64::new(size)
|
std::num::NonZeroU64::new(size)
|
||||||
.ok_or_else(|| type_error("size must be larger than 0"))?,
|
.ok_or_else(|| type_error("size must be larger than 0"))?,
|
||||||
|
@ -520,130 +432,106 @@ pub fn op_webgpu_render_pass_set_vertex_buffer(
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_set_vertex_buffer(
|
wgpu_core::command::render_ffi::wgpu_render_pass_set_vertex_buffer(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
args.slot,
|
slot,
|
||||||
buffer_resource.0,
|
buffer_resource.0,
|
||||||
args.offset,
|
offset,
|
||||||
size,
|
size,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_pass_draw(
|
||||||
pub struct RenderPassDrawArgs {
|
state: &mut OpState,
|
||||||
render_pass_rid: ResourceId,
|
render_pass_rid: ResourceId,
|
||||||
vertex_count: u32,
|
vertex_count: u32,
|
||||||
instance_count: u32,
|
instance_count: u32,
|
||||||
first_vertex: u32,
|
first_vertex: u32,
|
||||||
first_instance: u32,
|
first_instance: u32,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_pass_draw(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderPassDrawArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_draw(
|
wgpu_core::command::render_ffi::wgpu_render_pass_draw(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
args.vertex_count,
|
vertex_count,
|
||||||
args.instance_count,
|
instance_count,
|
||||||
args.first_vertex,
|
first_vertex,
|
||||||
args.first_instance,
|
first_instance,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_render_pass_draw_indexed(
|
||||||
pub struct RenderPassDrawIndexedArgs {
|
state: &mut OpState,
|
||||||
render_pass_rid: ResourceId,
|
render_pass_rid: ResourceId,
|
||||||
index_count: u32,
|
index_count: u32,
|
||||||
instance_count: u32,
|
instance_count: u32,
|
||||||
first_index: u32,
|
first_index: u32,
|
||||||
base_vertex: i32,
|
base_vertex: i32,
|
||||||
first_instance: u32,
|
first_instance: u32,
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_render_pass_draw_indexed(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: RenderPassDrawIndexedArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_draw_indexed(
|
wgpu_core::command::render_ffi::wgpu_render_pass_draw_indexed(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
args.index_count,
|
index_count,
|
||||||
args.instance_count,
|
instance_count,
|
||||||
args.first_index,
|
first_index,
|
||||||
args.base_vertex,
|
base_vertex,
|
||||||
args.first_instance,
|
first_instance,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassDrawIndirectArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
indirect_buffer: u32,
|
|
||||||
indirect_offset: u64,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_draw_indirect(
|
pub fn op_webgpu_render_pass_draw_indirect(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassDrawIndirectArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
indirect_buffer: u32,
|
||||||
|
indirect_offset: u64,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.indirect_buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(indirect_buffer)?;
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_draw_indirect(
|
wgpu_core::command::render_ffi::wgpu_render_pass_draw_indirect(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
buffer_resource.0,
|
buffer_resource.0,
|
||||||
args.indirect_offset,
|
indirect_offset,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
|
||||||
#[serde(rename_all = "camelCase")]
|
|
||||||
pub struct RenderPassDrawIndexedIndirectArgs {
|
|
||||||
render_pass_rid: ResourceId,
|
|
||||||
indirect_buffer: u32,
|
|
||||||
indirect_offset: u64,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
#[op]
|
||||||
pub fn op_webgpu_render_pass_draw_indexed_indirect(
|
pub fn op_webgpu_render_pass_draw_indexed_indirect(
|
||||||
state: &mut OpState,
|
state: &mut OpState,
|
||||||
args: RenderPassDrawIndexedIndirectArgs,
|
render_pass_rid: ResourceId,
|
||||||
|
indirect_buffer: u32,
|
||||||
|
indirect_offset: u64,
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let buffer_resource = state
|
let buffer_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::buffer::WebGpuBuffer>(args.indirect_buffer)?;
|
.get::<super::buffer::WebGpuBuffer>(indirect_buffer)?;
|
||||||
let render_pass_resource = state
|
let render_pass_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<WebGpuRenderPass>(args.render_pass_rid)?;
|
.get::<WebGpuRenderPass>(render_pass_rid)?;
|
||||||
|
|
||||||
wgpu_core::command::render_ffi::wgpu_render_pass_draw_indexed_indirect(
|
wgpu_core::command::render_ffi::wgpu_render_pass_draw_indexed_indirect(
|
||||||
&mut render_pass_resource.0.borrow_mut(),
|
&mut render_pass_resource.0.borrow_mut(),
|
||||||
buffer_resource.0,
|
buffer_resource.0,
|
||||||
args.indirect_offset,
|
indirect_offset,
|
||||||
);
|
);
|
||||||
|
|
||||||
Ok(WebGpuResult::empty())
|
Ok(WebGpuResult::empty())
|
||||||
|
|
|
@ -2,8 +2,9 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
|
|
||||||
|
@ -26,7 +27,7 @@ pub struct CreateSamplerArgs {
|
||||||
address_mode_w: wgpu_types::AddressMode,
|
address_mode_w: wgpu_types::AddressMode,
|
||||||
mag_filter: wgpu_types::FilterMode,
|
mag_filter: wgpu_types::FilterMode,
|
||||||
min_filter: wgpu_types::FilterMode,
|
min_filter: wgpu_types::FilterMode,
|
||||||
mipmap_filter: wgpu_types::FilterMode,
|
mipmap_filter: wgpu_types::FilterMode, // TODO: GPUMipmapFilterMode
|
||||||
lod_min_clamp: f32,
|
lod_min_clamp: f32,
|
||||||
lod_max_clamp: f32,
|
lod_max_clamp: f32,
|
||||||
compare: Option<wgpu_types::CompareFunction>,
|
compare: Option<wgpu_types::CompareFunction>,
|
||||||
|
|
|
@ -2,9 +2,9 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
|
|
||||||
use super::error::WebGpuResult;
|
use super::error::WebGpuResult;
|
||||||
|
@ -16,31 +16,24 @@ impl Resource for WebGpuShaderModule {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize)]
|
#[op]
|
||||||
#[serde(rename_all = "camelCase")]
|
pub fn op_webgpu_create_shader_module(
|
||||||
pub struct CreateShaderModuleArgs {
|
state: &mut OpState,
|
||||||
device_rid: ResourceId,
|
device_rid: ResourceId,
|
||||||
label: Option<String>,
|
label: Option<String>,
|
||||||
code: String,
|
code: String,
|
||||||
_source_map: Option<()>, // not yet implemented
|
_source_map: Option<()>, // not yet implemented
|
||||||
}
|
|
||||||
|
|
||||||
#[op]
|
|
||||||
pub fn op_webgpu_create_shader_module(
|
|
||||||
state: &mut OpState,
|
|
||||||
args: CreateShaderModuleArgs,
|
|
||||||
) -> Result<WebGpuResult, AnyError> {
|
) -> Result<WebGpuResult, AnyError> {
|
||||||
let instance = state.borrow::<super::Instance>();
|
let instance = state.borrow::<super::Instance>();
|
||||||
let device_resource = state
|
let device_resource = state
|
||||||
.resource_table
|
.resource_table
|
||||||
.get::<super::WebGpuDevice>(args.device_rid)?;
|
.get::<super::WebGpuDevice>(device_rid)?;
|
||||||
let device = device_resource.0;
|
let device = device_resource.0;
|
||||||
|
|
||||||
let source =
|
let source = wgpu_core::pipeline::ShaderModuleSource::Wgsl(Cow::from(code));
|
||||||
wgpu_core::pipeline::ShaderModuleSource::Wgsl(Cow::from(args.code));
|
|
||||||
|
|
||||||
let descriptor = wgpu_core::pipeline::ShaderModuleDescriptor {
|
let descriptor = wgpu_core::pipeline::ShaderModuleDescriptor {
|
||||||
label: args.label.map(Cow::from),
|
label: label.map(Cow::from),
|
||||||
shader_bound_checks: wgpu_types::ShaderBoundChecks::default(),
|
shader_bound_checks: wgpu_types::ShaderBoundChecks::default(),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -2,8 +2,9 @@
|
||||||
|
|
||||||
use deno_core::error::AnyError;
|
use deno_core::error::AnyError;
|
||||||
use deno_core::op;
|
use deno_core::op;
|
||||||
|
use deno_core::OpState;
|
||||||
|
use deno_core::Resource;
|
||||||
use deno_core::ResourceId;
|
use deno_core::ResourceId;
|
||||||
use deno_core::{OpState, Resource};
|
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use std::borrow::Cow;
|
use std::borrow::Cow;
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
interface mixin GPUObjectBase {
|
interface mixin GPUObjectBase {
|
||||||
attribute USVString? label;
|
attribute USVString label;
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPUObjectDescriptorBase {
|
dictionary GPUObjectDescriptorBase {
|
||||||
|
@ -41,6 +41,14 @@ interface GPUSupportedFeatures {
|
||||||
readonly setlike<DOMString>;
|
readonly setlike<DOMString>;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
|
interface GPUAdapterInfo {
|
||||||
|
readonly attribute DOMString vendor;
|
||||||
|
readonly attribute DOMString architecture;
|
||||||
|
readonly attribute DOMString device;
|
||||||
|
readonly attribute DOMString description;
|
||||||
|
};
|
||||||
|
|
||||||
enum GPUPredefinedColorSpace {
|
enum GPUPredefinedColorSpace {
|
||||||
"srgb",
|
"srgb",
|
||||||
};
|
};
|
||||||
|
@ -68,12 +76,12 @@ enum GPUPowerPreference {
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
interface GPUAdapter {
|
interface GPUAdapter {
|
||||||
readonly attribute DOMString name;
|
|
||||||
[SameObject] readonly attribute GPUSupportedFeatures features;
|
[SameObject] readonly attribute GPUSupportedFeatures features;
|
||||||
[SameObject] readonly attribute GPUSupportedLimits limits;
|
[SameObject] readonly attribute GPUSupportedLimits limits;
|
||||||
readonly attribute boolean isFallbackAdapter;
|
readonly attribute boolean isFallbackAdapter;
|
||||||
|
|
||||||
Promise<GPUDevice> requestDevice(optional GPUDeviceDescriptor descriptor = {});
|
Promise<GPUDevice> requestDevice(optional GPUDeviceDescriptor descriptor = {});
|
||||||
|
Promise<GPUAdapterInfo> requestAdapterInfo(optional sequence<DOMString> unmaskHints = []);
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPUDeviceDescriptor : GPUObjectDescriptorBase {
|
dictionary GPUDeviceDescriptor : GPUObjectDescriptorBase {
|
||||||
|
@ -85,12 +93,12 @@ enum GPUFeatureName {
|
||||||
"depth-clip-control",
|
"depth-clip-control",
|
||||||
"depth24unorm-stencil8",
|
"depth24unorm-stencil8",
|
||||||
"depth32float-stencil8",
|
"depth32float-stencil8",
|
||||||
"pipeline-statistics-query",
|
|
||||||
"texture-compression-bc",
|
"texture-compression-bc",
|
||||||
"texture-compression-etc2",
|
"texture-compression-etc2",
|
||||||
"texture-compression-astc",
|
"texture-compression-astc",
|
||||||
"timestamp-query",
|
"timestamp-query",
|
||||||
"indirect-first-instance",
|
"indirect-first-instance",
|
||||||
|
"shader-f16",
|
||||||
};
|
};
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
|
@ -141,7 +149,7 @@ dictionary GPUBufferDescriptor : GPUObjectDescriptorBase {
|
||||||
|
|
||||||
typedef [EnforceRange] unsigned long GPUBufferUsageFlags;
|
typedef [EnforceRange] unsigned long GPUBufferUsageFlags;
|
||||||
[Exposed=(Window, DedicatedWorker)]
|
[Exposed=(Window, DedicatedWorker)]
|
||||||
interface GPUBufferUsage {
|
namespace GPUBufferUsage {
|
||||||
const GPUFlagsConstant MAP_READ = 0x0001;
|
const GPUFlagsConstant MAP_READ = 0x0001;
|
||||||
const GPUFlagsConstant MAP_WRITE = 0x0002;
|
const GPUFlagsConstant MAP_WRITE = 0x0002;
|
||||||
const GPUFlagsConstant COPY_SRC = 0x0004;
|
const GPUFlagsConstant COPY_SRC = 0x0004;
|
||||||
|
@ -156,7 +164,7 @@ interface GPUBufferUsage {
|
||||||
|
|
||||||
typedef [EnforceRange] unsigned long GPUMapModeFlags;
|
typedef [EnforceRange] unsigned long GPUMapModeFlags;
|
||||||
[Exposed=(Window, DedicatedWorker)]
|
[Exposed=(Window, DedicatedWorker)]
|
||||||
interface GPUMapMode {
|
namespace GPUMapMode {
|
||||||
const GPUFlagsConstant READ = 0x0001;
|
const GPUFlagsConstant READ = 0x0001;
|
||||||
const GPUFlagsConstant WRITE = 0x0002;
|
const GPUFlagsConstant WRITE = 0x0002;
|
||||||
};
|
};
|
||||||
|
@ -186,7 +194,7 @@ enum GPUTextureDimension {
|
||||||
|
|
||||||
typedef [EnforceRange] unsigned long GPUTextureUsageFlags;
|
typedef [EnforceRange] unsigned long GPUTextureUsageFlags;
|
||||||
[Exposed=(Window, DedicatedWorker)]
|
[Exposed=(Window, DedicatedWorker)]
|
||||||
interface GPUTextureUsage {
|
namespace GPUTextureUsage {
|
||||||
const GPUFlagsConstant COPY_SRC = 0x01;
|
const GPUFlagsConstant COPY_SRC = 0x01;
|
||||||
const GPUFlagsConstant COPY_DST = 0x02;
|
const GPUFlagsConstant COPY_DST = 0x02;
|
||||||
const GPUFlagsConstant TEXTURE_BINDING = 0x04;
|
const GPUFlagsConstant TEXTURE_BINDING = 0x04;
|
||||||
|
@ -272,13 +280,19 @@ enum GPUTextureFormat {
|
||||||
"rgba32sint",
|
"rgba32sint",
|
||||||
"rgba32float",
|
"rgba32float",
|
||||||
|
|
||||||
// Depth and stencil formats
|
// Depth/stencil formats
|
||||||
"stencil8",
|
"stencil8",
|
||||||
"depth16unorm",
|
"depth16unorm",
|
||||||
"depth24plus",
|
"depth24plus",
|
||||||
"depth24plus-stencil8",
|
"depth24plus-stencil8",
|
||||||
"depth32float",
|
"depth32float",
|
||||||
|
|
||||||
|
// "depth24unorm-stencil8" feature
|
||||||
|
"depth24unorm-stencil8",
|
||||||
|
|
||||||
|
// "depth32float-stencil8" feature
|
||||||
|
"depth32float-stencil8",
|
||||||
|
|
||||||
// BC compressed formats usable if "texture-compression-bc" is both
|
// BC compressed formats usable if "texture-compression-bc" is both
|
||||||
// supported by the device/user agent and enabled in requestDevice.
|
// supported by the device/user agent and enabled in requestDevice.
|
||||||
"bc1-rgba-unorm",
|
"bc1-rgba-unorm",
|
||||||
|
@ -339,12 +353,6 @@ enum GPUTextureFormat {
|
||||||
"astc-12x10-unorm-srgb",
|
"astc-12x10-unorm-srgb",
|
||||||
"astc-12x12-unorm",
|
"astc-12x12-unorm",
|
||||||
"astc-12x12-unorm-srgb",
|
"astc-12x12-unorm-srgb",
|
||||||
|
|
||||||
// "depth24unorm-stencil8" feature
|
|
||||||
"depth24unorm-stencil8",
|
|
||||||
|
|
||||||
// "depth32float-stencil8" feature
|
|
||||||
"depth32float-stencil8",
|
|
||||||
};
|
};
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
|
@ -358,7 +366,7 @@ dictionary GPUSamplerDescriptor : GPUObjectDescriptorBase {
|
||||||
GPUAddressMode addressModeW = "clamp-to-edge";
|
GPUAddressMode addressModeW = "clamp-to-edge";
|
||||||
GPUFilterMode magFilter = "nearest";
|
GPUFilterMode magFilter = "nearest";
|
||||||
GPUFilterMode minFilter = "nearest";
|
GPUFilterMode minFilter = "nearest";
|
||||||
GPUFilterMode mipmapFilter = "nearest";
|
GPUMipmapFilterMode mipmapFilter = "nearest";
|
||||||
float lodMinClamp = 0;
|
float lodMinClamp = 0;
|
||||||
float lodMaxClamp = 32;
|
float lodMaxClamp = 32;
|
||||||
GPUCompareFunction compare;
|
GPUCompareFunction compare;
|
||||||
|
@ -376,6 +384,11 @@ enum GPUFilterMode {
|
||||||
"linear",
|
"linear",
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum GPUMipmapFilterMode {
|
||||||
|
"nearest",
|
||||||
|
"linear",
|
||||||
|
};
|
||||||
|
|
||||||
enum GPUCompareFunction {
|
enum GPUCompareFunction {
|
||||||
"never",
|
"never",
|
||||||
"less",
|
"less",
|
||||||
|
@ -396,14 +409,6 @@ dictionary GPUBindGroupLayoutDescriptor : GPUObjectDescriptorBase {
|
||||||
required sequence<GPUBindGroupLayoutEntry> entries;
|
required sequence<GPUBindGroupLayoutEntry> entries;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef [EnforceRange] unsigned long GPUShaderStageFlags;
|
|
||||||
[Exposed=(Window, DedicatedWorker)]
|
|
||||||
interface GPUShaderStage {
|
|
||||||
const GPUFlagsConstant VERTEX = 0x1;
|
|
||||||
const GPUFlagsConstant FRAGMENT = 0x2;
|
|
||||||
const GPUFlagsConstant COMPUTE = 0x4;
|
|
||||||
};
|
|
||||||
|
|
||||||
dictionary GPUBindGroupLayoutEntry {
|
dictionary GPUBindGroupLayoutEntry {
|
||||||
required GPUIndex32 binding;
|
required GPUIndex32 binding;
|
||||||
required GPUShaderStageFlags visibility;
|
required GPUShaderStageFlags visibility;
|
||||||
|
@ -414,6 +419,14 @@ dictionary GPUBindGroupLayoutEntry {
|
||||||
GPUStorageTextureBindingLayout storageTexture;
|
GPUStorageTextureBindingLayout storageTexture;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef [EnforceRange] unsigned long GPUShaderStageFlags;
|
||||||
|
[Exposed=(Window, DedicatedWorker)]
|
||||||
|
namespace GPUShaderStage {
|
||||||
|
const GPUFlagsConstant VERTEX = 0x1;
|
||||||
|
const GPUFlagsConstant FRAGMENT = 0x2;
|
||||||
|
const GPUFlagsConstant COMPUTE = 0x4;
|
||||||
|
};
|
||||||
|
|
||||||
enum GPUBufferBindingType {
|
enum GPUBufferBindingType {
|
||||||
"uniform",
|
"uniform",
|
||||||
"storage",
|
"storage",
|
||||||
|
@ -524,12 +537,16 @@ interface GPUCompilationInfo {
|
||||||
readonly attribute FrozenArray<GPUCompilationMessage> messages;
|
readonly attribute FrozenArray<GPUCompilationMessage> messages;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum GPUAutoLayoutMode {
|
||||||
|
"auto"
|
||||||
|
};
|
||||||
|
|
||||||
dictionary GPUPipelineDescriptorBase : GPUObjectDescriptorBase {
|
dictionary GPUPipelineDescriptorBase : GPUObjectDescriptorBase {
|
||||||
GPUPipelineLayout layout;
|
required (GPUPipelineLayout or GPUAutoLayoutMode) layout;
|
||||||
};
|
};
|
||||||
|
|
||||||
interface mixin GPUPipelineBase {
|
interface mixin GPUPipelineBase {
|
||||||
GPUBindGroupLayout getBindGroupLayout(unsigned long index);
|
[NewObject] GPUBindGroupLayout getBindGroupLayout(unsigned long index);
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPUProgrammableStage {
|
dictionary GPUProgrammableStage {
|
||||||
|
@ -564,14 +581,6 @@ dictionary GPURenderPipelineDescriptor : GPUPipelineDescriptorBase {
|
||||||
GPUFragmentState fragment;
|
GPUFragmentState fragment;
|
||||||
};
|
};
|
||||||
|
|
||||||
enum GPUPrimitiveTopology {
|
|
||||||
"point-list",
|
|
||||||
"line-list",
|
|
||||||
"line-strip",
|
|
||||||
"triangle-list",
|
|
||||||
"triangle-strip",
|
|
||||||
};
|
|
||||||
|
|
||||||
dictionary GPUPrimitiveState {
|
dictionary GPUPrimitiveState {
|
||||||
GPUPrimitiveTopology topology = "triangle-list";
|
GPUPrimitiveTopology topology = "triangle-list";
|
||||||
GPUIndexFormat stripIndexFormat;
|
GPUIndexFormat stripIndexFormat;
|
||||||
|
@ -582,6 +591,14 @@ dictionary GPUPrimitiveState {
|
||||||
boolean unclippedDepth = false;
|
boolean unclippedDepth = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum GPUPrimitiveTopology {
|
||||||
|
"point-list",
|
||||||
|
"line-list",
|
||||||
|
"line-strip",
|
||||||
|
"triangle-list",
|
||||||
|
"triangle-strip",
|
||||||
|
};
|
||||||
|
|
||||||
enum GPUFrontFace {
|
enum GPUFrontFace {
|
||||||
"ccw",
|
"ccw",
|
||||||
"cw",
|
"cw",
|
||||||
|
@ -600,7 +617,7 @@ dictionary GPUMultisampleState {
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPUFragmentState : GPUProgrammableStage {
|
dictionary GPUFragmentState : GPUProgrammableStage {
|
||||||
required sequence<GPUColorTargetState> targets;
|
required sequence<GPUColorTargetState?> targets;
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPUColorTargetState {
|
dictionary GPUColorTargetState {
|
||||||
|
@ -617,7 +634,7 @@ dictionary GPUBlendState {
|
||||||
|
|
||||||
typedef [EnforceRange] unsigned long GPUColorWriteFlags;
|
typedef [EnforceRange] unsigned long GPUColorWriteFlags;
|
||||||
[Exposed=(Window, DedicatedWorker)]
|
[Exposed=(Window, DedicatedWorker)]
|
||||||
interface GPUColorWrite {
|
namespace GPUColorWrite {
|
||||||
const GPUFlagsConstant RED = 0x1;
|
const GPUFlagsConstant RED = 0x1;
|
||||||
const GPUFlagsConstant GREEN = 0x2;
|
const GPUFlagsConstant GREEN = 0x2;
|
||||||
const GPUFlagsConstant BLUE = 0x4;
|
const GPUFlagsConstant BLUE = 0x4;
|
||||||
|
@ -758,6 +775,9 @@ GPUCommandBuffer includes GPUObjectBase;
|
||||||
dictionary GPUCommandBufferDescriptor : GPUObjectDescriptorBase {
|
dictionary GPUCommandBufferDescriptor : GPUObjectDescriptorBase {
|
||||||
};
|
};
|
||||||
|
|
||||||
|
interface mixin GPUCommandsMixin {
|
||||||
|
};
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
interface GPUCommandEncoder {
|
interface GPUCommandEncoder {
|
||||||
GPURenderPassEncoder beginRenderPass(GPURenderPassDescriptor descriptor);
|
GPURenderPassEncoder beginRenderPass(GPURenderPassDescriptor descriptor);
|
||||||
|
@ -786,13 +806,9 @@ interface GPUCommandEncoder {
|
||||||
GPUExtent3D copySize);
|
GPUExtent3D copySize);
|
||||||
|
|
||||||
undefined clearBuffer(
|
undefined clearBuffer(
|
||||||
GPUBuffer destination,
|
GPUBuffer buffer,
|
||||||
GPUSize64 destinationOffset,
|
optional GPUSize64 offset = 0,
|
||||||
GPUSize64 size);
|
optional GPUSize64 size);
|
||||||
|
|
||||||
undefined pushDebugGroup(USVString groupLabel);
|
|
||||||
undefined popDebugGroup();
|
|
||||||
undefined insertDebugMarker(USVString markerLabel);
|
|
||||||
|
|
||||||
undefined writeTimestamp(GPUQuerySet querySet, GPUSize32 queryIndex);
|
undefined writeTimestamp(GPUQuerySet querySet, GPUSize32 queryIndex);
|
||||||
|
|
||||||
|
@ -806,6 +822,8 @@ interface GPUCommandEncoder {
|
||||||
GPUCommandBuffer finish(optional GPUCommandBufferDescriptor descriptor = {});
|
GPUCommandBuffer finish(optional GPUCommandBufferDescriptor descriptor = {});
|
||||||
};
|
};
|
||||||
GPUCommandEncoder includes GPUObjectBase;
|
GPUCommandEncoder includes GPUObjectBase;
|
||||||
|
GPUCommandEncoder includes GPUCommandsMixin;
|
||||||
|
GPUCommandEncoder includes GPUDebugCommandsMixin;
|
||||||
|
|
||||||
dictionary GPUCommandEncoderDescriptor : GPUObjectDescriptorBase {
|
dictionary GPUCommandEncoderDescriptor : GPUObjectDescriptorBase {
|
||||||
};
|
};
|
||||||
|
@ -827,7 +845,7 @@ dictionary GPUImageCopyTexture {
|
||||||
GPUTextureAspect aspect = "all";
|
GPUTextureAspect aspect = "all";
|
||||||
};
|
};
|
||||||
|
|
||||||
interface mixin GPUProgrammablePassEncoder {
|
interface mixin GPUBindingCommandsMixin {
|
||||||
undefined setBindGroup(GPUIndex32 index, GPUBindGroup bindGroup,
|
undefined setBindGroup(GPUIndex32 index, GPUBindGroup bindGroup,
|
||||||
optional sequence<GPUBufferDynamicOffset> dynamicOffsets = []);
|
optional sequence<GPUBufferDynamicOffset> dynamicOffsets = []);
|
||||||
|
|
||||||
|
@ -835,7 +853,9 @@ interface mixin GPUProgrammablePassEncoder {
|
||||||
Uint32Array dynamicOffsetsData,
|
Uint32Array dynamicOffsetsData,
|
||||||
GPUSize64 dynamicOffsetsDataStart,
|
GPUSize64 dynamicOffsetsDataStart,
|
||||||
GPUSize32 dynamicOffsetsDataLength);
|
GPUSize32 dynamicOffsetsDataLength);
|
||||||
|
};
|
||||||
|
|
||||||
|
interface mixin GPUDebugCommandsMixin {
|
||||||
undefined pushDebugGroup(USVString groupLabel);
|
undefined pushDebugGroup(USVString groupLabel);
|
||||||
undefined popDebugGroup();
|
undefined popDebugGroup();
|
||||||
undefined insertDebugMarker(USVString markerLabel);
|
undefined insertDebugMarker(USVString markerLabel);
|
||||||
|
@ -844,39 +864,24 @@ interface mixin GPUProgrammablePassEncoder {
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
interface GPUComputePassEncoder {
|
interface GPUComputePassEncoder {
|
||||||
undefined setPipeline(GPUComputePipeline pipeline);
|
undefined setPipeline(GPUComputePipeline pipeline);
|
||||||
undefined dispatch(GPUSize32 x, optional GPUSize32 y = 1, optional GPUSize32 z = 1);
|
undefined dispatchWorkgroups(GPUSize32 workgroupCountX, optional GPUSize32 workgroupCountY = 1, optional GPUSize32 workgroupCountZ = 1);
|
||||||
undefined dispatchIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset);
|
undefined dispatchWorkgroupsIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset);
|
||||||
|
|
||||||
undefined beginPipelineStatisticsQuery(GPUQuerySet querySet, GPUSize32 queryIndex);
|
undefined beginPipelineStatisticsQuery(GPUQuerySet querySet, GPUSize32 queryIndex);
|
||||||
undefined endPipelineStatisticsQuery();
|
undefined endPipelineStatisticsQuery();
|
||||||
|
|
||||||
undefined writeTimestamp(GPUQuerySet querySet, GPUSize32 queryIndex);
|
undefined writeTimestamp(GPUQuerySet querySet, GPUSize32 queryIndex);
|
||||||
|
|
||||||
undefined endPass();
|
undefined end();
|
||||||
};
|
};
|
||||||
GPUComputePassEncoder includes GPUObjectBase;
|
GPUComputePassEncoder includes GPUObjectBase;
|
||||||
GPUComputePassEncoder includes GPUProgrammablePassEncoder;
|
GPUComputePassEncoder includes GPUCommandsMixin;
|
||||||
|
GPUComputePassEncoder includes GPUDebugCommandsMixin;
|
||||||
|
GPUComputePassEncoder includes GPUBindingCommandsMixin;
|
||||||
|
|
||||||
dictionary GPUComputePassDescriptor : GPUObjectDescriptorBase {
|
dictionary GPUComputePassDescriptor : GPUObjectDescriptorBase {
|
||||||
};
|
};
|
||||||
|
|
||||||
interface mixin GPURenderEncoderBase {
|
|
||||||
undefined setPipeline(GPURenderPipeline pipeline);
|
|
||||||
|
|
||||||
undefined setIndexBuffer(GPUBuffer buffer, GPUIndexFormat indexFormat, optional GPUSize64 offset = 0, optional GPUSize64 size);
|
|
||||||
undefined setVertexBuffer(GPUIndex32 slot, GPUBuffer buffer, optional GPUSize64 offset = 0, optional GPUSize64 size);
|
|
||||||
|
|
||||||
undefined draw(GPUSize32 vertexCount, optional GPUSize32 instanceCount = 1,
|
|
||||||
optional GPUSize32 firstVertex = 0, optional GPUSize32 firstInstance = 0);
|
|
||||||
undefined drawIndexed(GPUSize32 indexCount, optional GPUSize32 instanceCount = 1,
|
|
||||||
optional GPUSize32 firstIndex = 0,
|
|
||||||
optional GPUSignedOffset32 baseVertex = 0,
|
|
||||||
optional GPUSize32 firstInstance = 0);
|
|
||||||
|
|
||||||
undefined drawIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset);
|
|
||||||
undefined drawIndexedIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset);
|
|
||||||
};
|
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
interface GPURenderPassEncoder {
|
interface GPURenderPassEncoder {
|
||||||
undefined setViewport(float x, float y,
|
undefined setViewport(float x, float y,
|
||||||
|
@ -898,14 +903,16 @@ interface GPURenderPassEncoder {
|
||||||
undefined writeTimestamp(GPUQuerySet querySet, GPUSize32 queryIndex);
|
undefined writeTimestamp(GPUQuerySet querySet, GPUSize32 queryIndex);
|
||||||
|
|
||||||
undefined executeBundles(sequence<GPURenderBundle> bundles);
|
undefined executeBundles(sequence<GPURenderBundle> bundles);
|
||||||
undefined endPass();
|
undefined end();
|
||||||
};
|
};
|
||||||
GPURenderPassEncoder includes GPUObjectBase;
|
GPURenderPassEncoder includes GPUObjectBase;
|
||||||
GPURenderPassEncoder includes GPUProgrammablePassEncoder;
|
GPURenderPassEncoder includes GPUCommandsMixin;
|
||||||
GPURenderPassEncoder includes GPURenderEncoderBase;
|
GPURenderPassEncoder includes GPUDebugCommandsMixin;
|
||||||
|
GPURenderPassEncoder includes GPUBindingCommandsMixin;
|
||||||
|
GPURenderPassEncoder includes GPURenderCommandsMixin;
|
||||||
|
|
||||||
dictionary GPURenderPassDescriptor : GPUObjectDescriptorBase {
|
dictionary GPURenderPassDescriptor : GPUObjectDescriptorBase {
|
||||||
required sequence<GPURenderPassColorAttachment> colorAttachments;
|
required sequence<GPURenderPassColorAttachment?> colorAttachments;
|
||||||
GPURenderPassDepthStencilAttachment depthStencilAttachment;
|
GPURenderPassDepthStencilAttachment depthStencilAttachment;
|
||||||
GPUQuerySet occlusionQuerySet;
|
GPUQuerySet occlusionQuerySet;
|
||||||
};
|
};
|
||||||
|
@ -914,24 +921,28 @@ dictionary GPURenderPassColorAttachment {
|
||||||
required GPUTextureView view;
|
required GPUTextureView view;
|
||||||
GPUTextureView resolveTarget;
|
GPUTextureView resolveTarget;
|
||||||
|
|
||||||
required (GPULoadOp or GPUColor) loadValue;
|
GPUColor clearValue;
|
||||||
|
required GPULoadOp loadOp;
|
||||||
required GPUStoreOp storeOp;
|
required GPUStoreOp storeOp;
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPURenderPassDepthStencilAttachment {
|
dictionary GPURenderPassDepthStencilAttachment {
|
||||||
required GPUTextureView view;
|
required GPUTextureView view;
|
||||||
|
|
||||||
required (GPULoadOp or float) depthLoadValue;
|
float depthClearValue = 0;
|
||||||
required GPUStoreOp depthStoreOp;
|
GPULoadOp depthLoadOp;
|
||||||
|
GPUStoreOp depthStoreOp;
|
||||||
boolean depthReadOnly = false;
|
boolean depthReadOnly = false;
|
||||||
|
|
||||||
required (GPULoadOp or GPUStencilValue) stencilLoadValue;
|
GPUStencilValue stencilClearValue = 0;
|
||||||
required GPUStoreOp stencilStoreOp;
|
GPULoadOp stencilLoadOp;
|
||||||
|
GPUStoreOp stencilStoreOp;
|
||||||
boolean stencilReadOnly = false;
|
boolean stencilReadOnly = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
enum GPULoadOp {
|
enum GPULoadOp {
|
||||||
"load",
|
"load",
|
||||||
|
"clear",
|
||||||
};
|
};
|
||||||
|
|
||||||
enum GPUStoreOp {
|
enum GPUStoreOp {
|
||||||
|
@ -940,11 +951,28 @@ enum GPUStoreOp {
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPURenderPassLayout: GPUObjectDescriptorBase {
|
dictionary GPURenderPassLayout: GPUObjectDescriptorBase {
|
||||||
required sequence<GPUTextureFormat> colorFormats;
|
required sequence<GPUTextureFormat?> colorFormats;
|
||||||
GPUTextureFormat depthStencilFormat;
|
GPUTextureFormat depthStencilFormat;
|
||||||
GPUSize32 sampleCount = 1;
|
GPUSize32 sampleCount = 1;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
interface mixin GPURenderCommandsMixin {
|
||||||
|
undefined setPipeline(GPURenderPipeline pipeline);
|
||||||
|
|
||||||
|
undefined setIndexBuffer(GPUBuffer buffer, GPUIndexFormat indexFormat, optional GPUSize64 offset = 0, optional GPUSize64 size);
|
||||||
|
undefined setVertexBuffer(GPUIndex32 slot, GPUBuffer buffer, optional GPUSize64 offset = 0, optional GPUSize64 size);
|
||||||
|
|
||||||
|
undefined draw(GPUSize32 vertexCount, optional GPUSize32 instanceCount = 1,
|
||||||
|
optional GPUSize32 firstVertex = 0, optional GPUSize32 firstInstance = 0);
|
||||||
|
undefined drawIndexed(GPUSize32 indexCount, optional GPUSize32 instanceCount = 1,
|
||||||
|
optional GPUSize32 firstIndex = 0,
|
||||||
|
optional GPUSignedOffset32 baseVertex = 0,
|
||||||
|
optional GPUSize32 firstInstance = 0);
|
||||||
|
|
||||||
|
undefined drawIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset);
|
||||||
|
undefined drawIndexedIndirect(GPUBuffer indirectBuffer, GPUSize64 indirectOffset);
|
||||||
|
};
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
interface GPURenderBundle {
|
interface GPURenderBundle {
|
||||||
};
|
};
|
||||||
|
@ -958,8 +986,10 @@ interface GPURenderBundleEncoder {
|
||||||
GPURenderBundle finish(optional GPURenderBundleDescriptor descriptor = {});
|
GPURenderBundle finish(optional GPURenderBundleDescriptor descriptor = {});
|
||||||
};
|
};
|
||||||
GPURenderBundleEncoder includes GPUObjectBase;
|
GPURenderBundleEncoder includes GPUObjectBase;
|
||||||
GPURenderBundleEncoder includes GPUProgrammablePassEncoder;
|
GPURenderBundleEncoder includes GPUCommandsMixin;
|
||||||
GPURenderBundleEncoder includes GPURenderEncoderBase;
|
GPURenderBundleEncoder includes GPUDebugCommandsMixin;
|
||||||
|
GPURenderBundleEncoder includes GPUBindingCommandsMixin;
|
||||||
|
GPURenderBundleEncoder includes GPURenderCommandsMixin;
|
||||||
|
|
||||||
dictionary GPURenderBundleEncoderDescriptor : GPURenderPassLayout {
|
dictionary GPURenderBundleEncoderDescriptor : GPURenderPassLayout {
|
||||||
boolean depthReadOnly = false;
|
boolean depthReadOnly = false;
|
||||||
|
@ -1033,17 +1063,19 @@ enum GPUErrorFilter {
|
||||||
};
|
};
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
interface GPUOutOfMemoryError {
|
interface GPUError {
|
||||||
constructor();
|
|
||||||
};
|
|
||||||
|
|
||||||
[Exposed=(Window, DedicatedWorker), SecureContext]
|
|
||||||
interface GPUValidationError {
|
|
||||||
constructor(DOMString message);
|
|
||||||
readonly attribute DOMString message;
|
readonly attribute DOMString message;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef (GPUOutOfMemoryError or GPUValidationError) GPUError;
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
|
interface GPUOutOfMemoryError : GPUError {
|
||||||
|
constructor(DOMString message);
|
||||||
|
};
|
||||||
|
|
||||||
|
[Exposed=(Window, DedicatedWorker), SecureContext]
|
||||||
|
interface GPUValidationError : GPUError {
|
||||||
|
constructor(DOMString message);
|
||||||
|
};
|
||||||
|
|
||||||
partial interface GPUDevice {
|
partial interface GPUDevice {
|
||||||
undefined pushErrorScope(GPUErrorFilter filter);
|
undefined pushErrorScope(GPUErrorFilter filter);
|
||||||
|
@ -1056,7 +1088,7 @@ interface GPUUncapturedErrorEvent : Event {
|
||||||
DOMString type,
|
DOMString type,
|
||||||
GPUUncapturedErrorEventInit gpuUncapturedErrorEventInitDict
|
GPUUncapturedErrorEventInit gpuUncapturedErrorEventInitDict
|
||||||
);
|
);
|
||||||
[SameObject] readonly attribute GPUError error;
|
readonly attribute GPUError error;
|
||||||
};
|
};
|
||||||
|
|
||||||
dictionary GPUUncapturedErrorEventInit : EventInit {
|
dictionary GPUUncapturedErrorEventInit : EventInit {
|
||||||
|
@ -1108,4 +1140,3 @@ dictionary GPUExtent3DDict {
|
||||||
GPUIntegerCoordinate depthOrArrayLayers = 1;
|
GPUIntegerCoordinate depthOrArrayLayers = 1;
|
||||||
};
|
};
|
||||||
typedef (sequence<GPUIntegerCoordinate> or GPUExtent3DDict) GPUExtent3D;
|
typedef (sequence<GPUIntegerCoordinate> or GPUExtent3DDict) GPUExtent3D;
|
||||||
|
|
||||||
|
|
|
@ -3,10 +3,9 @@
|
||||||
|
|
||||||
import { join, ROOT_PATH, walk } from "./util.js";
|
import { join, ROOT_PATH, walk } from "./util.js";
|
||||||
|
|
||||||
// const COMMIT = "c00e471274b6c21acda89b4b13d41742c0285d71"; // Release 12
|
const COMMIT = "076df1a56812eee01614b7a3a4c88798012e79ab";
|
||||||
const COMMIT = "c4aa3eaed020a640fec06b48f0a5ea93490d41bb"; // tip of PR (needs merge)
|
const REPO = "gfx-rs/wgpu";
|
||||||
const REPO = "kvark/wgpu";
|
const V_WGPU = "0.13";
|
||||||
const V_WGPU = "0.12";
|
|
||||||
const TARGET_DIR = join(ROOT_PATH, "ext", "webgpu");
|
const TARGET_DIR = join(ROOT_PATH, "ext", "webgpu");
|
||||||
|
|
||||||
async function bash(subcmd, opts = {}) {
|
async function bash(subcmd, opts = {}) {
|
||||||
|
|
Loading…
Add table
Reference in a new issue