cancel
Showing results for 
Search instead for 
Did you mean: 

Archives Discussions

naededra
Journeyman III

Shader Storage Buffer object : type or qualifier changed between vertex and fragment ?

Hi everyone,

I'm currently testing shader storage buffer object on my HD 7950 (catalyst 14.4 / Windows 7 x64) and I'm having a strange issue :

I currently need to access some data stored in a SSBO from my fragment shader and, if the code works well on a GTX690, i can't get it to work on my AMD card :

To test if the data are correct in my buffer, i created a simple rendering of a quad that displays the data grid on screen using a vertex and a fragment shader :

-> a simple texture coordinate (which is in fact the fragment coord) is passed from the vertex to the fragment and is used to draw a 10x10 grid.


Thing is, if i don't use the SSBO, everything is fine and the grid is correctly displayed, but if i try to access the SSBO data inside the fragment, the openGL compiler throws me this error when I call  glUseProgramStages with the fragment shader:

textureCoordinates' s data type or qualifier doesn't match between vertex shader and fragment shader


Vertex Shader :


#version 430


/**


* Basic vertex shader for FBO rendering


*/


out gl_PerVertex {


        vec4 gl_Position;


        float gl_PointSize;


        float gl_ClipDistance[];


};


layout (location = 0) in vec3 Position;


out vec3 textureCoordinates;


void main()


{


  gl_Position = vec4(Position,1.0);


  textureCoordinates = 0.5*(Position.xyz+1.0);


}





Fragment shader


#version 430



in vec3 textureCoordinates;



out vec4 Color;



struct SSBOStructure


{


  vec4 data;


};



layout (binding=0) buffer SSBO


{


  int nbData;


  SSBOStructure datas[];


};



void main()


{



  Color = vec4(0.0);



  vec2 cellPos = textureCoordinates.xy * 10;


  vec2 delta = fract(cellPos);


  cellPos = floor(cellPos);


  if(delta.x < 0.01 || delta.x > 0.99 || delta.y < 0.01 || delta.y > 0.99)


  {


       Color = vec4(1.0);


  }



  if(cellPos.x == 0 && cellPos.y == 0)


  {


       Color = vec4(datas[0].data); // if this line is commented, everythings ok


  }


}



I've seen other discussion that report issues with SSBO on AMD cards so i know that this kind of buffer is kinda still "experimental" on AMD devices,  but did anyone had this issue before, or does anyone have an idea of what is wrong with my fragment shader that makes it unsuitable for AMD cards ?

Edit : I just have tested multiple SSBOs binding and access in fragment shader using a grid computed with gl_FragCoord instead of interpolated texture coords, and deleting the in and out vec3 textureCoordinates. It works well in that case, so my guess is the use of SSBO somehow breaks the interpolated variable between stages for the compiler (maybe the memory layout of the interpolated data).

0 Likes
6 Replies
temtaime
Journeyman III

Hi !

Is there any solution? I've hit that error too with 7850 and latest omega driver.

0 Likes
gsellers
Staff

Here's a wild guess, shooting from the hip...

This has nothing to do with SSBO. It looks from your mention of glUseProgramStages that you're using SSO. In that case, you're required to declare gl_PerVertex for all built-ins that you're using. You have done that in the vertex shader, but have not done so in the fragment shader. Therefore, the interfaces don't match. The fragment shader compiles and links fine because you don't actually use any of the built-in inputs. However, the "textureCoordinate" user-defined input is automatically assigned in input slot, which then conflicts with part of the gl_PerVertex block defined in the vertex shader. That explains the message about "textureCoordinates" not matching between vertex and fragment shader, and also explains why the sample works when you use gl_FragCoord.

Try declaring gl_PerVertex as an input to the fragment shader. Also, remove the gl_PointSize and gl_ClipDistance[] declarations from gl_PerVertex if you're not using them as it will be harmful to performance.

Cheers,

Graham

0 Likes

Hi Graham !

Thanks for your reply and your great work.

But i still cannot to realise what i need to do.

gl_PerVertex used as input in geometry shader, not fragment.

If i try to declare gl_PerVertex in my fragment shader as

in gl_PerVertex { vec4 gl_Position; };

i am getting an error:

error #168 : reserved built-in name 'Fragment Shader in'

Also that page Built-in Variable (GLSL) - OpenGL.org doesn't say that fragment shader have any interface built-ins.

Also i'm not using any of fragment shader built-ins in my fragment shader.

If i try to declare some built-in as you suggested for example

in vec4 gl_FragCoord;


an error is still here.


Please investigate in that bad error

I really love amd's hardware but that meaningless error makes me unhappy.

0 Likes
cgrant78
Adept III

The interface is between pipeline stages, fragment shader would not have an output interface because there is no exposed pipeline stage after the fragment shader. With that said the fragment shader takes input from previous pipeline stages and as such the input in your case from the vertex shader ( you are declaring out gl_PerVertex ) must match the input the fragment shader is expecting

As per in vec4 gl_FragCoord... the gl_FragCoord builtin is NOT an input for the fragment shader..it is an output.

Finally from the looks of things and as explained before..this does not seems to be an AMD error or a driver issue so far. How is the error meaningless ?

0 Likes

It's OK but i cannot declare gl_PerVertex for fragment shader as it's not a fragment shader input. If i try to do it then i'm getting an error as i described above.

0 Likes

In fragment, it not use out gl_PerVertex to declare pipeline between vertex and fragment stages.

You may use "in gl_ClipDistance[]  " to declare input corresponding to vertex 's gl_PerVertex.gl_ClipDistance[].

Or, you can delete gl_ClipDistance member is Vertex, since you did not use id at all.

0 Likes