موارد جدید در WebGPU (Chrome 121)

فرانسوا بوفور
François Beaufort

پشتیبانی از WebGPU در اندروید

تیم Chrome مشتاق است اعلام کند که WebGPU اکنون به طور پیش‌فرض در Chrome 121 در دستگاه‌های دارای Android 12 و بالاتر با پردازنده‌های گرافیکی Qualcomm و ARM فعال است.

پشتیبانی به تدریج گسترش خواهد یافت و طیف گسترده‌تری از دستگاه‌های اندرویدی، از جمله دستگاه‌هایی که در آینده نزدیک بر روی Android 11 اجرا می‌شوند را در بر می‌گیرد. این گسترش به آزمایش و بهینه سازی بیشتر برای اطمینان از تجربه یکپارچه در طیف وسیع تری از پیکربندی های سخت افزاری بستگی دارد. به شماره chromium:1497815 مراجعه کنید.

نماگرفت نمونه WebGPU در حال اجرا در Chrome for Android.
نمونه WebGPU در حال اجرا در Chrome برای Android.

برای کامپایل شیدر در ویندوز به جای FXC از DXC استفاده کنید

کروم اکنون از قدرت DXC (کامپایلر DirectX) برای کامپایل سایه‌بان‌ها در دستگاه‌های Windows D3D12 مجهز به سخت‌افزار گرافیکی SM6+ استفاده می‌کند. پیش از این، WebGPU برای کامپایل شیدر در ویندوز به FXC (کامپایلر FX) متکی بود. در حالی که FXC کاربردی بود، فاقد مجموعه ویژگی ها و بهینه سازی عملکرد موجود در DXC بود.

آزمایش اولیه نشان دهنده افزایش متوسط ​​20 درصدی در سرعت کامپایل شیدر محاسباتی هنگام استفاده از DXC در مقایسه با FXC است.

پرس و جوهای مهر زمانی در گذرنامه های محاسبه و ارائه

پرس و جوهای مهر زمان به برنامه های کاربردی WebGPU اجازه می دهد تا به طور دقیق (تا نانوثانیه) مدت زمان لازم برای اجرای محاسبات و رندر پاس های دستورات GPU را اندازه گیری کنند. آنها به شدت برای به دست آوردن بینش در مورد عملکرد و رفتار بارهای کاری GPU استفاده می شوند.

هنگامی که ویژگی "timestamp-query" در یک GPUAdapter در دسترس است، اکنون می توانید کارهای زیر را انجام دهید:

  • یک GPUDevice با ویژگی "timestamp-query" درخواست کنید.
  • یک GPUQuerySet از نوع "timestamp" ایجاد کنید.
  • از GPUComputePassDescriptor.timestampWrites و GPURenderPassDescriptor.timestampWrites برای تعیین محل نوشتن مقادیر برچسب زمانی در GPUQuerySet استفاده کنید.
  • مقادیر مهر زمان را با resolveQuerySet() در یک GPUBuffer حل کنید.
  • با کپی کردن نتایج از 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 میکروثانیه کوانتیزه می‌شوند که مصالحه خوبی بین دقت و امنیت فراهم می‌کند. در مرورگر کروم، می‌توانید با فعال کردن پرچم «ویژگی‌های توسعه‌دهنده WebGPU» در chrome://flags/#enable-webgpu-developer-features در حین توسعه برنامه خود، کمی‌سازی مهر زمانی را غیرفعال کنید. برای کسب اطلاعات بیشتر، کوانتیزه‌سازی پرسش‌های مهر زمانی را ببینید.

از آنجایی که پردازنده‌های گرافیکی ممکن است گهگاه شمارنده مهر زمان را بازنشانی کنند، که می‌تواند منجر به مقادیر غیرمنتظره مانند دلتاهای منفی بین مهرهای زمانی شود، توصیه می‌کنم تغییرات git diff را بررسی کنید که پشتیبانی از پرس و جو مهر زمانی را به نمونه Compute Boids زیر اضافه می‌کند.

نماگرفت نمونه Compute Boids با درخواست مهر زمانی.
نمونه Compute Boids با پرس و جوی مهر زمان.

نقاط ورودی پیش فرض به ماژول های سایه زن

برای بهبود تجربه توسعه دهنده، اکنون می توانید هنگام ایجاد خط لوله محاسبه یا رندر، entryPoint ماژول سایه زن خود را حذف کنید. اگر نقطه ورودی منحصر به فردی برای مرحله سایه زن در کد سایه زن یافت نشد، یک خطای GPUValidation Error راه اندازی می شود. مثال زیر و شماره 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

اکنون می‌توانید هنگام وارد کردن GPUExternalTexture از ویدیوهای HDR با importExternalTexture() فضای رنگ مقصد "display-p3" را تنظیم کنید. بررسی کنید که 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» در 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 اضافه شده‌اند. شماره سپیده دم: 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 Sharing ، D3D11 multithread محافظت شده ، همگام‌سازی ضمنی دستگاه ، قالب‌های بافت Norm16 ، Query Timestamp Inside Passes ، Pixel Local Storage ، ویژگی‌های Shader ، و Multi Planar Formats .

تیم کروم یک مخزن رسمی GitHub برای Dawn ایجاد کرده است.

این تنها برخی از نکات کلیدی را پوشش می دهد. فهرست جامع تعهدات را بررسی کنید.

چه چیزی در WebGPU جدید است

فهرستی از همه چیزهایی که در سری What's New in WebGPU پوشش داده شده است.

کروم 131

کروم 130

کروم 129

کروم 128

کروم 127

کروم 126

کروم 125

کروم 124

کروم 123

کروم 122

کروم 121

کروم 120

کروم 119

کروم 118

کروم 117

کروم 116

کروم 115

کروم 114

کروم 113