มีอะไรใหม่ใน WebGPU (Chrome 121)

François Beaufort
François Beaufort

รองรับ WebGPU บน Android

ทีม Chrome ยินดีที่จะประกาศว่าตอนนี้ WebGPU เปิดใช้งานโดยค่าเริ่มต้นใน Chrome 121 ในอุปกรณ์ที่ใช้ Android 12 ขึ้นไป ซึ่งขับเคลื่อนโดย Qualcomm และ ARM GPU

เราจะทยอยขยายการรองรับไปยังอุปกรณ์ Android ที่หลากหลายมากขึ้น รวมถึงอุปกรณ์ Android 11 ในอนาคตอันใกล้ การขยายการใช้งานนี้จะขึ้นอยู่กับการทดสอบและการเพิ่มประสิทธิภาพเพิ่มเติม เพื่อประสบการณ์การใช้งานที่ราบรื่นในการกำหนดค่าฮาร์ดแวร์ที่หลากหลาย ดูปัญหา chromium:1497815

วันที่ ภาพหน้าจอของตัวอย่าง WebGPU ที่ทำงานใน Chrome สำหรับ Android
ตัวอย่าง WebGPU ที่ทำงานใน Chrome สำหรับ Android

ใช้ DXC แทน FXC สำหรับการคอมไพล์ตัวปรับแสงเงาใน Windows

ปัจจุบัน Chrome ใช้ความสามารถของ DXC (DirectX Compiler) เพื่อคอมไพล์ตัวปรับแสงเงาบนเครื่อง Windows D3D12 ที่มีฮาร์ดแวร์กราฟิก SM6+ ก่อนหน้านี้ WebGPU ใช้ FXC (FX Compiler) ในการคอมไพล์ตัวปรับแสงเงาใน Windows ในระหว่างที่ทำงานได้ แต่ FXC ยังไม่มีชุดฟีเจอร์และการเพิ่มประสิทธิภาพที่มีใน DXC

การทดสอบเริ่มต้นแสดงให้เห็นว่าความเร็วในการคอมไพล์ตัวปรับแสงเงาประมวลผลเพิ่มขึ้นโดยเฉลี่ย 20% เมื่อใช้ DXC เมื่อเทียบกับ FXC

การค้นหาการประทับเวลาในการประมวลผลและแสดงผลบัตรผ่าน

การค้นหาการประทับเวลาช่วยให้แอปพลิเคชัน WebGPU วัดได้แม่นยำ (จนถึงระดับนาโนวินาที) เวลาที่คำสั่ง GPU ใช้ในการประมวลผลการประมวลผลและแสดงผลบัตรผ่าน โดยระบบจะใช้ข้อมูลจำนวนมากเพื่อรับข้อมูลเชิงลึกเกี่ยวกับประสิทธิภาพและพฤติกรรมของภาระงาน GPU

เมื่อฟีเจอร์ "timestamp-query" พร้อมใช้งานใน GPUAdapter คุณจะทําสิ่งต่อไปนี้ได้

  • ขอ GPUDevice ด้วยฟีเจอร์ "timestamp-query"
  • สร้าง GPUQuerySet ประเภท "timestamp"
  • ใช้ GPUComputePassDescriptor.timestampWrites และ GPURenderPassDescriptor.timestampWrites เพื่อระบุตำแหน่งที่จะเขียนค่าการประทับเวลาใน GPUQuerySet
  • แก้ไขค่าการประทับเวลาเป็น GPUBuffer ด้วย resolveQuerySet()
  • อ่านค่าการประทับเวลาย้อนกลับโดยคัดลอกผลลัพธ์จาก GPUBuffer ไปยัง CPU
  • ถอดรหัสค่าการประทับเวลาเป็น BigInt64Array

ดูตัวอย่างและรุ่น dawn:1800 ต่อไปนี้

const adapter = await navigator.gpu.requestAdapter();
if (!adapter.features.has("timestamp-query")) {
  throw new Error("Timestamp query feature is not available");
}
// Explicitly request timestamp query feature.
const device = await adapter.requestDevice({
  requiredFeatures: ["timestamp-query"],
});
const commandEncoder = device.createCommandEncoder();

// Create a GPUQuerySet which holds 2 timestamp query results: one for the
// beginning and one for the end of compute pass execution.
const querySet = device.createQuerySet({ type: "timestamp", count: 2 });
const timestampWrites = {
  querySet,
  beginningOfPassWriteIndex: 0, // Write timestamp in index 0 when pass begins.
  endOfPassWriteIndex: 1, // Write timestamp in index 1 when pass ends.
};
const passEncoder = commandEncoder.beginComputePass({ timestampWrites });
// TODO: Set pipeline, bind group, and dispatch work to be performed.
passEncoder.end();

// Resolve timestamps in nanoseconds as a 64-bit unsigned integer into a GPUBuffer.
const size = 2 * BigInt64Array.BYTES_PER_ELEMENT;
const resolveBuffer = device.createBuffer({
  size,
  usage: GPUBufferUsage.QUERY_RESOLVE | GPUBufferUsage.COPY_SRC,
});
commandEncoder.resolveQuerySet(querySet, 0, 2, resolveBuffer, 0);

// Read GPUBuffer memory.
const resultBuffer = device.createBuffer({
  size,
  usage: GPUBufferUsage.COPY_DST | GPUBufferUsage.MAP_READ,
});
commandEncoder.copyBufferToBuffer(resolveBuffer, 0, resultBuffer, 0, size);

// Submit commands to the GPU.
device.queue.submit([commandEncoder.finish()]);

// Log compute pass duration in nanoseconds.
await resultBuffer.mapAsync(GPUMapMode.READ);
const times = new BigInt64Array(resultBuffer.getMappedRange());
console.log(`Compute pass duration: ${Number(times[1] - times[0])}ns`);
resultBuffer.unmap();

เนื่องจากข้อกังวลเกี่ยวกับการโจมตีที่ใช้เวลาเพียงสั้นๆ การค้นหาการประทับเวลาจะมีการวัดปริมาณด้วยความละเอียด 100 ไมโครวินาที ซึ่งทำให้ความแม่นยำและความปลอดภัยสามารถลดหลั่นกันได้ดี ในเบราว์เซอร์ Chrome คุณจะปิดใช้เชิงปริมาณการประทับเวลาได้โดยเปิดใช้ "ฟีเจอร์สำหรับนักพัฒนาแอป WebGPU" แจ้งที่ chrome://flags/#enable-webgpu-developer-features ในระหว่างการพัฒนาแอป ดูข้อมูลเพิ่มเติมได้ที่การนับปริมาณการค้นหาการประทับเวลา

เนื่องจาก GPU อาจรีเซ็ตตัวนับการประทับเวลาเป็นครั้งคราว ซึ่งส่งผลให้เกิดค่าที่ไม่คาดคิด เช่น เดลต้าเชิงลบระหว่างการประทับเวลา เราขอแนะนำให้คุณดูการเปลี่ยนแปลงความแตกต่างของ Git ที่เพิ่มการรองรับการค้นหาการประทับเวลาในตัวอย่าง Compute Boids ต่อไปนี้

วันที่ ภาพหน้าจอของตัวอย่าง Compute Boids ที่มีการค้นหาการประทับเวลา
ตัวอย่าง Compute Boids ที่มีการค้นหาการประทับเวลา

จุดแรกเข้าเริ่มต้นสำหรับโมดูลตัวปรับเฉดสี

หากต้องการปรับปรุงประสบการณ์สําหรับนักพัฒนาซอฟต์แวร์ ตอนนี้คุณสามารถละ entryPoint ของโมดูลตัวปรับแสงเงาเมื่อสร้างไปป์ไลน์การประมวลผลหรือแสดงผลได้แล้ว หากไม่พบจุดแรกเข้าที่ไม่ซ้ำกันสำหรับขั้นตอนตัวปรับแสงเงาในโค้ดตัวปรับแสง ระบบจะทริกเกอร์ GPUValidationError ดูตัวอย่างและปัญหา dawn:2254

const code = `
    @vertex fn vertexMain(@builtin(vertex_index) i : u32) ->
      @builtin(position) vec4f {
       const pos = array(vec2f(0, 1), vec2f(-1, -1), vec2f(1, -1));
       return vec4f(pos[i], 0, 1);
    }
    @fragment fn fragmentMain() -> @location(0) vec4f {
      return vec4f(1, 0, 0, 1);
    }`;
const module = myDevice.createShaderModule({ code });
const format = navigator.gpu.getPreferredCanvasFormat();
const pipeline = await myDevice.createRenderPipelineAsync({
  layout: "auto",
  vertex: { module, entryPoint: "vertexMain" },
  fragment: { module, entryPoint: "fragmentMain", targets: [{ format }] },
  vertex: { module },
  fragment: { module, targets: [{ format }] },
});

รองรับ display-p3 เป็นพื้นที่สี GPUExternalTexture

คุณสามารถกำหนดพื้นที่สีปลายทาง "display-p3" ได้แล้วเมื่อนำเข้า GPUExternalTexture จากวิดีโอ HDR ด้วย importExternalTexture() ดูวิธีที่ WebGPU จัดการพื้นที่สี ดูตัวอย่างและปัญหา chromium:1330250 ต่อไปนี้

// Create texture from HDR video.
const video = document.querySelector("video");
const texture = myDevice.importExternalTexture({
  source: video,
  colorSpace: "display-p3",
});

ข้อมูลฮีปหน่วยความจำ

เพื่อช่วยให้คุณทราบถึงขีดจำกัดของหน่วยความจำเมื่อจัดสรรปริมาณมากในระหว่างการพัฒนาแอป ตอนนี้ requestAdapterInfo() จะแสดงข้อมูล memoryHeaps เช่น ขนาดและประเภทของฮีปหน่วยความจำที่มีอยู่ในอะแดปเตอร์ ฟีเจอร์ทดลองนี้จะเข้าถึงได้เฉพาะเมื่อ "ฟีเจอร์สำหรับนักพัฒนาซอฟต์แวร์ WebGPU" flag ที่ chrome://flags/#enable-webgpu-developer-features เปิดใช้อยู่ ดูตัวอย่างและปัญหา dawn:2249

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

for (const { size, properties } of adapterInfo.memoryHeaps) {
  console.log(size); // memory heap size in bytes
  if (properties & GPUHeapProperty.DEVICE_LOCAL)  { /* ... */ }
  if (properties & GPUHeapProperty.HOST_VISIBLE)  { /* ... */ }
  if (properties & GPUHeapProperty.HOST_COHERENT) { /* ... */ }
  if (properties & GPUHeapProperty.HOST_UNCACHED) { /* ... */ }
  if (properties & GPUHeapProperty.HOST_CACHED)   { /* ... */ }
}
ภาพหน้าจอของ https://webgpureport.org ซึ่งแสดงฮีปหน่วยความจำในข้อมูลอะแดปเตอร์
ฮีปหน่วยความจำข้อมูลอะแดปเตอร์แสดงใน https://webgpureport.org

ข้อมูลอัปเดตรุ่งเช้า

เพิ่มเมธอด HasWGSLLanguageFeature และ EnumerateWGSLLanguageFeatures ใน wgpu::Instance เพื่อรองรับฟีเจอร์ภาษา WGSL แล้ว ดูฉบับ dawn:2260

ฟีเจอร์ wgpu::Feature::BufferMapExtendedUsages ที่ไม่ใช่แบบมาตรฐานช่วยให้คุณสร้างบัฟเฟอร์ GPU ที่มี wgpu::BufferUsage::MapRead หรือ wgpu::BufferUsage::MapWrite และ wgpu::BufferUsage อื่นๆ ได้ ดูตัวอย่างและปัญหา dawn:2204 ต่อไปนี้

wgpu::BufferDescriptor descriptor = {
  .size = 128,
  .usage = wgpu::BufferUsage::MapWrite | wgpu::BufferUsage::Uniform
};
wgpu::Buffer uniformBuffer = device.CreateBuffer(&descriptor);

uniformBuffer.MapAsync(wgpu::MapMode::Write, 0, 128,
   [](WGPUBufferMapAsyncStatus status, void* userdata)
   {
      wgpu::Buffer* buffer = static_cast<wgpu::Buffer*>(userdata);
      memcpy(buffer->GetMappedRange(), data, sizeof(data));
   },
   &uniformBuffer);

ฟีเจอร์ที่ได้รับการจัดทำเอกสาร ได้แก่ ANGLE Texture Share, D3D11 multiชุดข้อความ ที่มีการป้องกัน, การซิงค์อุปกรณ์แบบไม่เจาะจงปลายทาง, รูปแบบพื้นผิวแบบ Norm16, Timestamp Query Inside Passes, พื้นที่เก็บข้อมูลในเครื่อง Pixel, ฟีเจอร์ Shader และรูปแบบ Multi Planar

ทีม Chrome ได้สร้างที่เก็บ GitHub อย่างเป็นทางการสำหรับ Dawn แล้ว

ซึ่งกล่าวถึงไฮไลต์สำคัญเพียงบางส่วนเท่านั้น ดูรายการคอมมิตทั้งหมด

มีอะไรใหม่ใน WebGPU

รายการทั้งหมดที่กล่าวถึงในซีรีส์ What's New in WebGPU

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