mesa: glsl: fix glGetUniform for matrix queries
authorBrian Paul <brian.paul@tungstengraphics.com>
Wed, 6 Aug 2008 19:07:09 +0000 (13:07 -0600)
committerBrian Paul <brian.paul@tungstengraphics.com>
Wed, 6 Aug 2008 19:07:09 +0000 (13:07 -0600)
src/mesa/shader/shader_api.c

index 86b3d536e56faccc85f7e5a6f35ce9cac8e76eab..3a85f476740d8e1897c8b3cee2210fab03338966 100644 (file)
@@ -996,6 +996,71 @@ _mesa_get_shader_source(GLcontext *ctx, GLuint shader, GLsizei maxLength,
 }
 
 
+static void
+get_matrix_dims(GLenum type, GLint *rows, GLint *cols)
+{
+   switch (type) {
+   case GL_FLOAT_MAT2:
+      *rows = *cols = 2;
+      break;
+   case GL_FLOAT_MAT2x3:
+      *rows = 3;
+      *cols = 2;
+      break;
+   case GL_FLOAT_MAT2x4:
+      *rows = 4;
+      *cols = 2;
+      break;
+   case GL_FLOAT_MAT3:
+      *rows = 3;
+      *cols = 3;
+      break;
+   case GL_FLOAT_MAT3x2:
+      *rows = 2;
+      *cols = 3;
+      break;
+   case GL_FLOAT_MAT3x4:
+      *rows = 4;
+      *cols = 3;
+      break;
+   case GL_FLOAT_MAT4:
+      *rows = 4;
+      *cols = 4;
+      break;
+   case GL_FLOAT_MAT4x2:
+      *rows = 2;
+      *cols = 4;
+      break;
+   case GL_FLOAT_MAT4x3:
+      *rows = 3;
+      *cols = 4;
+      break;
+   default:
+      *rows = *cols = 0;
+   }
+}
+
+
+/**
+ * Determine the number of rows and columns occupied by a uniform
+ * according to its datatype.
+ */
+static void
+get_uniform_rows_cols(const struct gl_program_parameter *p,
+                      GLint *rows, GLint *cols)
+{
+   get_matrix_dims(p->DataType, rows, cols);
+   if (*rows == 0 && *cols == 0) {
+      /* not a matrix type, probably a float or vector */
+      *rows = p->Size / 4 + 1;
+      if (p->Size % 4 == 0)
+         *cols = 4;
+      else
+         *cols = p->Size % 4;
+   }
+}
+
+
 #define MAX_UNIFORM_ELEMENTS 16
 
 /**
@@ -1012,7 +1077,6 @@ get_uniformfv(GLcontext *ctx, GLuint program, GLint location,
       if (shProg->Uniforms &&
           location >= 0 && location < (GLint) shProg->Uniforms->NumUniforms) {
          GLint progPos;
-         GLuint i;
          const struct gl_program *prog = NULL;
 
          progPos = shProg->Uniforms->Uniforms[location].VertPos;
@@ -1028,13 +1092,23 @@ get_uniformfv(GLcontext *ctx, GLuint program, GLint location,
 
          ASSERT(prog);
          if (prog) {
+            const struct gl_program_parameter *p =
+               &prog->Parameters->Parameters[progPos];
+            GLint rows, cols, i, j, k;
+
             /* See uniformiv() below */                    
-            assert(prog->Parameters->Parameters[progPos].Size <= MAX_UNIFORM_ELEMENTS);
+            assert(p->Size <= MAX_UNIFORM_ELEMENTS);
 
-            for (i = 0; i < prog->Parameters->Parameters[progPos].Size; i++) {
-               params[i] = prog->Parameters->ParameterValues[progPos][i];
+            get_uniform_rows_cols(p, &rows, &cols);
+
+            k = 0;
+            for (i = 0; i < rows; i++) {
+               for (j = 0; j < cols; j++ ) {
+                  params[k++] = prog->Parameters->ParameterValues[progPos+i][j];
+               }
             }
-            return prog->Parameters->Parameters[progPos].Size;
+
+            return p->Size;
          }
       }
       else {
@@ -1415,51 +1489,6 @@ _mesa_uniform(GLcontext *ctx, GLint location, GLsizei count,
 }
 
 
-static void
-get_matrix_dims(GLenum type, GLint *rows, GLint *cols)
-{
-   switch (type) {
-   case GL_FLOAT_MAT2:
-      *rows = *cols = 2;
-      break;
-   case GL_FLOAT_MAT2x3:
-      *rows = 3;
-      *cols = 2;
-      break;
-   case GL_FLOAT_MAT2x4:
-      *rows = 4;
-      *cols = 2;
-      break;
-   case GL_FLOAT_MAT3:
-      *rows = 3;
-      *cols = 3;
-      break;
-   case GL_FLOAT_MAT3x2:
-      *rows = 2;
-      *cols = 3;
-      break;
-   case GL_FLOAT_MAT3x4:
-      *rows = 4;
-      *cols = 3;
-      break;
-   case GL_FLOAT_MAT4:
-      *rows = 4;
-      *cols = 4;
-      break;
-   case GL_FLOAT_MAT4x2:
-      *rows = 2;
-      *cols = 4;
-      break;
-   case GL_FLOAT_MAT4x3:
-      *rows = 3;
-      *cols = 4;
-      break;
-   default:
-      *rows = *cols = 0;
-   }
-}
-
-
 static void
 set_program_uniform_matrix(GLcontext *ctx, struct gl_program *program,
                            GLuint location, GLuint count,