glsl: Add ir_demote
authorCaio Marcelo de Oliveira Filho <caio.oliveira@intel.com>
Fri, 20 Sep 2019 16:27:00 +0000 (09:27 -0700)
committerCaio Marcelo de Oliveira Filho <caio.oliveira@intel.com>
Mon, 30 Sep 2019 19:44:30 +0000 (12:44 -0700)
To represent the new `demote` keyword when using
EXT_demote_to_helper_invocation extension.  Most of the changes are to
include it in the visitors.

Demote is not considered a control flow, so also include an empty
visit member function in ir_control_flow_visitor.

Only NIR actually supports `demote`, so assert the translations for
TGSI and Mesa's gl_program -- since the demote is not expected to
appear for those.

Reviewed-by: Kenneth Graunke <kenneth@whitecape.org>
src/compiler/glsl/glsl_to_nir.cpp
src/compiler/glsl/ir.h
src/compiler/glsl/ir_clone.cpp
src/compiler/glsl/ir_hierarchical_visitor.cpp
src/compiler/glsl/ir_hierarchical_visitor.h
src/compiler/glsl/ir_hv_accept.cpp
src/compiler/glsl/ir_print_visitor.cpp
src/compiler/glsl/ir_print_visitor.h
src/compiler/glsl/ir_visitor.h
src/mesa/program/ir_to_mesa.cpp
src/mesa/state_tracker/st_glsl_to_tgsi.cpp

index 1e096a66c203dffddf26b04f35067eaba6681ad8..883cfb57601300f79e311302ba097d21c86c7fb5 100644 (file)
@@ -63,6 +63,7 @@ public:
    virtual void visit(ir_loop *);
    virtual void visit(ir_if *);
    virtual void visit(ir_discard *);
+   virtual void visit(ir_demote *);
    virtual void visit(ir_loop_jump *);
    virtual void visit(ir_return *);
    virtual void visit(ir_call *);
@@ -775,6 +776,15 @@ nir_visitor::visit(ir_discard *ir)
    nir_builder_instr_insert(&b, &discard->instr);
 }
 
+void
+nir_visitor::visit(ir_demote *ir)
+{
+   nir_intrinsic_instr *demote =
+      nir_intrinsic_instr_create(this->shader, nir_intrinsic_demote);
+
+   nir_builder_instr_insert(&b, &demote->instr);
+}
+
 void
 nir_visitor::visit(ir_emit_vertex *ir)
 {
index ba831f2c1ed1f1feeb07c1b4db235ebe9ddb9e8b..e3c28bbb2b8b277c1d7e3d66182ca073f40d74d2 100644 (file)
@@ -74,6 +74,7 @@ enum ir_node_type {
    ir_type_loop_jump,
    ir_type_return,
    ir_type_discard,
+   ir_type_demote,
    ir_type_emit_vertex,
    ir_type_end_primitive,
    ir_type_barrier,
@@ -1804,6 +1805,28 @@ public:
 /*@}*/
 
 
+/**
+ * IR instruction representing demote statements from
+ * GL_EXT_demote_to_helper_invocation.
+ */
+class ir_demote : public ir_instruction {
+public:
+   ir_demote()
+      : ir_instruction(ir_type_demote)
+   {
+   }
+
+   virtual ir_demote *clone(void *mem_ctx, struct hash_table *ht) const;
+
+   virtual void accept(ir_visitor *v)
+   {
+      v->visit(this);
+   }
+
+   virtual ir_visitor_status accept(ir_hierarchical_visitor *);
+};
+
+
 /**
  * Texture sampling opcodes used in ir_texture
  */
index c492fdbb3d0254d8a228d1132db31f3a986f6a12..eb24ffe9be2e3faf5041c6d21ec15e3412ea1e34 100644 (file)
@@ -102,6 +102,12 @@ ir_discard::clone(void *mem_ctx, struct hash_table *ht) const
    return new(mem_ctx) ir_discard(new_condition);
 }
 
+ir_demote *
+ir_demote::clone(void *mem_ctx, struct hash_table *ht) const
+{
+   return new(mem_ctx) ir_demote();
+}
+
 ir_loop_jump *
 ir_loop_jump::clone(void *mem_ctx, struct hash_table *ht) const
 {
index 1d23a776643dc12dbd60bb9c4cc3661a44c54657..8fcf48e2bb418543e4764911027809818c726574 100644 (file)
@@ -304,6 +304,24 @@ ir_hierarchical_visitor::visit_leave(ir_discard *ir)
    return visit_continue;
 }
 
+ir_visitor_status
+ir_hierarchical_visitor::visit_enter(ir_demote *ir)
+{
+   if (this->callback_enter != NULL)
+      this->callback_enter(ir, this->data_enter);
+
+   return visit_continue;
+}
+
+ir_visitor_status
+ir_hierarchical_visitor::visit_leave(ir_demote *ir)
+{
+   if (this->callback_leave != NULL)
+      this->callback_leave(ir, this->data_leave);
+
+   return visit_continue;
+}
+
 ir_visitor_status
 ir_hierarchical_visitor::visit_enter(ir_if *ir)
 {
index 5f5acd041b8d98b4cf10351b64daacb13f6c85e9..e10bb7c60db57491d2b18ca45ec5466f8b3f3046 100644 (file)
@@ -133,6 +133,8 @@ public:
    virtual ir_visitor_status visit_leave(class ir_return *);
    virtual ir_visitor_status visit_enter(class ir_discard *);
    virtual ir_visitor_status visit_leave(class ir_discard *);
+   virtual ir_visitor_status visit_enter(class ir_demote *);
+   virtual ir_visitor_status visit_leave(class ir_demote *);
    virtual ir_visitor_status visit_enter(class ir_if *);
    virtual ir_visitor_status visit_leave(class ir_if *);
    virtual ir_visitor_status visit_enter(class ir_emit_vertex *);
index f04a5b6fd192b62b9f116644449940d43dce94ef..6e5e25378e1bb998ffc1901ac885d2066d3885f9 100644 (file)
@@ -378,6 +378,18 @@ ir_discard::accept(ir_hierarchical_visitor *v)
 }
 
 
+ir_visitor_status
+ir_demote::accept(ir_hierarchical_visitor *v)
+{
+   ir_visitor_status s = v->visit_enter(this);
+
+   if (s != visit_continue)
+      return (s == visit_continue_with_parent) ? visit_continue : s;
+
+   return v->visit_leave(this);
+}
+
+
 ir_visitor_status
 ir_if::accept(ir_hierarchical_visitor *v)
 {
index b3a62ce38bd3e0139ebc5998195e1d51eeaa49bc..2eaebb21d479b5677d4de170b208fb469a884ca7 100644 (file)
@@ -564,6 +564,13 @@ ir_print_visitor::visit(ir_discard *ir)
 }
 
 
+void
+ir_print_visitor::visit(ir_demote *ir)
+{
+   fprintf(f, "(demote)");
+}
+
+
 void
 ir_print_visitor::visit(ir_if *ir)
 {
index 652cd90bc008acd1d721c92c55eb30974d66f624..a71e1aba8865d7159f1c0a84c75f7018d3288ce5 100644 (file)
@@ -63,6 +63,7 @@ public:
    virtual void visit(ir_call *);
    virtual void visit(ir_return *);
    virtual void visit(ir_discard *);
+   virtual void visit(ir_demote *);
    virtual void visit(ir_if *);
    virtual void visit(ir_loop *);
    virtual void visit(ir_loop_jump *);
index 117b5bc6ae88ecd6c8713d27c6c7a7005777de3b..b06e310ffd78f75648af8aaeb82ec5b8fb5ce306 100644 (file)
@@ -59,6 +59,7 @@ public:
    virtual void visit(class ir_call *) = 0;
    virtual void visit(class ir_return *) = 0;
    virtual void visit(class ir_discard *) = 0;
+   virtual void visit(class ir_demote *) = 0;
    virtual void visit(class ir_if *) = 0;
    virtual void visit(class ir_loop *) = 0;
    virtual void visit(class ir_loop_jump *) = 0;
@@ -83,6 +84,7 @@ public:
    virtual void visit(class ir_assignment *) {}
    virtual void visit(class ir_constant *) {}
    virtual void visit(class ir_call *) {}
+   virtual void visit(class ir_demote *) {}
    virtual void visit(class ir_emit_vertex *) {}
    virtual void visit(class ir_end_primitive *) {}
    virtual void visit(class ir_barrier *) {}
index 777fd168c7ec579ccb94330a70c54e9682732fe2..679b46ba7eee4fa2077580e54b78351842795420 100644 (file)
@@ -252,6 +252,7 @@ public:
    virtual void visit(ir_call *);
    virtual void visit(ir_return *);
    virtual void visit(ir_discard *);
+   virtual void visit(ir_demote *);
    virtual void visit(ir_texture *);
    virtual void visit(ir_if *);
    virtual void visit(ir_emit_vertex *);
@@ -2201,6 +2202,12 @@ ir_to_mesa_visitor::visit(ir_discard *ir)
    emit(ir, OPCODE_KIL, undef_dst, this->result);
 }
 
+void
+ir_to_mesa_visitor::visit(ir_demote *ir)
+{
+   assert(!"demote statement unsupported");
+}
+
 void
 ir_to_mesa_visitor::visit(ir_if *ir)
 {
index 9b982569490ce1b529f5b2ec472be07f8e3bb396..b0afe2d23850dbf4174b5253bba1b4864a51ad6b 100644 (file)
@@ -284,6 +284,7 @@ public:
    virtual void visit(ir_call *);
    virtual void visit(ir_return *);
    virtual void visit(ir_discard *);
+   virtual void visit(ir_demote *);
    virtual void visit(ir_texture *);
    virtual void visit(ir_if *);
    virtual void visit(ir_emit_vertex *);
@@ -4626,6 +4627,12 @@ glsl_to_tgsi_visitor::visit(ir_discard *ir)
    }
 }
 
+void
+glsl_to_tgsi_visitor::visit(ir_demote *ir)
+{
+   assert(!"demote statement unsupported");
+}
+
 void
 glsl_to_tgsi_visitor::visit(ir_if *ir)
 {