[Mesa-dev] [PATCH 3/4] glsl: Merge if-simplification and conditional discard opt

Thomas Helland thomashelland90 at gmail.com
Wed May 17 19:15:19 UTC 2017


The conditional discard pass is really just a form of if-simplification.
So there is no reason why we can not just merge the two, and avoid
running the visitor two times.

V2: Add back in the wrongly removed optimization
---
 src/compiler/Makefile.sources                 |  1 -
 src/compiler/glsl/glsl_parser_extras.cpp      |  1 -
 src/compiler/glsl/ir_optimization.h           |  1 -
 src/compiler/glsl/opt_conditional_discard.cpp | 99 ---------------------------
 src/compiler/glsl/opt_if_simplification.cpp   | 39 +++++++++++
 5 files changed, 39 insertions(+), 102 deletions(-)
 delete mode 100644 src/compiler/glsl/opt_conditional_discard.cpp

diff --git a/src/compiler/Makefile.sources b/src/compiler/Makefile.sources
index 611362ed73..964f454cca 100644
--- a/src/compiler/Makefile.sources
+++ b/src/compiler/Makefile.sources
@@ -114,7 +114,6 @@ LIBGLSL_FILES = \
 	glsl/lower_ubo_reference.cpp \
 	glsl/opt_algebraic.cpp \
 	glsl/opt_array_splitting.cpp \
-	glsl/opt_conditional_discard.cpp \
 	glsl/opt_constant_folding.cpp \
 	glsl/opt_constant_propagation.cpp \
 	glsl/opt_constant_variable.cpp \
diff --git a/src/compiler/glsl/glsl_parser_extras.cpp b/src/compiler/glsl/glsl_parser_extras.cpp
index 218ce6949a..220c3a94ed 100644
--- a/src/compiler/glsl/glsl_parser_extras.cpp
+++ b/src/compiler/glsl/glsl_parser_extras.cpp
@@ -2176,7 +2176,6 @@ do_common_optimization(exec_list *ir, bool linked,
    }
    propagate_invariance(ir);
    OPT(do_if_simplification, ir);
-   OPT(opt_conditional_discard, ir);
    OPT(do_copy_propagation, ir);
    OPT(do_copy_propagation_elements, ir);
 
diff --git a/src/compiler/glsl/ir_optimization.h b/src/compiler/glsl/ir_optimization.h
index e9e705a1cc..7ffb47696c 100644
--- a/src/compiler/glsl/ir_optimization.h
+++ b/src/compiler/glsl/ir_optimization.h
@@ -96,7 +96,6 @@ bool ir_constant_fold(ir_rvalue **rvalue);
 bool do_rebalance_tree(exec_list *instructions);
 bool do_algebraic(exec_list *instructions, bool native_integers,
                   const struct gl_shader_compiler_options *options);
-bool opt_conditional_discard(exec_list *instructions);
 bool do_constant_folding(exec_list *instructions);
 bool do_constant_variable(exec_list *instructions);
 bool do_constant_variable_unlinked(exec_list *instructions);
diff --git a/src/compiler/glsl/opt_conditional_discard.cpp b/src/compiler/glsl/opt_conditional_discard.cpp
deleted file mode 100644
index d7cb2069ed..0000000000
--- a/src/compiler/glsl/opt_conditional_discard.cpp
+++ /dev/null
@@ -1,99 +0,0 @@
-/*
- * Copyright © 2014 Intel Corporation
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- */
-
-/**
- * \file opt_conditional_discard.cpp
- *
- * Replace
- *
- *    if (cond) discard;
- *
- * with
- *
- *    (discard <condition>)
- */
-
-#include "compiler/glsl_types.h"
-#include "ir.h"
-
-namespace {
-
-class opt_conditional_discard_visitor : public ir_hierarchical_visitor {
-public:
-   opt_conditional_discard_visitor()
-   {
-      progress = false;
-   }
-
-   ir_visitor_status visit_leave(ir_if *);
-   ir_visitor_status visit_enter(ir_assignment *);
-
-   bool progress;
-};
-
-} /* anonymous namespace */
-
-/* We only care about the top level "if" instructions, so don't
- * descend into expressions.
- */
-ir_visitor_status
-opt_conditional_discard_visitor::visit_enter(ir_assignment *ir)
-{
-   (void) ir;
-   return visit_continue_with_parent;
-}
-
-bool
-opt_conditional_discard(exec_list *instructions)
-{
-   opt_conditional_discard_visitor v;
-   v.run(instructions);
-   return v.progress;
-}
-
-ir_visitor_status
-opt_conditional_discard_visitor::visit_leave(ir_if *ir)
-{
-   /* Look for "if (...) discard" with no else clause or extra statements. */
-   if (ir->then_instructions.is_empty() ||
-       !ir->then_instructions.get_head_raw()->next->is_tail_sentinel() ||
-       !((ir_instruction *) ir->then_instructions.get_head_raw())->as_discard() ||
-       !ir->else_instructions.is_empty())
-      return visit_continue;
-
-   /* Move the condition and replace the ir_if with the ir_discard. */
-   ir_discard *discard = (ir_discard *) ir->then_instructions.get_head_raw();
-   if (!discard->condition)
-      discard->condition = ir->condition;
-   else {
-      void *ctx = ralloc_parent(ir);
-      discard->condition = new(ctx) ir_expression(ir_binop_logic_and,
-                                                  ir->condition,
-                                                  discard->condition);
-   }
-   ir->replace_with(discard);
-
-   progress = true;
-
-   return visit_continue;
-}
diff --git a/src/compiler/glsl/opt_if_simplification.cpp b/src/compiler/glsl/opt_if_simplification.cpp
index 05159319ba..bcdda1061a 100644
--- a/src/compiler/glsl/opt_if_simplification.cpp
+++ b/src/compiler/glsl/opt_if_simplification.cpp
@@ -70,6 +70,40 @@ do_if_simplification(exec_list *instructions)
    return v.made_progress;
 }
 
+/**
+ *
+ * Replace
+ *
+ *    if (cond) discard;
+ *
+ * with
+ *
+ *    (discard <condition>)
+ */
+static bool
+opt_conditional_discard(ir_if *ir)
+{
+   /* Look for "if (...) discard" with no else clause or extra statements. */
+   if (ir->then_instructions.is_empty() ||
+       !ir->then_instructions.get_head_raw()->next->is_tail_sentinel() ||
+       !((ir_instruction *) ir->then_instructions.get_head_raw())->as_discard() ||
+       !ir->else_instructions.is_empty())
+      return visit_continue;
+
+   /* Move the condition and replace the ir_if with the ir_discard. */
+   ir_discard *discard = (ir_discard *) ir->then_instructions.get_head_raw();
+   if (!discard->condition)
+      discard->condition = ir->condition;
+   else {
+      void *ctx = ralloc_parent(ir);
+      discard->condition = new(ctx) ir_expression(ir_binop_logic_and,
+                                                  ir->condition,
+                                                  discard->condition);
+   }
+   ir->replace_with(discard);
+
+   return true;
+}
 
 /**
  * 
@@ -116,6 +150,11 @@ ir_if_simplification_visitor::visit_leave(ir_if *ir)
    if (opt_flatten_nested_if_blocks(ir))
       this->made_progress = true;
 
+   if (opt_conditional_discard(ir)) {
+      this->made_progress = true;
+      return visit_continue;
+   }
+
    /* If the if statement has nothing on either side, remove it. */
    if (ir->then_instructions.is_empty() &&
        ir->else_instructions.is_empty()) {
-- 
2.12.2



More information about the mesa-dev mailing list