zink: support more texturing
authorErik Faye-Lund <erik.faye-lund@collabora.com>
Fri, 12 Jul 2019 10:43:20 +0000 (12:43 +0200)
committerErik Faye-Lund <erik.faye-lund@collabora.com>
Mon, 28 Oct 2019 08:51:46 +0000 (08:51 +0000)
Acked-by: Jordan Justen <jordan.l.justen@intel.com>
src/gallium/drivers/zink/nir_to_spirv/nir_to_spirv.c
src/gallium/drivers/zink/nir_to_spirv/spirv_builder.c
src/gallium/drivers/zink/nir_to_spirv/spirv_builder.h

index e55fe449f6b75f8e29f582b65e8fbac92edd75a8..ca29e7e8398431e24fcc2fe55dbbe795024b4a46 100644 (file)
@@ -1094,12 +1094,12 @@ get_src_float(struct ntv_context *ctx, nir_src *src)
 static void
 emit_tex(struct ntv_context *ctx, nir_tex_instr *tex)
 {
-   assert(tex->op == nir_texop_tex);
+   assert(tex->op == nir_texop_tex ||
+          tex->op == nir_texop_txb);
    assert(nir_alu_type_get_base_type(tex->dest_type) == nir_type_float);
    assert(tex->texture_index == tex->sampler_index);
 
-   bool has_proj = false, has_lod = false;
-   SpvId coord = 0, proj, lod;
+   SpvId coord = 0, proj = 0, bias = 0, lod = 0;
    unsigned coord_components;
    for (unsigned i = 0; i < tex->num_srcs; i++) {
       switch (tex->src[i].src_type) {
@@ -1109,15 +1109,21 @@ emit_tex(struct ntv_context *ctx, nir_tex_instr *tex)
          break;
 
       case nir_tex_src_projector:
-         has_proj = true;
-         proj = get_src_float(ctx, &tex->src[i].src);
          assert(nir_src_num_components(tex->src[i].src) == 1);
+         proj = get_src_float(ctx, &tex->src[i].src);
+         assert(proj != 0);
+         break;
+
+      case nir_tex_src_bias:
+         assert(tex->op == nir_texop_txb);
+         bias = get_src_float(ctx, &tex->src[i].src);
+         assert(bias != 0);
          break;
 
       case nir_tex_src_lod:
-         has_lod = true;
-         lod = get_src_float(ctx, &tex->src[i].src);
          assert(nir_src_num_components(tex->src[i].src) == 1);
+         lod = get_src_float(ctx, &tex->src[i].src);
+         assert(lod != 0);
          break;
 
       default:
@@ -1126,9 +1132,9 @@ emit_tex(struct ntv_context *ctx, nir_tex_instr *tex)
       }
    }
 
-   if (!has_lod && ctx->stage != MESA_SHADER_FRAGMENT) {
-      has_lod = true;
+   if (lod == 0 && ctx->stage != MESA_SHADER_FRAGMENT) {
       lod = spirv_builder_const_float(&ctx->builder, 32, 0);
+      assert(lod != 0);
    }
 
    bool is_ms;
@@ -1146,8 +1152,7 @@ emit_tex(struct ntv_context *ctx, nir_tex_instr *tex)
 
    SpvId dest_type = get_dest_type(ctx, &tex->dest, tex->dest_type);
 
-   SpvId result;
-   if (has_proj) {
+   if (proj) {
       SpvId constituents[coord_components + 1];
       SpvId float_type = spirv_builder_type_float(&ctx->builder, 32);
       for (uint32_t i = 0; i < coord_components; ++i)
@@ -1159,34 +1164,17 @@ emit_tex(struct ntv_context *ctx, nir_tex_instr *tex)
       constituents[coord_components++] = proj;
 
       SpvId vec_type = get_fvec_type(ctx, 32, coord_components);
-      SpvId merged = spirv_builder_emit_composite_construct(&ctx->builder,
+      coord = spirv_builder_emit_composite_construct(&ctx->builder,
                                                             vec_type,
                                                             constituents,
                                                             coord_components);
-
-      if (has_lod)
-         result = spirv_builder_emit_image_sample_proj_explicit_lod(&ctx->builder,
-                                                                    dest_type,
-                                                                    load,
-                                                                    merged,
-                                                                    lod);
-      else
-         result = spirv_builder_emit_image_sample_proj_implicit_lod(&ctx->builder,
-                                                                    dest_type,
-                                                                    load,
-                                                                    merged);
-   } else {
-      if (has_lod)
-         result = spirv_builder_emit_image_sample_explicit_lod(&ctx->builder,
-                                                               dest_type,
-                                                               load,
-                                                               coord, lod);
-      else
-         result = spirv_builder_emit_image_sample_implicit_lod(&ctx->builder,
-                                                               dest_type,
-                                                               load,
-                                                               coord);
    }
+
+   SpvId result = spirv_builder_emit_image_sample(&ctx->builder,
+                                                  dest_type, load,
+                                                  coord,
+                                                  proj != 0,
+                                                  lod, bias);
    spirv_builder_emit_decoration(&ctx->builder, result,
                                  SpvDecorationRelaxedPrecision);
 
index b5aa3d9e61b1a04860d3efa0d31fc860b4f24364..1b3718307f9563c4ea3c33081630277f1681585c 100644 (file)
@@ -506,72 +506,48 @@ spirv_builder_emit_kill(struct spirv_builder *b)
 }
 
 SpvId
-spirv_builder_emit_image_sample_implicit_lod(struct spirv_builder *b,
-                                             SpvId result_type,
-                                             SpvId sampled_image,
-                                             SpvId coordinate)
+spirv_builder_emit_image_sample(struct spirv_builder *b,
+                                SpvId result_type,
+                                SpvId sampled_image,
+                                SpvId coordinate,
+                                bool proj,
+                                SpvId lod,
+                                SpvId bias)
 {
    SpvId result = spirv_builder_new_id(b);
-   spirv_buffer_prepare(&b->instructions, 5);
-   spirv_buffer_emit_word(&b->instructions, SpvOpImageSampleImplicitLod | (5 << 16));
-   spirv_buffer_emit_word(&b->instructions, result_type);
-   spirv_buffer_emit_word(&b->instructions, result);
-   spirv_buffer_emit_word(&b->instructions, sampled_image);
-   spirv_buffer_emit_word(&b->instructions, coordinate);
-   return result;
-}
 
-SpvId
-spirv_builder_emit_image_sample_explicit_lod(struct spirv_builder *b,
-                                             SpvId result_type,
-                                             SpvId sampled_image,
-                                             SpvId coordinate,
-                                             SpvId lod)
-{
-   SpvId result = spirv_builder_new_id(b);
-   spirv_buffer_prepare(&b->instructions, 7);
-   spirv_buffer_emit_word(&b->instructions, SpvOpImageSampleExplicitLod | (7 << 16));
-   spirv_buffer_emit_word(&b->instructions, result_type);
-   spirv_buffer_emit_word(&b->instructions, result);
-   spirv_buffer_emit_word(&b->instructions, sampled_image);
-   spirv_buffer_emit_word(&b->instructions, coordinate);
-   spirv_buffer_emit_word(&b->instructions, SpvImageOperandsLodMask);
-   spirv_buffer_emit_word(&b->instructions, lod);
-   return result;
-}
+   int opcode = SpvOpImageSampleImplicitLod;
+   if (proj)
+      opcode += SpvOpImageSampleProjImplicitLod - SpvOpImageSampleImplicitLod;
+   if (lod)
+      opcode += SpvOpImageSampleExplicitLod - SpvOpImageSampleImplicitLod;
+
+   SpvImageOperandsMask operand_mask = 0;
+   SpvId extra_operands[3];
+   int num_extra_operands = SpvImageOperandsMaskNone;
+   if (bias) {
+      extra_operands[++num_extra_operands] = bias;
+      operand_mask |= SpvImageOperandsBiasMask;
+   }
+   if (lod) {
+      extra_operands[++num_extra_operands] = lod;
+      operand_mask |= SpvImageOperandsLodMask;
+   }
 
-SpvId
-spirv_builder_emit_image_sample_proj_implicit_lod(struct spirv_builder *b,
-                                                  SpvId result_type,
-                                                  SpvId sampled_image,
-                                                  SpvId coordinate)
-{
-   SpvId result = spirv_builder_new_id(b);
-   spirv_buffer_prepare(&b->instructions, 5);
-   spirv_buffer_emit_word(&b->instructions, SpvOpImageSampleProjImplicitLod | (5 << 16));
-   spirv_buffer_emit_word(&b->instructions, result_type);
-   spirv_buffer_emit_word(&b->instructions, result);
-   spirv_buffer_emit_word(&b->instructions, sampled_image);
-   spirv_buffer_emit_word(&b->instructions, coordinate);
-   return result;
-}
+   /* finalize num_extra_operands / extra_operands */
+   if (num_extra_operands > 0) {
+      extra_operands[0] = operand_mask;
+      num_extra_operands++;
+   }
 
-SpvId
-spirv_builder_emit_image_sample_proj_explicit_lod(struct spirv_builder *b,
-                                                  SpvId result_type,
-                                                  SpvId sampled_image,
-                                                  SpvId coordinate,
-                                                  SpvId lod)
-{
-   SpvId result = spirv_builder_new_id(b);
-   spirv_buffer_prepare(&b->instructions, 7);
-   spirv_buffer_emit_word(&b->instructions, SpvOpImageSampleProjExplicitLod | (7 << 16));
+   spirv_buffer_prepare(&b->instructions, 5 + num_extra_operands);
+   spirv_buffer_emit_word(&b->instructions, opcode | ((5 + num_extra_operands) << 16));
    spirv_buffer_emit_word(&b->instructions, result_type);
    spirv_buffer_emit_word(&b->instructions, result);
    spirv_buffer_emit_word(&b->instructions, sampled_image);
    spirv_buffer_emit_word(&b->instructions, coordinate);
-   spirv_buffer_emit_word(&b->instructions, SpvImageOperandsLodMask);
-   spirv_buffer_emit_word(&b->instructions, lod);
+   for (int i = 0; i < num_extra_operands; ++i)
+      spirv_buffer_emit_word(&b->instructions, extra_operands[i]);
    return result;
 }
 
index 461f5ad3d12601c16e3285f6e9cbfe71aa4d974e..0bb16b16dd3400aaef4fec38756beb74af50b5dd 100644 (file)
@@ -204,31 +204,15 @@ spirv_builder_set_phi_operand(struct spirv_builder *b, size_t position,
 void
 spirv_builder_emit_kill(struct spirv_builder *b);
 
-SpvId
-spirv_builder_emit_image_sample_implicit_lod(struct spirv_builder *b,
-                                             SpvId result_type,
-                                             SpvId sampled_image,
-                                             SpvId coordinate);
-
-SpvId
-spirv_builder_emit_image_sample_explicit_lod(struct spirv_builder *b,
-                                             SpvId result_type,
-                                             SpvId sampled_image,
-                                             SpvId coordinate,
-                                             SpvId lod);
-
-SpvId
-spirv_builder_emit_image_sample_proj_implicit_lod(struct spirv_builder *b,
-                                                  SpvId result_type,
-                                                  SpvId sampled_image,
-                                                  SpvId coordinate);
 
 SpvId
-spirv_builder_emit_image_sample_proj_explicit_lod(struct spirv_builder *b,
-                                                  SpvId result_type,
-                                                  SpvId sampled_image,
-                                                  SpvId coordinate,
-                                                  SpvId lod);
+spirv_builder_emit_image_sample(struct spirv_builder *b,
+                                SpvId result_type,
+                                SpvId sampled_image,
+                                SpvId coordinate,
+                                bool proj,
+                                SpvId lod,
+                                SpvId bias);
 
 SpvId
 spirv_builder_emit_ext_inst(struct spirv_builder *b, SpvId result_type,