<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Fri, Oct 6, 2017 at 6:31 AM, Lionel Landwerlin <span dir="ltr"><<a href="mailto:lionel.g.landwerlin@intel.com" target="_blank">lionel.g.landwerlin@intel.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Signed-off-by: Lionel Landwerlin <<a href="mailto:lionel.g.landwerlin@intel.com">lionel.g.landwerlin@intel.com</a><wbr>><br>
Reviewed-by: Jason Ekstrand <<a href="mailto:jason@jlekstrand.net">jason@jlekstrand.net</a>><br>
---<br>
 src/intel/vulkan/anv_<wbr>descriptor_set.c            |  13 +++<br>
 src/intel/vulkan/anv_nir_<wbr>apply_pipeline_layout.c | 113 ++++++++++++++++++-----<br>
 src/intel/vulkan/anv_private.h                   |   7 ++<br>
 src/intel/vulkan/genX_state.c                    |   2 +<br>
 4 files changed, 113 insertions(+), 22 deletions(-)<br>
<br>
diff --git a/src/intel/vulkan/anv_<wbr>descriptor_set.c b/src/intel/vulkan/anv_<wbr>descriptor_set.c<br>
index 84077982307..629c041eedf 100644<br>
--- a/src/intel/vulkan/anv_<wbr>descriptor_set.c<br>
+++ b/src/intel/vulkan/anv_<wbr>descriptor_set.c<br>
@@ -400,6 +400,19 @@ anv_descriptor_set_layout_<wbr>size(const struct anv_descriptor_set_layout *layout)<br>
       layout->buffer_count * sizeof(struct anv_buffer_view);<br>
 }<br>
<br>
+size_t<br>
+anv_descriptor_set_binding_<wbr>layout_get_hw_size(const struct anv_descriptor_set_binding_<wbr>layout *binding)<br>
+{<br>
+   if (!binding->immutable_samplers)<br>
+      return binding->array_size;<br>
+<br>
+   uint32_t total_plane_count = 0;<br>
+   for (uint32_t i = 0; i < binding->array_size; i++)<br>
+      total_plane_count += binding->immutable_samplers[i]<wbr>->n_planes;<br>
+<br>
+   return total_plane_count;<br>
+}<br>
+<br>
 struct surface_state_free_list_entry {<br>
    void *next;<br>
    struct anv_state state;<br>
diff --git a/src/intel/vulkan/anv_nir_<wbr>apply_pipeline_layout.c b/src/intel/vulkan/anv_nir_<wbr>apply_pipeline_layout.c<br>
index 67bcf5e29ef..02323fba31a 100644<br>
--- a/src/intel/vulkan/anv_nir_<wbr>apply_pipeline_layout.c<br>
+++ b/src/intel/vulkan/anv_nir_<wbr>apply_pipeline_layout.c<br>
@@ -131,7 +131,7 @@ lower_res_index_intrinsic(nir_<wbr>intrinsic_instr *intrin,<br>
 static void<br>
 lower_tex_deref(nir_tex_instr *tex, nir_deref_var *deref,<br>
                 unsigned *const_index, unsigned array_size,<br>
-                nir_tex_src_type src_type,<br>
+                nir_tex_src_type src_type, bool allow_indirect,<br>
                 struct apply_pipeline_layout_state *state)<br>
 {<br>
    nir_builder *b = &state->builder;<br>
@@ -141,6 +141,15 @@ lower_tex_deref(nir_tex_instr *tex, nir_deref_var *deref,<br>
       nir_deref_array *deref_array = nir_deref_as_array(deref-><wbr>deref.child);<br>
<br>
       if (deref_array->deref_array_type == nir_deref_array_type_indirect) {<br>
+         /* From VK_KHR_sampler_ycbcr_<wbr>conversion:<br>
+          *<br>
+          * If sampler Y’CBCR conversion is enabled, the combined image<br>
+          * sampler must be indexed only by constant integral expressions when<br>
+          * aggregated into arrays in shader code, irrespective of the<br>
+          * shaderSampledImageArrayDynamic<wbr>Indexing feature.<br>
+          */<br>
+         assert(allow_indirect);<br>
+<br>
          nir_ssa_def *index =<br>
             nir_iadd(b, nir_imm_int(b, deref_array->base_offset),<br>
                         nir_ssa_for_src(b, deref_array->indirect, 1));<br>
@@ -186,6 +195,46 @@ cleanup_tex_deref(nir_tex_<wbr>instr *tex, nir_deref_var *deref)<br>
    nir_instr_rewrite_src(&tex-><wbr>instr, &deref_array->indirect, NIR_SRC_INIT);<br>
 }<br>
<br>
+static bool<br>
+has_tex_src_plane(nir_tex_<wbr>instr *tex)<br>
+{<br>
+   for (unsigned i = 0; i < tex->num_srcs; i++) {<br>
+      if (tex->src[i].src_type == nir_tex_src_plane)<br>
+         return true;<br>
+   }<br>
+<br>
+   return false;<br>
+}<br>
+<br>
+static uint32_t<br>
+extract_tex_src_plane(nir_<wbr>tex_instr *tex)<br>
+{<br>
+   nir_tex_src *new_srcs = rzalloc_array(tex, nir_tex_src, tex->num_srcs - 1);<br>
+   unsigned plane = 0;<br>
+<br>
+   for (unsigned i = 0, w = 0; i < tex->num_srcs; i++) {<br>
+      if (tex->src[i].src_type == nir_tex_src_plane) {<br>
+         nir_const_value *const_plane =<br>
+            nir_src_as_const_value(tex-><wbr>src[i].src);<br>
+<br>
+         /* Our color conversion lowering pass should only ever insert<br>
+          * constants. */<br>
+         assert(const_plane);<br>
+         plane = const_plane->u32[0];<br></blockquote><div><br></div><div>As I mentioned on IRC today, we need to do</div><div><br></div><div>nir_instr_rewrite_src(&tex->instr, &tex->src[i].src, NIR_SRC_INIT);</div><div><br></div><div>here to get rid of the reference that he source carries to the load_const SSA def.  Sorry that's not terribly intuitive.<br></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+      } else {<br>
+         new_srcs[w].src_type = tex->src[i].src_type;<br>
+         nir_instr_move_src(&tex-><wbr>instr, &new_srcs[w].src, &tex->src[i].src);<br>
+         w++;<br>
+      }<br>
+   }<br>
+<br>
+   ralloc_free(tex->src);<br>
+   tex->src = new_srcs;<br>
+   tex->num_srcs--;<br>
+<br>
+   return plane;<br>
+}<br>
+<br>
 static void<br>
 lower_tex(nir_tex_instr *tex, struct apply_pipeline_layout_state *state)<br>
 {<br>
@@ -198,9 +247,13 @@ lower_tex(nir_tex_instr *tex, struct apply_pipeline_layout_state *state)<br>
    unsigned binding = tex->texture->var->data.<wbr>binding;<br>
    unsigned array_size =<br>
       state->layout->set[set].<wbr>layout->binding[binding].<wbr>array_size;<br>
+   bool has_plane = has_tex_src_plane(tex);<br>
+   unsigned plane = has_plane ? extract_tex_src_plane(tex) : 0;<br>
+<br>
    tex->texture_index = state->set[set].surface_<wbr>offsets[binding];<br>
    lower_tex_deref(tex, tex->texture, &tex->texture_index, array_size,<br>
-                   nir_tex_src_texture_offset, state);<br>
+                   nir_tex_src_texture_offset, !has_plane, state);<br>
+   tex->texture_index += plane;<br>
<br>
    if (tex->sampler) {<br>
       unsigned set = tex->sampler->var->data.<wbr>descriptor_set;<br>
@@ -209,7 +262,8 @@ lower_tex(nir_tex_instr *tex, struct apply_pipeline_layout_state *state)<br>
          state->layout->set[set].<wbr>layout->binding[binding].<wbr>array_size;<br>
       tex->sampler_index = state->set[set].sampler_<wbr>offsets[binding];<br>
       lower_tex_deref(tex, tex->sampler, &tex->sampler_index, array_size,<br>
-                      nir_tex_src_sampler_offset, state);<br>
+                      nir_tex_src_sampler_offset, !has_plane, state);<br>
+      tex->sampler_index += plane;<br>
    }<br>
<br>
    /* The backend only ever uses this to mark used surfaces.  We don't care<br>
@@ -299,10 +353,14 @@ anv_nir_apply_pipeline_layout(<wbr>struct anv_pipeline *pipeline,<br>
       BITSET_WORD b, _tmp;<br>
       BITSET_FOREACH_SET(b, _tmp, state.set[set].used,<br>
                          set_layout->binding_count) {<br>
-         if (set_layout->binding[b].stage[<wbr>shader->stage].surface_index >= 0)<br>
-            map->surface_count += set_layout->binding[b].array_<wbr>size;<br>
-         if (set_layout->binding[b].stage[<wbr>shader->stage].sampler_index >= 0)<br>
-            map->sampler_count += set_layout->binding[b].array_<wbr>size;<br>
+         if (set_layout->binding[b].stage[<wbr>shader->stage].surface_index >= 0) {<br>
+            map->surface_count +=<br>
+               anv_descriptor_set_binding_<wbr>layout_get_hw_size(&set_<wbr>layout->binding[b]);<br>
+         }<br>
+         if (set_layout->binding[b].stage[<wbr>shader->stage].sampler_index >= 0) {<br>
+            map->sampler_count +=<br>
+               anv_descriptor_set_binding_<wbr>layout_get_hw_size(&set_<wbr>layout->binding[b]);<br>
+         }<br>
          if (set_layout->binding[b].stage[<wbr>shader->stage].image_index >= 0)<br>
             map->image_count += set_layout->binding[b].array_<wbr>size;<br>
       }<br>
@@ -317,31 +375,42 @@ anv_nir_apply_pipeline_layout(<wbr>struct anv_pipeline *pipeline,<br>
       BITSET_WORD b, _tmp;<br>
       BITSET_FOREACH_SET(b, _tmp, state.set[set].used,<br>
                          set_layout->binding_count) {<br>
-         unsigned array_size = set_layout->binding[b].array_<wbr>size;<br>
+         struct anv_descriptor_set_binding_<wbr>layout *binding =<br>
+            &set_layout->binding[b];<br>
<br>
-         if (set_layout->binding[b].stage[<wbr>shader->stage].surface_index >= 0) {<br>
+         if (binding->stage[shader->stage]<wbr>.surface_index >= 0) {<br>
             state.set[set].surface_<wbr>offsets[b] = surface;<br>
-            for (unsigned i = 0; i < array_size; i++) {<br>
-               map->surface_to_descriptor[<wbr>surface + i].set = set;<br>
-               map->surface_to_descriptor[<wbr>surface + i].binding = b;<br>
-               map->surface_to_descriptor[<wbr>surface + i].index = i;<br>
+            struct anv_sampler **samplers = binding->immutable_samplers;<br>
+            for (unsigned i = 0; i < binding->array_size; i++) {<br>
+               uint8_t planes = samplers ? samplers[i]->n_planes : 1;<br>
+               for (uint8_t p = 0; p < planes; p++) {<br>
+                  map->surface_to_descriptor[<wbr>surface].set = set;<br>
+                  map->surface_to_descriptor[<wbr>surface].binding = b;<br>
+                  map->surface_to_descriptor[<wbr>surface].index = i;<br>
+                  map->surface_to_descriptor[<wbr>surface].plane = p;<br>
+                  surface++;<br>
+               }<br>
             }<br>
-            surface += array_size;<br>
          }<br>
<br>
-         if (set_layout->binding[b].stage[<wbr>shader->stage].sampler_index >= 0) {<br>
+         if (binding->stage[shader->stage]<wbr>.sampler_index >= 0) {<br>
             state.set[set].sampler_<wbr>offsets[b] = sampler;<br>
-            for (unsigned i = 0; i < array_size; i++) {<br>
-               map->sampler_to_descriptor[<wbr>sampler + i].set = set;<br>
-               map->sampler_to_descriptor[<wbr>sampler + i].binding = b;<br>
-               map->sampler_to_descriptor[<wbr>sampler + i].index = i;<br>
+            struct anv_sampler **samplers = binding->immutable_samplers;<br>
+            for (unsigned i = 0; i < binding->array_size; i++) {<br>
+               uint8_t planes = samplers ? samplers[i]->n_planes : 1;<br>
+               for (uint8_t p = 0; p < planes; p++) {<br>
+                  map->sampler_to_descriptor[<wbr>sampler].set = set;<br>
+                  map->sampler_to_descriptor[<wbr>sampler].binding = b;<br>
+                  map->sampler_to_descriptor[<wbr>sampler].index = i;<br>
+                  map->sampler_to_descriptor[<wbr>sampler].plane = p;<br>
+                  sampler++;<br>
+               }<br>
             }<br>
-            sampler += array_size;<br>
          }<br>
<br>
-         if (set_layout->binding[b].stage[<wbr>shader->stage].image_index >= 0) {<br>
+         if (binding->stage[shader->stage]<wbr>.image_index >= 0) {<br>
             state.set[set].image_offsets[<wbr>b] = image;<br>
-            image += array_size;<br>
+            image += binding->array_size;<br>
          }<br>
       }<br>
    }<br>
diff --git a/src/intel/vulkan/anv_<wbr>private.h b/src/intel/vulkan/anv_<wbr>private.h<br>
index 36aa86141fc..ff1b1cc8a80 100644<br>
--- a/src/intel/vulkan/anv_<wbr>private.h<br>
+++ b/src/intel/vulkan/anv_<wbr>private.h<br>
@@ -1323,6 +1323,9 @@ struct anv_descriptor_update_template {<br>
    struct anv_descriptor_template_entry entries[0];<br>
 };<br>
<br>
+size_t<br>
+anv_descriptor_set_binding_<wbr>layout_get_hw_size(const struct anv_descriptor_set_binding_<wbr>layout *binding);<br>
+<br>
 size_t<br>
 anv_descriptor_set_layout_<wbr>size(const struct anv_descriptor_set_layout *layout);<br>
<br>
@@ -1385,6 +1388,9 @@ struct anv_pipeline_binding {<br>
    /* Index in the binding */<br>
    uint32_t index;<br>
<br>
+   /* Plane in the binding index */<br>
+   uint8_t plane;<br>
+<br>
    /* Input attachment index (relative to the subpass) */<br>
    uint8_t input_attachment_index;<br>
<br>
@@ -2540,6 +2546,7 @@ void anv_fill_buffer_surface_state(<wbr>struct anv_device *device,<br>
<br>
 struct anv_sampler {<br>
    uint32_t state[4];<br>
+   uint32_t n_planes;<br>
 };<br>
<br>
 struct anv_framebuffer {<br>
diff --git a/src/intel/vulkan/genX_state.<wbr>c b/src/intel/vulkan/genX_state.<wbr>c<br>
index d016aff4a54..81570825a54 100644<br>
--- a/src/intel/vulkan/genX_state.<wbr>c<br>
+++ b/src/intel/vulkan/genX_state.<wbr>c<br>
@@ -171,6 +171,8 @@ VkResult genX(CreateSampler)(<br>
    if (!sampler)<br>
       return vk_error(VK_ERROR_OUT_OF_HOST_<wbr>MEMORY);<br>
<br>
+   sampler->n_planes = 1;<br>
+<br>
    uint32_t border_color_offset = device->border_colors.offset +<br>
                                   pCreateInfo->borderColor * 64;<br>
<span class="HOEnZb"><font color="#888888"><br>
--<br>
2.14.2<br>
<br>
______________________________<wbr>_________________<br>
mesa-dev mailing list<br>
<a href="mailto:mesa-dev@lists.freedesktop.org">mesa-dev@lists.freedesktop.org</a><br>
<a href="https://lists.freedesktop.org/mailman/listinfo/mesa-dev" rel="noreferrer" target="_blank">https://lists.freedesktop.org/<wbr>mailman/listinfo/mesa-dev</a><br>
</font></span></blockquote></div><br></div></div>