diff options
author | Jonathan Gray <jsg@cvs.openbsd.org> | 2020-01-22 02:13:18 +0000 |
---|---|---|
committer | Jonathan Gray <jsg@cvs.openbsd.org> | 2020-01-22 02:13:18 +0000 |
commit | fdcc03929065b5bf5dd93553db219ea3e05c8c34 (patch) | |
tree | ca90dc8d9e89febdcd4160956c1b8ec098a4efc9 /lib/mesa/src/compiler/glsl/lower_vector_derefs.cpp | |
parent | 3c9de4a7e13712b5696750bbd59a18c848742022 (diff) |
Import Mesa 19.2.8
Diffstat (limited to 'lib/mesa/src/compiler/glsl/lower_vector_derefs.cpp')
-rw-r--r-- | lib/mesa/src/compiler/glsl/lower_vector_derefs.cpp | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/lib/mesa/src/compiler/glsl/lower_vector_derefs.cpp b/lib/mesa/src/compiler/glsl/lower_vector_derefs.cpp index 2aae30d82..0c09630fa 100644 --- a/lib/mesa/src/compiler/glsl/lower_vector_derefs.cpp +++ b/lib/mesa/src/compiler/glsl/lower_vector_derefs.cpp @@ -63,6 +63,16 @@ vector_deref_visitor::visit_enter(ir_assignment *ir) if (!deref->array->type->is_vector()) return ir_rvalue_enter_visitor::visit_enter(ir); + /* SSBOs and shared variables are backed by memory and may be accessed by + * multiple threads simultaneously. It's not safe to lower a single + * component store to a load-vec-store because it may race with writes to + * other components. + */ + ir_variable *var = deref->variable_referenced(); + if (var->data.mode == ir_var_shader_storage || + var->data.mode == ir_var_shader_shared) + return ir_rvalue_enter_visitor::visit_enter(ir); + ir_rvalue *const new_lhs = deref->array; void *mem_ctx = ralloc_parent(ir); @@ -150,6 +160,17 @@ vector_deref_visitor::handle_rvalue(ir_rvalue **rv) if (!deref->array->type->is_vector()) return; + /* Back-ends need to be able to handle derefs on vectors for SSBOs, UBOs, + * and shared variables. They have to handle it for writes anyway so we + * may as well require it for reads. + */ + ir_variable *var = deref->variable_referenced(); + if (var && (var->data.mode == ir_var_shader_storage || + var->data.mode == ir_var_shader_shared || + (var->data.mode == ir_var_uniform && + var->get_interface_type()))) + return; + void *mem_ctx = ralloc_parent(deref); *rv = new(mem_ctx) ir_expression(ir_binop_vector_extract, deref->array, |