This actually tries to pack any input with an explicit location we
just let the optimisiation passes clean up the extra assignments if
there was no actual packing done.
---
src/glsl/ir_optimization.h | 1 +
src/glsl/link_varyings.cpp | 33 ++++++++++++++++++++++++++-------
src/glsl/lower_packed_varyings.cpp | 20 ++++++++++++--------
3 files changed, 39 insertions(+), 15 deletions(-)
diff --git a/src/glsl/ir_optimization.h b/src/glsl/ir_optimization.h
index eab76ff..a313e30 100644
--- a/src/glsl/ir_optimization.h
+++ b/src/glsl/ir_optimization.h
@@ -129,6 +129,7 @@ void lower_ubo_reference(struct gl_shader *shader);
void lower_packed_varyings(void *mem_ctx,
unsigned locations_used, ir_variable_mode mode,
unsigned gs_input_vertices, gl_shader *shader,
+ unsigned base_location,
bool disable_varying_packing,
bool has_enhanced_layouts);
bool lower_vector_insert(exec_list *instructions, bool
lower_nonconstant_index);
diff --git a/src/glsl/link_varyings.cpp b/src/glsl/link_varyings.cpp
index 543153e..dd96c03 100644
--- a/src/glsl/link_varyings.cpp
+++ b/src/glsl/link_varyings.cpp
@@ -1583,7 +1583,8 @@ canonicalize_shader_io(exec_list *ir, enum
ir_variable_mode io_mode)
* In theory a 32 bits value will be enough but a 64 bits value is future
proof.
*/
uint64_t
-reserved_varying_slot(struct gl_shader *stage, ir_variable_mode io_mode)
+reserved_varying_slot(struct gl_shader *stage, ir_variable_mode io_mode,
+ int base_location)
{
assert(io_mode == ir_var_shader_in || io_mode == ir_var_shader_out);
assert(MAX_VARYING <= 64); /* avoid an overflow of the returned value */
@@ -1599,10 +1600,10 @@ reserved_varying_slot(struct gl_shader *stage,
ir_variable_mode io_mode)
if (var == NULL || var->data.mode != io_mode ||
!var->data.explicit_location ||
- var->data.location < VARYING_SLOT_VAR0)
+ var->data.location < base_location)
continue;
- var_slot = var->data.location - VARYING_SLOT_VAR0;
+ var_slot = var->data.location - base_location;
unsigned num_elements = get_varying_type(var, stage->Stage)
->count_attribute_slots(stage->Stage == MESA_SHADER_VERTEX);
@@ -1793,8 +1794,8 @@ assign_varying_locations(struct gl_context *ctx,
}
const uint64_t reserved_slots =
- reserved_varying_slot(producer, ir_var_shader_out) |
- reserved_varying_slot(consumer, ir_var_shader_in);
+ reserved_varying_slot(producer, ir_var_shader_out, VARYING_SLOT_VAR0) |
+ reserved_varying_slot(consumer, ir_var_shader_in, VARYING_SLOT_VAR0);
/* Add varyings with explicit locations to varyings with implicit locations
* to get the total number of slots used.
@@ -1822,10 +1823,28 @@ assign_varying_locations(struct gl_context *ctx,
hash_table_dtor(consumer_interface_inputs);
if (producer) {
+ if (producer->Stage == MESA_SHADER_VERTEX) {
+ /* Since we only pack vertex inputs with an explicit location we only
+ * need to count those inputs.
+ */
+ const uint64_t reserved_slots =
+ reserved_varying_slot(producer, ir_var_shader_in,
+ VERT_ATTRIB_GENERIC0);
+
+ /* Pack vertex inputs with the component layout qualifier */
+ unsigned vertex_attributes = _mesa_bitcount_64(reserved_slots);
+ if (vertex_attributes > 0)
+ lower_packed_varyings(mem_ctx, vertex_attributes,
+ ir_var_shader_in, 0, producer,
+ VERT_ATTRIB_GENERIC0, true,
+ ctx->Extensions.ARB_enhanced_layouts);
+ }
+
remove_unused_shader_inputs_and_outputs(prog, producer,
ir_var_shader_out);
lower_packed_varyings(mem_ctx, slots_used, ir_var_shader_out,
- 0, producer, disable_varying_packing,
+ 0, producer, VARYING_SLOT_VAR0,
+ disable_varying_packing,
ctx->Extensions.ARB_enhanced_layouts);
}
@@ -1833,7 +1852,7 @@ assign_varying_locations(struct gl_context *ctx,
remove_unused_shader_inputs_and_outputs(prog, consumer,
ir_var_shader_in);
lower_packed_varyings(mem_ctx, slots_used, ir_var_shader_in,
- consumer_vertices, consumer,
+ consumer_vertices, consumer, VARYING_SLOT_VAR0,
disable_varying_packing,
ctx->Extensions.ARB_enhanced_layouts);
}
diff --git a/src/glsl/lower_packed_varyings.cpp
b/src/glsl/lower_packed_varyings.cpp
index cfba9af..9a8c336 100644
--- a/src/glsl/lower_packed_varyings.cpp
+++ b/src/glsl/lower_packed_varyings.cpp
@@ -169,6 +169,7 @@ public:
unsigned gs_input_vertices,
exec_list *out_instructions,
exec_list *out_variables,
+ unsigned base_location,
bool disable_varying_packing,
bool has_enhanced_layouts);
@@ -197,11 +198,13 @@ private:
*/
void * const mem_ctx;
+ const unsigned base_location;
+
/**
* Number of generic varying slots which are used by this shader. This is
* used to allocate temporary intermediate data structures. If any varying
* used by this shader has a location greater than or equal to
- * VARYING_SLOT_VAR0 + locations_used, an assertion will fire.
+ * base_location + locations_used, an assertion will fire.
*/
const unsigned locations_used;
@@ -245,9 +248,10 @@ private:
lower_packed_varyings_visitor::lower_packed_varyings_visitor(
void *mem_ctx, unsigned locations_used, ir_variable_mode mode,
unsigned gs_input_vertices, exec_list *out_instructions,
- exec_list *out_variables, bool disable_varying_packing,
- bool has_enhanced_layouts)
+ exec_list *out_variables, unsigned base_location,
+ bool disable_varying_packing, bool has_enhanced_layouts)
: mem_ctx(mem_ctx),
+ base_location(base_location),
locations_used(locations_used),
packed_varyings((ir_variable **)
rzalloc_array_size(mem_ctx, sizeof(*packed_varyings),
@@ -270,7 +274,7 @@ lower_packed_varyings_visitor::run(struct gl_shader *shader)
continue;
if (var->data.mode != this->mode ||
- var->data.location < VARYING_SLOT_VAR0 ||
+ var->data.location < (int) this->base_location ||
!this->needs_lowering(var))
continue;
@@ -594,7 +598,6 @@ lower_packed_varyings_visitor::lower_arraylike(ir_rvalue
*rvalue,
} else {
char *subscripted_name
= ralloc_asprintf(this->mem_ctx, "%s[%d]", name, i);
-
fine_location =
this->lower_rvalue(dereference_array, fine_location,
unpacked_var, subscripted_name,
@@ -621,7 +624,7 @@ lower_packed_varyings_visitor::get_packed_varying_deref(
unsigned location, ir_variable *unpacked_var, const char *name,
unsigned vertex_index)
{
- unsigned slot = location - VARYING_SLOT_VAR0;
+ unsigned slot = location - this->base_location;
assert(slot < locations_used);
if (this->packed_varyings[slot] == NULL) {
char *packed_name = ralloc_asprintf(this->mem_ctx, "packed:%s", name);
@@ -748,8 +751,8 @@
lower_packed_varyings_gs_splicer::visit_leave(ir_emit_vertex *ev)
void
lower_packed_varyings(void *mem_ctx, unsigned locations_used,
ir_variable_mode mode, unsigned gs_input_vertices,
- gl_shader *shader, bool disable_varying_packing,
- bool has_enhanced_layouts)
+ gl_shader *shader, unsigned base_location,
+ bool disable_varying_packing, bool has_enhanced_layouts)
{
exec_list *instructions = shader->ir;
ir_function *main_func = shader->symbols->get_function("main");
@@ -761,6 +764,7 @@ lower_packed_varyings(void *mem_ctx, unsigned
locations_used,
gs_input_vertices,
&new_instructions,
&new_variables,
+ base_location,
disable_varying_packing,
has_enhanced_layouts);
visitor.run(shader);
--
2.4.3
_______________________________________________
mesa-dev mailing list
[email protected]
http://lists.freedesktop.org/mailman/listinfo/mesa-dev