[Mesa-dev] [PATCH V2 1/3] glsl: move array validation into its own function

Timothy Arceri t_arceri at yahoo.com.au
Wed Feb 25 23:45:11 PST 2015


V2: return true when var->type is unsized by max access is within valid range

---
 src/glsl/linker.cpp | 89 ++++++++++++++++++++++++++++++-----------------------
 src/glsl/linker.h   |  5 +++
 2 files changed, 55 insertions(+), 39 deletions(-)

diff --git a/src/glsl/linker.cpp b/src/glsl/linker.cpp
index 3f5eac1..dafcbe0 100644
--- a/src/glsl/linker.cpp
+++ b/src/glsl/linker.cpp
@@ -680,6 +680,45 @@ validate_geometry_shader_emissions(struct gl_context *ctx,
    }
 }
 
+bool
+validate_intrastage_arrays(struct gl_shader_program *prog,
+                           ir_variable *const var,
+		           ir_variable *const existing)
+{
+   /* Consider the types to be "the same" if both types are arrays
+    * of the same type and one of the arrays is implicitly sized.
+    * In addition, set the type of the linked variable to the
+    * explicitly sized array.
+    */
+   if (var->type->is_array() && existing->type->is_array() &&
+       (var->type->fields.array == existing->type->fields.array) &&
+       ((var->type->length == 0)|| (existing->type->length == 0))) {
+      if (var->type->length != 0) {
+         if (var->type->length <= existing->data.max_array_access) {
+            linker_error(prog, "%s `%s' declared as type "
+                         "`%s' but outermost dimension has an index"
+                         " of `%i'\n",
+                         mode_string(var),
+                         var->name, var->type->name,
+                         existing->data.max_array_access);
+         }
+         existing->type = var->type;
+         return true;
+      } else if (existing->type->length != 0) {
+         if(existing->type->length <= var->data.max_array_access) {
+            linker_error(prog, "%s `%s' declared as type "
+                         "`%s' but outermost dimension has an index"
+                         " of `%i'\n",
+                         mode_string(var),
+                         var->name, existing->type->name,
+                         var->data.max_array_access);
+         }
+         return true;
+      }
+   }
+   return false;
+}
+
 
 /**
  * Perform validation of global variables used across multiple shaders
@@ -719,50 +758,22 @@ cross_validate_globals(struct gl_shader_program *prog,
 	  */
 	 ir_variable *const existing = variables.get_variable(var->name);
 	 if (existing != NULL) {
+            /* Check if types match. Interface blocks have some special
+             * rules so we handle those elsewhere.
+             */
 	    if (var->type != existing->type) {
-	       /* Consider the types to be "the same" if both types are arrays
-		* of the same type and one of the arrays is implicitly sized.
-		* In addition, set the type of the linked variable to the
-		* explicitly sized array.
-		*/
-	       if (var->type->is_array()
-		   && existing->type->is_array()
-		   && (var->type->fields.array == existing->type->fields.array)
-		   && ((var->type->length == 0)
-		       || (existing->type->length == 0))) {
-		  if (var->type->length != 0) {
-                     if (var->type->length <= existing->data.max_array_access) {
-                        linker_error(prog, "%s `%s' declared as type "
-                                     "`%s' but outermost dimension has an index"
-                                     " of `%i'\n",
-                                     mode_string(var),
-                                     var->name, var->type->name,
-                                     existing->data.max_array_access);
-                        return;
-                     }
-		     existing->type = var->type;
-		  } else if (existing->type->length != 0
-                             && existing->type->length <=
-                                var->data.max_array_access) {
+	       if (!validate_intrastage_arrays(prog, var, existing)) {
+                  if (var->type->is_record() && existing->type->is_record()
+                      && existing->type->record_compare(var->type)) {
+                     existing->type = var->type;
+                  } else {
                      linker_error(prog, "%s `%s' declared as type "
-                                  "`%s' but outermost dimension has an index"
-                                  " of `%i'\n",
+                                  "`%s' and type `%s'\n",
                                   mode_string(var),
-                                  var->name, existing->type->name,
-                                  var->data.max_array_access);
+                                  var->name, var->type->name,
+                                  existing->type->name);
                      return;
                   }
-               } else if (var->type->is_record()
-		   && existing->type->is_record()
-		   && existing->type->record_compare(var->type)) {
-		  existing->type = var->type;
-	       } else {
-		  linker_error(prog, "%s `%s' declared as type "
-			       "`%s' and type `%s'\n",
-			       mode_string(var),
-			       var->name, var->type->name,
-			       existing->type->name);
-		  return;
 	       }
 	    }
 
diff --git a/src/glsl/linker.h b/src/glsl/linker.h
index be4da5e..ce3dc32 100644
--- a/src/glsl/linker.h
+++ b/src/glsl/linker.h
@@ -61,6 +61,11 @@ link_uniform_blocks(void *mem_ctx,
                     unsigned num_shaders,
                     struct gl_uniform_block **blocks_ret);
 
+bool
+validate_intrastage_arrays(struct gl_shader_program *prog,
+                           ir_variable *const var,
+                           ir_variable *const existing);
+
 void
 validate_intrastage_interface_blocks(struct gl_shader_program *prog,
                                      const gl_shader **shader_list,
-- 
2.1.0



More information about the mesa-dev mailing list