Some Sokol WebGPU demos have wildly misplaced vertex geometry on macOS
Categories
(Core :: Graphics: WebGPU, defect)
Tracking
()
People
(Reporter: ErichDonGubler, Unassigned)
References
(Blocks 1 open bug)
Details
Attachments
(4 files)
Some entries from the Sokol demos' WebGPU variants have some wildly misplaced vertices.
Steps to reproduce
-
Open a demo that is known to exhibit this behavior in Firefox. Observe broken geometry.
The
sbuftex
andozz-storagebuffer
entries are the two examples I'm currently aware of that follow this. -
Compare the entry selected in the previous step in Chrome. Observe that the demo functions as expected.
Reporter | ||
Comment 1•6 months ago
|
||
From the WebGPU team's internal chat:
Erich Gubler: This seems like vertex pulling for macOS might not be handling a vertex format properly (CC :bradwerth).
Jim Blandy: Right. The first thing I would check is which vertex format the vertex buffer is using, and then see if the code generated by
naga::back::msl::Writer::write_unpacking_function is correct
.
Reporter | ||
Comment 2•6 months ago
|
||
Reporter | ||
Comment 3•6 months ago
|
||
Reporter | ||
Comment 4•6 months ago
|
||
Reporter | ||
Comment 5•6 months ago
|
||
Reporter | ||
Comment 6•6 months ago
|
||
N.B., we have not confirmed whether this reproduces on platforms outside of macOS yet.
Comment 7•6 months ago
|
||
I managed to test on windows (d3d12 backend) and the examples display properly - the issue is most likely macOS only (due to vertex pulling).
I also tried a few other examples on the website and they also work properly.
Reporter | ||
Updated•6 months ago
|
Reporter | ||
Updated•6 months ago
|
Comment 8•5 months ago
|
||
Filed an upstream issue: wgpu#7456
Reporter | ||
Comment 9•3 months ago
|
||
Andre Weissflog (the author of the demo, CC'd) has speculated the following about the root cause of this issue (Matrix link):
- this sample should render a cube via vertex pulling, but renders a mess... I suspect there's something wrong with struct item alignment in storage buffers: https://floooh.github.io/sokol-webgpu/sbuftex-sapp.html
Comment 10•3 months ago
|
||
I stumbled upon https://github.com/gfx-rs/wgpu/issues/5262 last week, which seems like it could be relevant here.
Comment 11•3 months ago
|
||
I can provide a bit more info:
This vertex-pulling sample (https://floooh.github.io/sokol-webgpu/vertexpull-sapp.html) works fine with the vertex struct in the storage buffer looking like this:
struct sb_vertex {
pos: vec3f,
color: vec4f,
}
The C-side struct looks like this (generated by my shader-cross-compiler):
SOKOL_SHDC_ALIGN(16) typedef struct sb_vertex_t {
float pos[3];
uint8_t _pad_12[4];
float color[4];
} sb_vertex_t;
When running that same shader through SPIRVCross with MetalSL output, the struct looks like this:
struct sb_vertex
{
float3 pos;
float4 color;
};
This sample (https://floooh.github.io/sokol-webgpu/sbuftex-sapp.html) is broken and uses a vertex struct like this:
struct sb_vertex {
pos : vec3f,
idx : u32,
uv : vec2f,
}
The C-side struct looks like this:
SOKOL_SHDC_ALIGN(16) typedef struct sb_vertex_t {
float pos[3];
uint32_t idx;
float uv[2];
uint8_t _pad_24[8];
} sb_vertex_t;
...and that same struct as MetalSL via SPIRVCross:
struct sb_vertex
{
packed_float3 pos;
uint idx;
float2 uv;
char _m0_final_padding[8];
};
Note how SPIRVCross picks packed_float3
here instead of float3
. I guess the Firefox WGSL compiler simply doesn't do this when generating Metal output and causing the float3.
Also note that there's a closed issue which seems to be related here: https://github.com/gfx-rs/wgpu/issues/4522
...but maybe this is only for uniform data, not storage buffer data?
Comment 12•3 months ago
|
||
Bah, I can't edit my comments here can I? :) Excuse the weird typo in my above comment :)
TL;DR: I guess the Firefox WGSL compiler needs to be smarter about picking float3 vs packed_float3 when translating storage buffer array item structs to Metal.
Comment 13•3 months ago
|
||
PS: also note how SPIRVCross adds explicit padding bytes at the end to cause the struct size to be a multiple of 16 (maybe this is the actual issue?).
Comment 14•3 months ago
|
||
Ok, it's not the packed_float3
, but the struct size which is the problem:
When I change the WGSL struct item to so that the size if a multiple of 16 bytes the problem is fixed, e.g.:
struct sb_vertex {
pos : vec3f,
idx : u32,
uv : vec2f,
unused : vec2f,
}
...e.g. the last unused: vec2f
makes it work because it brings the struct size to 16 bytes. I guess Naga needs to add explicit padding bytes like SPIRVCross does (or maybe force a 16-byte alignment on the whole struct - assuming that this also works when the struct is in an array).
Reporter | ||
Updated•1 month ago
|
Reporter | ||
Comment 15•1 month ago
|
||
Confirmed as fixed upstream! 🙌🏻
Description
•