WebGPU 的新变化 (Chrome 120)

François Beaufort
François Beaufort

支持 WGSL 中的 16 位浮点值

在 WGSL 中,f16 类型是 IEEE-754 binary16(半精度)格式的一组 16 位浮点值。这意味着它使用 16 位来表示浮点数,而传统的单精度浮点数 (f32) 使用 32 位。这种较小的尺寸可以显著提升性能,尤其是在处理大量数据时。

为了进行比较,在 Apple M1 Pro 设备上,WebLLM 聊天演示中使用的 Llama2 7B 模型f16 实现比 f32 实现快得多,预填充速度提高了 28%,解码速度提高了 41%,如以下屏幕截图所示。

WebLLM 聊天演示的屏幕截图,其中包含 f32 和 f16 Llama2 7B 模型。
使用 f32(左)和 f16(右)Llama2 7B 模型的 WebLLM 对话演示。

并非所有 GPU 都支持 16 位浮点值。当 GPUAdapter 中提供 "shader-f16" 功能时,您现在可以请求具有此功能的 GPUDevice,并创建利用半精度浮点类型 f16 的 WGSL 着色器模块。只有在启用 enable f16;f16 WGSL 扩展程序时,此类型才能在 WGSL 着色器模块中使用。否则,createShaderModule() 将生成验证错误。请参阅以下最简示例和问题 dawn:1510

const adapter = await navigator.gpu.requestAdapter();
if (!adapter.features.has("shader-f16")) {
  throw new Error("16-bit floating-point value support is not available");
}
// Explicitly request 16-bit floating-point value support.
const device = await adapter.requestDevice({
  requiredFeatures: ["shader-f16"],
});

const code = `
  enable f16;

  @compute @workgroup_size(1)
  fn main() {
    const c : vec3h = vec3<f16>(1.0h, 2.0h, 3.0h);
  }
`;

const shaderModule = device.createShaderModule({ code });
// Create a compute pipeline with this shader module
// and run the shader on the GPU...

您可以在 WGSL 着色器模块代码中使用 alias 根据 "shader-f16" 功能支持来同时支持 f16f32 类型,如以下代码段所示。

const adapter = await navigator.gpu.requestAdapter();
const hasShaderF16 = adapter.features.has("shader-f16");

const device = await adapter.requestDevice({
  requiredFeatures: hasShaderF16 ? ["shader-f16"] : [],
});

const header = hasShaderF16
  ? `enable f16;
     alias min16float = f16;`
  : `alias min16float = f32;`;

const code = `
  ${header}

  @compute @workgroup_size(1)
  fn main() {
    const c = vec3<min16float>(1.0, 2.0, 3.0);
  }
`;

突破极限

默认情况下,保存渲染流水线输出数据(包括所有颜色附件)的一个样本(像素或子像素)所需的字节数上限为 32 字节。现在,您可以使用 maxColorAttachmentBytesPerSample 限制来请求最多 64 个。请参阅以下示例并发布 dawn:2036

const adapter = await navigator.gpu.requestAdapter();

if (adapter.limits.maxColorAttachmentBytesPerSample < 64) {
  // When the desired limit isn't supported, take action to either fall back to
  // a code path that does not require the higher limit or notify the user that
  // their device does not meet minimum requirements.
}

// Request highest limit of max color attachments bytes per sample.
const device = await adapter.requestDevice({
  requiredLimits: { maxColorAttachmentBytesPerSample: 64 },
});

所有平台上用于阶段间通信的 maxInterStageShaderVariablesmaxInterStageShaderComponents 限制均已提高。如需了解详情,请参阅问题 dawn:1448

对于每个着色器阶段,管道布局中存储缓冲区的绑定组布局条目数量上限默认为 8。现在,您可以使用 maxStorageBuffersPerShaderStage 限制请求最多 10 个。请参阅问题 dawn:2159

添加了新的 maxBindGroupsPlusVertexBuffers 限制。它由同时使用的绑定组和顶点缓冲区槽的最大数量组成,包括最高索引以下的任何空槽。其默认值为 24。请参阅问题 dawn:1849

对深度模具状态的更改

为了改善开发者体验,深度模具状态 depthWriteEnableddepthCompare 属性不再是必需的:depthWriteEnabled 仅在格式包含深度时是必需的,而 depthCompare 在格式包含深度时,如果完全未使用,则不是必需的。请参阅问题 dawn:2132

适配器信息更新

当用户在 chrome://flags/#enable-webgpu-developer-features 处启用“WebGPU 开发者功能”标志后,调用 requestAdapterInfo() 时,现在可以使用非标准的 typebackend 适配器信息属性。type 可以是“离散 GPU”“集成 GPU”“CPU”或“未知”。backend 为“WebGPU”“D3D11”“D3D12”“metal”“vulkan”“openGL”“openGLES”或“null”。请参阅问题 dawn:2112问题 dawn:2107

https://webgpureport.org 的屏幕截图,其中显示了后端和适配器信息中的类型。
https://webgpureport.org 上显示的适配器信息后端和类型。

移除了 requestAdapterInfo() 中的可选 unmaskHints 列表参数。请参阅问题 dawn:1427

时间戳查询量化

时间戳查询可让应用以纳秒级精度测量 GPU 命令的执行时间。不过,由于存在计时攻击方面的担忧,WebGPU 规范将时间戳查询设为可选。Chrome 团队认为,通过将分辨率降低到 100 微秒,对时间戳查询进行量化处理可在精度和安全性之间取得良好的平衡。请参阅问题 dawn:1800

在 Chrome 中,用户可以通过在 chrome://flags/#enable-webgpu-developer-features 处启用“WebGPU 开发者功能”标志来停用时间戳量化。请注意,此标志本身不会启用 "timestamp-query" 功能。其实现仍处于实验阶段,因此需要在 chrome://flags/#enable-unsafe-webgpu 处启用“不安全的 WebGPU 支持”标志。

在 Dawn 中,添加了一个新的设备切换开关“timestamp_quantization”,该开关默认处于启用状态。以下代码段展示了如何在请求设备时允许使用实验性“时间戳查询”功能,且不进行时间戳量化。

wgpu::DawnTogglesDescriptor deviceTogglesDesc = {};

const char* allowUnsafeApisToggle = "allow_unsafe_apis";
deviceTogglesDesc.enabledToggles = &allowUnsafeApisToggle;
deviceTogglesDesc.enabledToggleCount = 1;

const char* timestampQuantizationToggle = "timestamp_quantization";
deviceTogglesDesc.disabledToggles = &timestampQuantizationToggle;
deviceTogglesDesc.disabledToggleCount = 1;

wgpu::DeviceDescriptor desc = {.nextInChain = &deviceTogglesDesc};

// Request a device with no timestamp quantization.
myAdapter.RequestDevice(&desc, myCallback, myUserData);

春季大扫除功能

实验性功能“timestamp-query-inside-passes”已重命名为“chromium-experimental-timestamp-query-inside-passes”,以便开发者清楚了解此功能目前仅在基于 Chromium 的浏览器中提供,且仍处于实验阶段。请参阅问题 dawn:1193

实验性“pipeline-statistics-query”功能仅部分实现,现已移除,因为该功能不再开发。请参阅问题 chromium:1177506

这仅涵盖了部分重要亮点。查看详尽的提交列表

WebGPU 的新变化

WebGPU 新变化系列中涵盖的所有内容的列表。

Chrome 140

Chrome 139

Chrome 138

Chrome 137

Chrome 136

Chrome 135

Chrome 134

Chrome 133

Chrome 132

Chrome 131

Chrome 130

Chrome 129

Chrome 128

Chrome 127

Chrome 126

Chrome 125

Chrome 124

Chrome 123

Chrome 122

Chrome 121

Chrome 120

Chrome 119

Chrome 118

Chrome 117

Chrome 116

Chrome 115

Chrome 114

Chrome 113