[Mesa-dev] [PATCH 42/47] glsl: Add a lowering pass for 64-bit float min()

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


Signed-off-by: Elie Tournier <elie.tournier at collabora.com>
---
 src/compiler/glsl/ir_optimization.h        |  1 +
 src/compiler/glsl/lower_instructions.cpp   | 28 ++++++++++++++++++++++++++++
 src/mesa/state_tracker/st_glsl_to_tgsi.cpp |  1 +
 3 files changed, 30 insertions(+)

diff --git a/src/compiler/glsl/ir_optimization.h b/src/compiler/glsl/ir_optimization.h
index e18924d62b..a2ebc16e93 100644
--- a/src/compiler/glsl/ir_optimization.h
+++ b/src/compiler/glsl/ir_optimization.h
@@ -54,6 +54,7 @@
 #define DDIV_TO_MUL_RCP           0x100000
 #define DIV_TO_MUL_RCP            (FDIV_TO_MUL_RCP | DDIV_TO_MUL_RCP)
 #define SQRT_TO_ABS_SQRT          0x200000
+#define MIN_MAX_TO_LESS           0x400000
 
 /* Operations for lower_64bit_integer_instructions()
  * and lower_64bit_double_instructions()
diff --git a/src/compiler/glsl/lower_instructions.cpp b/src/compiler/glsl/lower_instructions.cpp
index 0c1408911d..76dde68c23 100644
--- a/src/compiler/glsl/lower_instructions.cpp
+++ b/src/compiler/glsl/lower_instructions.cpp
@@ -43,6 +43,7 @@
  * - BORROW_TO_ARITH
  * - SAT_TO_CLAMP
  * - DOPS_TO_DFRAC
+ * - MIN_MAX_TO_LESS
  *
  * SUB_TO_ADD_NEG:
  * ---------------
@@ -115,6 +116,12 @@
  * DOPS_TO_DFRAC:
  * --------------
  * Converts double trunc, ceil, floor, round to fract
+ *
+ * MIN_MAX_TO_LESS:
+ * ----------------
+ * Converts min, max into less.
+ * min(x,y) = less(x,y) ? x, y;
+ * max(x,y) = less(x,y) ? y, x;
  */
 
 #include "c99_math.h"
@@ -169,6 +176,7 @@ private:
    void find_msb_to_float_cast(ir_expression *ir);
    void imul_high_to_mul(ir_expression *ir);
    void sqrt_to_abs_sqrt(ir_expression *ir);
+   void min_to_less(ir_expression *ir);
 
    ir_expression *_carry(operand a, operand b);
 };
@@ -1623,6 +1631,20 @@ lower_instructions_visitor::sqrt_to_abs_sqrt(ir_expression *ir)
    this->progress = true;
 }
 
+void
+lower_instructions_visitor::min_to_less(ir_expression *ir)
+{
+   ir_rvalue *x_clone = ir->operands[0]->clone(ir, NULL);
+   ir_rvalue *y_clone = ir->operands[1]->clone(ir, NULL);
+   ir->operation = ir_triop_csel;
+   ir->init_num_operands();
+   ir->operands[0] = less(ir->operands[0], ir->operands[1]);
+   ir->operands[1] = x_clone;
+   ir->operands[2] = y_clone;
+
+   this->progress = true;
+}
+
 ir_visitor_status
 lower_instructions_visitor::visit_leave(ir_expression *ir)
 {
@@ -1766,6 +1788,12 @@ lower_instructions_visitor::visit_leave(ir_expression *ir)
          sqrt_to_abs_sqrt(ir);
       break;
 
+   case ir_binop_min:
+      if (lowering(MIN_MAX_TO_LESS) &&
+          ir->type->is_double() && ir->type->is_scalar())
+         min_to_less(ir);
+      break;
+
    default:
       return visit_continue;
    }
diff --git a/src/mesa/state_tracker/st_glsl_to_tgsi.cpp b/src/mesa/state_tracker/st_glsl_to_tgsi.cpp
index dc88a881f6..ef3a15932a 100644
--- a/src/mesa/state_tracker/st_glsl_to_tgsi.cpp
+++ b/src/mesa/state_tracker/st_glsl_to_tgsi.cpp
@@ -7058,6 +7058,7 @@ st_link_shader(struct gl_context *ctx, struct gl_shader_program *prog)
        */
       if (!pscreen->get_param(pscreen, PIPE_CAP_DOUBLES) &&
             ctx->Const.GLSLVersion >= 130) {
+         lower_instructions(ir, MIN_MAX_TO_LESS);
          unsigned lower_inst = ABS64 |
                                NEG64 |
                                SIGN64 |
-- 
2.14.1



More information about the mesa-dev mailing list