Mesa (master): zink: basic primitive restart support for strip/fan topologies
GitLab Mirror
gitlab-mirror at kemper.freedesktop.org
Fri Aug 7 11:26:57 UTC 2020
Module: Mesa
Branch: master
Commit: 5edaf081cdbdadfd027c2ba9ee5095f49b274f81
URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=5edaf081cdbdadfd027c2ba9ee5095f49b274f81
Author: Mike Blumenkrantz <michael.blumenkrantz at gmail.com>
Date: Wed Jul 1 15:57:43 2020 -0400
zink: basic primitive restart support for strip/fan topologies
this conditionally handles rewriting the index buffer to use vk-compatible
restart indexes and then enables it in the pipeline for supported draw
modes
fixes #3174
Reviewed-by: Erik Faye-Lund <erik.faye-lund at collabora.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/5912>
---
src/gallium/drivers/zink/zink_draw.c | 35 +++++++++++++++++++++++---------
src/gallium/drivers/zink/zink_pipeline.c | 15 +++++++++++++-
src/gallium/drivers/zink/zink_pipeline.h | 2 ++
3 files changed, 41 insertions(+), 11 deletions(-)
diff --git a/src/gallium/drivers/zink/zink_draw.c b/src/gallium/drivers/zink/zink_draw.c
index a9d6bcbf08c..32a1ea2f94d 100644
--- a/src/gallium/drivers/zink/zink_draw.c
+++ b/src/gallium/drivers/zink/zink_draw.c
@@ -11,6 +11,7 @@
#include "util/u_helpers.h"
#include "util/u_inlines.h"
#include "util/u_prim.h"
+#include "util/u_prim_restart.h"
static VkDescriptorSet
allocate_descriptor_set(struct zink_screen *screen,
@@ -206,6 +207,7 @@ zink_draw_vbo(struct pipe_context *pctx,
struct zink_so_target *so_target = zink_so_target(dinfo->count_from_stream_output);
VkBuffer counter_buffers[PIPE_MAX_SO_OUTPUTS];
VkDeviceSize counter_buffer_offsets[PIPE_MAX_SO_OUTPUTS] = {};
+ bool need_index_buffer_unref = false;
if (dinfo->mode >= PIPE_PRIM_QUADS ||
dinfo->mode == PIPE_PRIM_LINE_LOOP ||
@@ -222,6 +224,9 @@ zink_draw_vbo(struct pipe_context *pctx,
if (!gfx_program)
return;
+ /* this is broken for anything requiring primconvert atm */
+ ctx->gfx_pipeline_state.primitive_restart = !!dinfo->primitive_restart;
+
VkPipeline pipeline = zink_get_gfx_pipeline(screen, gfx_program,
&ctx->gfx_pipeline_state,
dinfo->mode);
@@ -249,13 +254,19 @@ zink_draw_vbo(struct pipe_context *pctx,
unsigned index_offset = 0;
struct pipe_resource *index_buffer = NULL;
if (dinfo->index_size > 0) {
- if (dinfo->has_user_indices) {
- if (!util_upload_index_buffer(pctx, dinfo, &index_buffer, &index_offset, 4)) {
- debug_printf("util_upload_index_buffer() failed\n");
- return;
- }
- } else
- index_buffer = dinfo->index.resource;
+ uint32_t restart_index = util_prim_restart_index_from_size(dinfo->index_size);
+ if ((dinfo->primitive_restart && (dinfo->restart_index != restart_index))) {
+ util_translate_prim_restart_ib(pctx, dinfo, &index_buffer);
+ need_index_buffer_unref = true;
+ } else {
+ if (dinfo->has_user_indices) {
+ if (!util_upload_index_buffer(pctx, dinfo, &index_buffer, &index_offset, 4)) {
+ debug_printf("util_upload_index_buffer() failed\n");
+ return;
+ }
+ } else
+ index_buffer = dinfo->index.resource;
+ }
}
VkWriteDescriptorSet wds[PIPE_SHADER_TYPES * PIPE_MAX_CONSTANT_BUFFERS + PIPE_SHADER_TYPES * PIPE_MAX_SHADER_SAMPLER_VIEWS];
@@ -424,7 +435,11 @@ zink_draw_vbo(struct pipe_context *pctx,
if (dinfo->index_size > 0) {
VkIndexType index_type;
- switch (dinfo->index_size) {
+ unsigned index_size = dinfo->index_size;
+ if (need_index_buffer_unref)
+ /* index buffer will have been promoted from uint8 to uint16 in this case */
+ index_size = MAX2(index_size, 2);
+ switch (index_size) {
case 1:
assert(screen->have_EXT_index_type_uint8);
index_type = VK_INDEX_TYPE_UINT8_EXT;
@@ -443,7 +458,7 @@ zink_draw_vbo(struct pipe_context *pctx,
zink_batch_reference_resoure(batch, res);
vkCmdDrawIndexed(batch->cmdbuf,
dinfo->count, dinfo->instance_count,
- dinfo->start, dinfo->index_bias, dinfo->start_instance);
+ need_index_buffer_unref ? 0 : dinfo->start, dinfo->index_bias, dinfo->start_instance);
} else {
if (so_target && screen->tf_props.transformFeedbackDraw) {
zink_batch_reference_resoure(batch, zink_resource(so_target->counter_buffer));
@@ -455,7 +470,7 @@ zink_draw_vbo(struct pipe_context *pctx,
vkCmdDraw(batch->cmdbuf, dinfo->count, dinfo->instance_count, dinfo->start, dinfo->start_instance);
}
- if (dinfo->index_size > 0 && dinfo->has_user_indices)
+ if (dinfo->index_size > 0 && (dinfo->has_user_indices || need_index_buffer_unref))
pipe_resource_reference(&index_buffer, NULL);
if (ctx->num_so_targets) {
diff --git a/src/gallium/drivers/zink/zink_pipeline.c b/src/gallium/drivers/zink/zink_pipeline.c
index 261bdde5201..70f859fdd3f 100644
--- a/src/gallium/drivers/zink/zink_pipeline.c
+++ b/src/gallium/drivers/zink/zink_pipeline.c
@@ -49,7 +49,20 @@ zink_create_gfx_pipeline(struct zink_screen *screen,
VkPipelineInputAssemblyStateCreateInfo primitive_state = {};
primitive_state.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO;
primitive_state.topology = primitive_topology;
- primitive_state.primitiveRestartEnable = VK_FALSE;
+ switch (primitive_topology) {
+ case VK_PRIMITIVE_TOPOLOGY_POINT_LIST:
+ case VK_PRIMITIVE_TOPOLOGY_LINE_LIST:
+ case VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST:
+ case VK_PRIMITIVE_TOPOLOGY_LINE_LIST_WITH_ADJACENCY:
+ case VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST_WITH_ADJACENCY:
+ case VK_PRIMITIVE_TOPOLOGY_PATCH_LIST:
+ if (state->primitive_restart)
+ debug_printf("restart_index set with unsupported primitive topology %u\n", primitive_topology);
+ primitive_state.primitiveRestartEnable = VK_FALSE;
+ break;
+ default:
+ primitive_state.primitiveRestartEnable = state->primitive_restart ? VK_TRUE : VK_FALSE;
+ }
VkPipelineColorBlendStateCreateInfo blend_state = {};
blend_state.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO;
diff --git a/src/gallium/drivers/zink/zink_pipeline.h b/src/gallium/drivers/zink/zink_pipeline.h
index d65bce21ffb..757bae6266f 100644
--- a/src/gallium/drivers/zink/zink_pipeline.h
+++ b/src/gallium/drivers/zink/zink_pipeline.h
@@ -51,6 +51,8 @@ struct zink_gfx_pipeline_state {
VkSampleMask sample_mask;
uint8_t rast_samples;
+
+ bool primitive_restart;
};
VkPipeline
More information about the mesa-commit
mailing list