WGSL struct internals seems to be wrongly generated

Hi, as followup to my WGSL debug question,

now that I can see the generated shader code with BabylonJS internals, it seems the way the structure Internals gets generated, its output is somehow corrupt,

struct Internals {
  yFactor_: f32,
  textureOutputHeight_: f32,
  output.position = gl_Position;
  output.position.y = output.position.y * internals.yFactor_;
  return output;
}

Even if the cause is incorrect WGSL code, it seems strange to end up with a struct that has regular code inside, which naturally Chrome doesn’t like.

Can you paste the GLSL code that generates such WGSL code? It seems incorrect indeed.

Sure, it is the same WGSL code I was using as sample on the other discussion thread.

Even if this code does have WGSL errors, I am the opinion that generating bad code such as the struct Internals isn’t of much help when doing shader based development, errors are bound to happen during interactive development, and this makes it quite hard to track down what is actually wrong with the shader code.

#include<sceneUboDeclaration>
#include<meshUboDeclaration>

// Attributes
attribute position : vec4<f32>;
attribute uv: vec2<f32>;

// Varying
varying vUV : vec2<f32>;

struct MyUBO {
    scale: f32,
};

var<uniform> myUBO: MyUBO;

@vertex
fn main(input : VertexInputs) -> FragmentInputs {
    gl_Position = scene.viewProjection * mesh.world * vec4<f32>(position * vec3<f32>(myUBO.scale), 1.0);

    vUV = uv;
} 

If I’m using your code (https://playground.babylonjs.com/#6GFJNR#171), the shader code I get from the browser console is:

//#define SHADER_NAME vertex:customcube
var<private> gl_VertexID : u32;
var<private> gl_InstanceID : u32;
var<private> gl_Position : vec4<f32>;
struct VertexInputs {
  @builtin(vertex_index) vertexIndex : u32,
  @builtin(instance_index) instanceIndex : u32,
@location(0) position : vec4<f32>,
@location(1) uv : vec2<f32>,
};
var<private> position : vec4<f32>;
var<private> uv : vec2<f32>;
struct FragmentInputs {
  @builtin(position) position : vec4<f32>,
@location(0) vUV : vec2<f32>,
};
var<private> vUV : vec2<f32>;

struct LeftOver {
 vColor : array<vec4<f32>, 2>,
};
@group(1) @binding(6) var<uniform> uniforms : LeftOver;
struct Internals {
yFactor_: f32,
textureOutputHeight_: f32,
};
@group(1) @binding(2) var<uniform> internals : Internals;
struct Scene {
viewProjection : mat4x4<f32>,
view : mat4x4<f32>,
projection : mat4x4<f32>,
vEyePosition : vec4<f32>,
};
@group(0) @binding(0) var<uniform> scene : Scene;
struct Mesh {
world : mat4x4<f32>,
visibility : f32,
};
@group(1) @binding(3) var<uniform> mesh : Mesh;
//#define WORLD_UBO



struct MyUBO {
scale: f32,
};
@group(1) @binding(4) var<uniform> myUBO: MyUBO;
@vertex
fn main(input : VertexInputs) -> FragmentInputs {  var output : FragmentInputs;
  gl_VertexID = input.vertexIndex;
  gl_InstanceID = input.instanceIndex;
  position = input.position;
  uv = input.uv;

gl_Position = scene.viewProjection * mesh.world * vec4<f32>(position * vec3<f32>(myUBO.scale), 1.0);
vUV = uv;
  output.position = gl_Position;
  output.position.y = output.position.y * internals.yFactor_;
  output.vUV = vUV;
  return output;
}

The Internals struct is ok there and the output related code is at the right location (just before returning from the main function).

Are you able to provide a link to a repro somewhere of what you get in your first post?

1 Like

Hi, thanks for looking into it.

Yes it is my ongoing improvements to CYOS, GitHub - pjmlp/CYOS: Create Your Own Shader

I just added those shaders as part of the basic example, here is how it looks like with debugging turned on,

This PR will improve the error message when the shader code has no “main” entry point:

1 Like

Thanks for the support, hopping to eventually get an improved CYOS by the time WebGPU 1.0 is released.

However I wonder, the shaders do have a main entry point, was the error on the ShaderMaterial configuration?

No, the shaders did not have a main entry point, the code was simply something like: // todo

Only the basic one has shader content, all the others ones are indeed marked as todo, see screenshot that is the basic one.

Yes, but when you switch the engine from WebGL to WebGPU it tries to take an empty shader (don’t remember which one - maybe the template is not “basic” after you just have started the app), that’s why it was failing: the non empty shaders do compile and work.

I guess I will have to do a deeper look into it, thanks.