[Mesa-users] GL_ACTIVE_UNIFORMS returns unexpected value

Lascha Lagidse laschalagidse at triumphstudios.com
Thu Mar 19 03:16:37 PDT 2015


On 3/18/2015 6:12 PM, Brian Paul wrote:
> On 03/18/2015 09:37 AM, Lascha Lagidse wrote:
>> Hello :)
>>
>> I am Lascha, new to linux and first time subscribing to a mailing list.
>> I heard you were great guys ;)
>
> We try to be. :)
>
>
>> So, I am currently in the process of porting the game Age of Wonders 3
>> to Linux. The game is currently in open-beta on Steam, and people
>> reported issues with the specifically the Mesa graphics driver. I had a
>> look and it looks like this driver behaves differently on this driver
>> when using glGetProgramiv and glGetActiveUniform.
>>
>> The vertex shader (see bottom) is attached to a program. The program is
>> then linked. Note: Only this vertex shader is attached to the program;
>> there is no other shader attached. Now using glGetProgramiv with
>> GL_ACTIVE_UNIFORMS will return 2, but I expect it to be 3 like on the
>> other drivers. According to glGetActiveUniform it is the variable 'c24'
>> which is missing. My guess is that it's optimized away, for some reason.
>> If I also link the fragment shader, then 'c24' is listed correctly.
>>
>> My goal is to retrieve the active uniforms from specifically the vertex
>> shader. If I link both the vertex AND the fragment program, then there
>> is no way to distinguish which uniforms belong to the vertex program and
>> which belong to the fragment program (or is there?).
>>
>> I can't think of a nice work-around; but since this is only
>> initialization code the only work-around that comes to mind is to
>> serialize the info I get from glGetActiveUniform on another driver and
>> use that info instead of calling glGetActiveUniform at initialization.
>>
>> #version 140
>> uniform mat4 c20;
>> uniform vec4 c24;
>> uniform vec4 c25;
>> in vec3 POSITION0;
>> in vec2 TEXCOORD0;
>> out vec2 xlv_TEXCOORD0;
>> void main ()
>> {
>>    vec4 PosWS_1;
>>    PosWS_1.xy = (c25.xy + (POSITION0.xy * c25.zw));
>>    PosWS_1.z = POSITION0.z;
>>    PosWS_1.w = 1.0;
>>    gl_Position = (c20 * PosWS_1);
>>    xlv_TEXCOORD0 = (c24.xy + (TEXCOORD0 * c24.zw));
>> }
>
> Which version of Mesa are you using?  Would it be possible to get a 
> simple glut/piglit test program?
>
> -Brian
>
Sorry if you're receiving this multiple times. I think I should have 
used 'Reply All' instead of 'Reply'. Realized this too late.

I'm using "3.3 (Core profile) Mesa 10.3.2" (according to GL_VERSION).

Here is a simple test program. It uses freeglut and glew. I hope that's 
okay.

#include <GL/glew.h>
#include <GL/freeglut.h>
#include <stdlib.h>
#include <cstdio>
#include <cstring>

int main(int argc, char *argv[])
{
   glutInit(&argc, argv);
   glutInitWindowSize(128,128);
   glutInitWindowPosition(10,10);
   glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE | GLUT_DEPTH);
   glutInitContextVersion(3, 3);
   glutInitContextFlags(GLUT_CORE_PROFILE);
   glutCreateWindow("LinuxShaderBug");
   glewInit();

   printf("version: %s\n", glGetString(GL_VERSION));

   const GLchar* shader_code = "#version 140\n\
     uniform mat4 c20;\n\
     uniform vec4 c24;\n\
     uniform vec4 c25;\n\
     in vec3 POSITION0;\n\
     in vec2 TEXCOORD0;\n\
     out vec2 xlv_TEXCOORD0;\n\
     void main ()\n\
     {\n\
       vec4 PosWS_1;\n\
       PosWS_1.xy = (c25.xy + (POSITION0.xy * c25.zw));\n\
       PosWS_1.z = POSITION0.z;\n\
       PosWS_1.w = 1.0;\n\
       gl_Position = (c20 * PosWS_1);\n\
       xlv_TEXCOORD0 = (c24.xy + (TEXCOORD0 * c24.zw));\n\
     }\n";

   const GLchar* shader_code_array[1] = { shader_code };
   const GLint shader_size_array[1] = { strlen(shader_code) };
   GLuint shader_handle = glCreateShader(GL_VERTEX_SHADER);
   glShaderSource(shader_handle, 1, shader_code_array, shader_size_array);
   glCompileShader(shader_handle);

   GLuint program_handle = glCreateProgram();
   glAttachShader(program_handle, shader_handle);
   glLinkProgram(program_handle);

   GLint num_uniforms = 0;
   glGetProgramiv(program_handle, GL_ACTIVE_UNIFORMS, &num_uniforms);
   printf("num_uniforms: %i\n", num_uniforms);

   char u_name[32];
   GLsizei u_name_len = 0;
   GLint u_size = 0;
   GLenum u_type = GL_NONE;
   GLint u_idx = 0;

   for (u_idx = 0; u_idx < num_uniforms; ++u_idx)
   {
     glGetActiveUniform(program_handle, u_idx, 31, &u_name_len, &u_size, 
&u_type, &u_name[0]);
     printf("u_name: %s\n", u_name);
   }

   return EXIT_SUCCESS;
}

- Lascha


More information about the mesa-users mailing list