[Mesa-dev] [PATCH 37/47] glsl/lower_64bit: handle any/all operations

Elie Tournier tournier.elie at gmail.com
Wed Aug 23 11:08:07 UTC 2017


From: Dave Airlie <airlied at redhat.com>

This just splits them out and combines the results.

Signed-off-by: Dave Airlie <airlied at redhat.com>
---
 src/compiler/glsl/lower_64bit.cpp | 61 ++++++++++++++++++++++++++++++++++++++-
 1 file changed, 60 insertions(+), 1 deletion(-)

diff --git a/src/compiler/glsl/lower_64bit.cpp b/src/compiler/glsl/lower_64bit.cpp
index f8fcf9fd0a..79148bb169 100644
--- a/src/compiler/glsl/lower_64bit.cpp
+++ b/src/compiler/glsl/lower_64bit.cpp
@@ -59,6 +59,12 @@ ir_dereference_variable *compact_destination(ir_factory &,
 ir_dereference_variable *merge_destination(ir_factory &,
                                            const glsl_type *type,
                                            ir_variable *result[4]);
+ir_dereference_variable *all_equal_destination(ir_factory &,
+					       const glsl_type *type,
+					       ir_variable *result[4]);
+ir_dereference_variable *any_nequal_destination(ir_factory &,
+						const glsl_type *type,
+						ir_variable *result[4]);
 
 ir_rvalue *lower_op_to_function_call(ir_instruction *base_ir,
                                      ir_expression *ir,
@@ -309,6 +315,47 @@ lower_64bit::merge_destination(ir_factory &body,
    return new(mem_ctx) ir_dereference_variable(merged_result);
 }
 
+/*
+ * and the results from each comparison.
+ */
+ir_dereference_variable *
+lower_64bit::all_equal_destination(ir_factory &body,
+			     const glsl_type *type,
+			     ir_variable *result[4])
+{
+   ir_variable *const merged_result =
+      body.make_temp(glsl_type::bool_type, "all_result");
+
+   body.emit(assign(merged_result, result[0]));
+   for (unsigned i = 1; i < type->vector_elements; i++) {
+      body.emit(assign(merged_result, logic_and(merged_result, result[i])));
+   }
+
+   void *const mem_ctx = ralloc_parent(merged_result);
+   return new(mem_ctx) ir_dereference_variable(merged_result);
+}
+
+/*
+ * and the results from each comparison, the not the result
+ */
+ir_dereference_variable *
+lower_64bit::any_nequal_destination(ir_factory &body,
+			     const glsl_type *type,
+			     ir_variable *result[4])
+{
+   ir_variable *const merged_result =
+      body.make_temp(glsl_type::bool_type, "any_result");
+
+   body.emit(assign(merged_result, result[0]));
+   for (unsigned i = 1; i < type->vector_elements; i++) {
+      body.emit(assign(merged_result, logic_and(merged_result, result[i])));
+   }
+
+   body.emit(assign(merged_result, logic_not(merged_result)));
+   void *const mem_ctx = ralloc_parent(merged_result);
+   return new(mem_ctx) ir_dereference_variable(merged_result);
+}
+
 ir_rvalue *
 lower_64bit::lower_op_to_function_call(ir_instruction *base_ir,
                                        ir_expression *ir,
@@ -362,7 +409,11 @@ lower_64bit::lower_op_to_function_call(ir_instruction *base_ir,
    }
 
    ir_rvalue *rv;
-   if (ir->type->is_64bit())
+   if (ir->operation == ir_binop_all_equal)
+      rv = all_equal_destination(body, ir->type, dst);
+   else if (ir->operation == ir_binop_any_nequal)
+      rv = any_nequal_destination(body, ir->type, dst);
+   else if (ir->type->is_64bit())
       rv = compact_destination(body, ir->type, dst);
    else
       rv = merge_destination(body, ir->type, dst);
@@ -579,6 +630,14 @@ lower_64bit_visitor::handle_rvalue(ir_rvalue **rvalue)
       }
       break;
 
+   case ir_binop_all_equal:
+   case ir_binop_any_nequal:
+      if (lowering(EQ64)) {
+	 if (ir->operands[0]->type->base_type == GLSL_TYPE_DOUBLE) {
+            *rvalue = handle_op(ir, "__builtin_feq64", generate_ir::feq64);
+	 }
+      }
+      break;
    default:
       break;
    }
-- 
2.14.1



More information about the mesa-dev mailing list