i965/fs Add a wm_prog_data bit for has_side_effects
authorJason Ekstrand <jason.ekstrand@intel.com>
Thu, 2 Jun 2016 01:46:30 +0000 (18:46 -0700)
committerJason Ekstrand <jason.ekstrand@intel.com>
Sat, 4 Jun 2016 02:29:28 +0000 (19:29 -0700)
This is more accurate than calling
_mesa_active_fragment_shader_has_side_effects because it looks at whether
or not the SSBOs, images, or atomic buffers are actually written rather
than just existing in the program.

Signed-off-by: Jason Ekstrand <jason@jlekstrand.net>
Reviewed-by: Kenneth Graunke <kenneth@whitecape.org>
Cc: "12.0" <mesa-stable@lists.freedesktop.org>
src/mesa/drivers/dri/i965/brw_compiler.h
src/mesa/drivers/dri/i965/brw_fs_nir.cpp

index 6e6d20c7d3819714362a7528da7e6e5f3eb3c17f..f55b7f37ffeac20ae230316f0c38db6c9c55064e 100644 (file)
@@ -402,6 +402,7 @@ struct brw_wm_prog_data {
    bool uses_src_depth;
    bool uses_src_w;
    bool uses_sample_mask;
+   bool has_side_effects;
    bool pulls_bary;
 
    /**
index 7fc43b5061dbdc1a7b8f64221512c7e19ce2d069..a4e5559a369793fe403c88b137abba6259990898 100644 (file)
@@ -3331,6 +3331,10 @@ fs_visitor::nir_emit_intrinsic(const fs_builder &bld, nir_intrinsic_instr *instr
    case nir_intrinsic_atomic_counter_inc:
    case nir_intrinsic_atomic_counter_dec:
    case nir_intrinsic_atomic_counter_read: {
+      if (stage == MESA_SHADER_FRAGMENT &&
+          instr->intrinsic != nir_intrinsic_atomic_counter_read)
+         ((struct brw_wm_prog_data *)prog_data)->has_side_effects = true;
+
       /* Get the arguments of the atomic intrinsic. */
       const fs_reg offset = get_nir_src(instr->src[0]);
       const unsigned surface = (stage_prog_data->binding_table.abo_start +
@@ -3377,6 +3381,10 @@ fs_visitor::nir_emit_intrinsic(const fs_builder &bld, nir_intrinsic_instr *instr
    case nir_intrinsic_image_atomic_comp_swap: {
       using namespace image_access;
 
+      if (stage == MESA_SHADER_FRAGMENT &&
+          instr->intrinsic != nir_intrinsic_image_load)
+         ((struct brw_wm_prog_data *)prog_data)->has_side_effects = true;
+
       /* Get the referenced image variable and type. */
       const nir_variable *var = instr->variables[0]->var;
       const glsl_type *type = var->type->without_array();
@@ -3690,6 +3698,9 @@ fs_visitor::nir_emit_intrinsic(const fs_builder &bld, nir_intrinsic_instr *instr
    case nir_intrinsic_store_ssbo: {
       assert(devinfo->gen >= 7);
 
+      if (stage == MESA_SHADER_FRAGMENT)
+         ((struct brw_wm_prog_data *)prog_data)->has_side_effects = true;
+
       /* Block index */
       fs_reg surf_index;
       nir_const_value *const_uniform_block =
@@ -3893,6 +3904,9 @@ void
 fs_visitor::nir_emit_ssbo_atomic(const fs_builder &bld,
                                  int op, nir_intrinsic_instr *instr)
 {
+   if (stage == MESA_SHADER_FRAGMENT)
+      ((struct brw_wm_prog_data *)prog_data)->has_side_effects = true;
+
    fs_reg dest;
    if (nir_intrinsic_infos[instr->intrinsic].has_dest)
       dest = get_nir_dest(instr->dest);