PIPE_TIMEOUT_INFINITE);
}
-static void
-zink_blit(struct pipe_context *pctx,
- const struct pipe_blit_info *info)
+static bool
+blit_resolve(struct zink_context *ctx, const struct pipe_blit_info *info)
{
- struct zink_context *ctx = zink_context(pctx);
- bool is_resolve = false;
if (info->mask != PIPE_MASK_RGBA ||
info->scissor_enable ||
- info->alpha_blend) {
- if (!util_blitter_is_blit_supported(ctx->blitter, info)) {
- debug_printf("blit unsupported %s -> %s\n",
- util_format_short_name(info->src.resource->format),
- util_format_short_name(info->dst.resource->format));
- return;
- }
-
- util_blitter_save_blend(ctx->blitter, ctx->gfx_pipeline_state.blend_state);
- util_blitter_save_depth_stencil_alpha(ctx->blitter, ctx->gfx_pipeline_state.depth_stencil_alpha_state);
- util_blitter_save_vertex_elements(ctx->blitter, ctx->element_state);
- util_blitter_save_stencil_ref(ctx->blitter, &ctx->stencil_ref);
- util_blitter_save_rasterizer(ctx->blitter, ctx->rast_state);
- util_blitter_save_fragment_shader(ctx->blitter, ctx->gfx_stages[PIPE_SHADER_FRAGMENT]);
- util_blitter_save_vertex_shader(ctx->blitter, ctx->gfx_stages[PIPE_SHADER_VERTEX]);
- util_blitter_save_framebuffer(ctx->blitter, &ctx->fb_state);
- util_blitter_save_viewport(ctx->blitter, ctx->viewport_states);
- util_blitter_save_scissor(ctx->blitter, ctx->scissor_states);
- util_blitter_save_fragment_sampler_states(ctx->blitter,
- ctx->num_samplers[PIPE_SHADER_FRAGMENT],
- (void **)ctx->samplers[PIPE_SHADER_FRAGMENT]);
- util_blitter_save_fragment_sampler_views(ctx->blitter,
- ctx->num_image_views[PIPE_SHADER_FRAGMENT],
- ctx->image_views[PIPE_SHADER_FRAGMENT]);
- util_blitter_save_fragment_constant_buffer_slot(ctx->blitter, ctx->ubos[PIPE_SHADER_FRAGMENT]);
- util_blitter_save_vertex_buffer_slot(ctx->blitter, ctx->buffers);
- util_blitter_save_sample_mask(ctx->blitter, ctx->gfx_pipeline_state.sample_mask);
-
- util_blitter_blit(ctx->blitter, info);
- return;
- }
+ info->alpha_blend)
+ return false;
struct zink_resource *src = zink_resource(info->src.resource);
struct zink_resource *dst = zink_resource(info->dst.resource);
- if (src->base.nr_samples > 1 && dst->base.nr_samples <= 1)
- is_resolve = true;
-
struct zink_batch *batch = zink_batch_no_rp(ctx);
zink_batch_reference_resoure(batch, src);
zink_batch_reference_resoure(batch, dst);
- if (is_resolve) {
- VkImageResolve region = {};
-
- region.srcSubresource.aspectMask = src->aspect;
- region.srcSubresource.mipLevel = info->src.level;
- region.srcSubresource.baseArrayLayer = 0; // no clue
- region.srcSubresource.layerCount = 1; // no clue
- region.srcOffset.x = info->src.box.x;
- region.srcOffset.y = info->src.box.y;
- region.srcOffset.z = info->src.box.z;
+ VkImageResolve region = {};
+
+ region.srcSubresource.aspectMask = src->aspect;
+ region.srcSubresource.mipLevel = info->src.level;
+ region.srcSubresource.baseArrayLayer = 0; // no clue
+ region.srcSubresource.layerCount = 1; // no clue
+ region.srcOffset.x = info->src.box.x;
+ region.srcOffset.y = info->src.box.y;
+ region.srcOffset.z = info->src.box.z;
+
+ region.dstSubresource.aspectMask = dst->aspect;
+ region.dstSubresource.mipLevel = info->dst.level;
+ region.dstSubresource.baseArrayLayer = 0; // no clue
+ region.dstSubresource.layerCount = 1; // no clue
+ region.dstOffset.x = info->dst.box.x;
+ region.dstOffset.y = info->dst.box.y;
+ region.dstOffset.z = info->dst.box.z;
+
+ region.extent.width = info->dst.box.width;
+ region.extent.height = info->dst.box.height;
+ region.extent.depth = info->dst.box.depth;
+ vkCmdResolveImage(batch->cmdbuf, src->image, src->layout,
+ dst->image, dst->layout,
+ 1, ®ion);
- region.dstSubresource.aspectMask = dst->aspect;
- region.dstSubresource.mipLevel = info->dst.level;
- region.dstSubresource.baseArrayLayer = 0; // no clue
- region.dstSubresource.layerCount = 1; // no clue
- region.dstOffset.x = info->dst.box.x;
- region.dstOffset.y = info->dst.box.y;
- region.dstOffset.z = info->dst.box.z;
-
- region.extent.width = info->dst.box.width;
- region.extent.height = info->dst.box.height;
- region.extent.depth = info->dst.box.depth;
- vkCmdResolveImage(batch->cmdbuf, src->image, src->layout,
- dst->image, dst->layout,
- 1, ®ion);
+ /* HACK: I have no idea why this is needed, but without it ioquake3
+ * randomly keeps fading to black.
+ */
+ flush_batch(ctx);
- } else {
- if (dst->layout != VK_IMAGE_LAYOUT_GENERAL &&
- dst->layout != VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL)
- zink_resource_barrier(batch->cmdbuf, dst, dst->aspect,
- VK_IMAGE_LAYOUT_GENERAL);
+ return true;
+}
- VkImageBlit region = {};
- region.srcSubresource.aspectMask = src->aspect;
- region.srcSubresource.mipLevel = info->src.level;
- region.srcOffsets[0].x = info->src.box.x;
- region.srcOffsets[0].y = info->src.box.y;
- region.srcOffsets[1].x = info->src.box.x + info->src.box.width;
- region.srcOffsets[1].y = info->src.box.y + info->src.box.height;
+static bool
+blit_native(struct zink_context *ctx, const struct pipe_blit_info *info)
+{
+ if (info->mask != PIPE_MASK_RGBA ||
+ info->scissor_enable ||
+ info->alpha_blend)
+ return false;
- if (src->base.array_size > 1) {
- region.srcOffsets[0].z = 0;
- region.srcOffsets[1].z = 1;
- region.srcSubresource.baseArrayLayer = info->src.box.z;
- region.srcSubresource.layerCount = info->src.box.depth;
- } else {
- region.srcOffsets[0].z = info->src.box.z;
- region.srcOffsets[1].z = info->src.box.z + info->src.box.depth;
- region.srcSubresource.baseArrayLayer = 0;
- region.srcSubresource.layerCount = 1;
- }
+ struct zink_resource *src = zink_resource(info->src.resource);
+ struct zink_resource *dst = zink_resource(info->dst.resource);
- region.dstSubresource.aspectMask = dst->aspect;
- region.dstSubresource.mipLevel = info->dst.level;
- region.dstOffsets[0].x = info->dst.box.x;
- region.dstOffsets[0].y = info->dst.box.y;
- region.dstOffsets[1].x = info->dst.box.x + info->dst.box.width;
- region.dstOffsets[1].y = info->dst.box.y + info->dst.box.height;
+ struct zink_batch *batch = zink_batch_no_rp(ctx);
+ zink_batch_reference_resoure(batch, src);
+ zink_batch_reference_resoure(batch, dst);
- if (dst->base.array_size > 1) {
- region.dstOffsets[0].z = 0;
- region.dstOffsets[1].z = 1;
- region.dstSubresource.baseArrayLayer = info->dst.box.z;
- region.dstSubresource.layerCount = info->dst.box.depth;
- } else {
- region.dstOffsets[0].z = info->dst.box.z;
- region.dstOffsets[1].z = info->dst.box.z + info->dst.box.depth;
- region.dstSubresource.baseArrayLayer = 0;
- region.dstSubresource.layerCount = 1;
- }
+ if (dst->layout != VK_IMAGE_LAYOUT_GENERAL &&
+ dst->layout != VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL)
+ zink_resource_barrier(batch->cmdbuf, dst, dst->aspect,
+ VK_IMAGE_LAYOUT_GENERAL);
+
+ VkImageBlit region = {};
+ region.srcSubresource.aspectMask = src->aspect;
+ region.srcSubresource.mipLevel = info->src.level;
+ region.srcOffsets[0].x = info->src.box.x;
+ region.srcOffsets[0].y = info->src.box.y;
+ region.srcOffsets[1].x = info->src.box.x + info->src.box.width;
+ region.srcOffsets[1].y = info->src.box.y + info->src.box.height;
+
+ if (src->base.array_size > 1) {
+ region.srcOffsets[0].z = 0;
+ region.srcOffsets[1].z = 1;
+ region.srcSubresource.baseArrayLayer = info->src.box.z;
+ region.srcSubresource.layerCount = info->src.box.depth;
+ } else {
+ region.srcOffsets[0].z = info->src.box.z;
+ region.srcOffsets[1].z = info->src.box.z + info->src.box.depth;
+ region.srcSubresource.baseArrayLayer = 0;
+ region.srcSubresource.layerCount = 1;
+ }
- vkCmdBlitImage(batch->cmdbuf, src->image, src->layout,
- dst->image, dst->layout,
- 1, ®ion,
- filter(info->filter));
+ region.dstSubresource.aspectMask = dst->aspect;
+ region.dstSubresource.mipLevel = info->dst.level;
+ region.dstOffsets[0].x = info->dst.box.x;
+ region.dstOffsets[0].y = info->dst.box.y;
+ region.dstOffsets[1].x = info->dst.box.x + info->dst.box.width;
+ region.dstOffsets[1].y = info->dst.box.y + info->dst.box.height;
+
+ if (dst->base.array_size > 1) {
+ region.dstOffsets[0].z = 0;
+ region.dstOffsets[1].z = 1;
+ region.dstSubresource.baseArrayLayer = info->dst.box.z;
+ region.dstSubresource.layerCount = info->dst.box.depth;
+ } else {
+ region.dstOffsets[0].z = info->dst.box.z;
+ region.dstOffsets[1].z = info->dst.box.z + info->dst.box.depth;
+ region.dstSubresource.baseArrayLayer = 0;
+ region.dstSubresource.layerCount = 1;
}
+ vkCmdBlitImage(batch->cmdbuf, src->image, src->layout,
+ dst->image, dst->layout,
+ 1, ®ion,
+ filter(info->filter));
+
/* HACK: I have no idea why this is needed, but without it ioquake3
* randomly keeps fading to black.
*/
flush_batch(ctx);
+
+ return true;
+}
+
+static void
+zink_blit(struct pipe_context *pctx,
+ const struct pipe_blit_info *info)
+{
+ struct zink_context *ctx = zink_context(pctx);
+ if (info->src.resource->nr_samples > 1 &&
+ info->dst.resource->nr_samples <= 1) {
+ if (blit_resolve(ctx, info))
+ return;
+ } else {
+ if (blit_native(ctx, info))
+ return;
+ }
+
+ if (!util_blitter_is_blit_supported(ctx->blitter, info)) {
+ debug_printf("blit unsupported %s -> %s\n",
+ util_format_short_name(info->src.resource->format),
+ util_format_short_name(info->dst.resource->format));
+ return;
+ }
+
+ util_blitter_save_blend(ctx->blitter, ctx->gfx_pipeline_state.blend_state);
+ util_blitter_save_depth_stencil_alpha(ctx->blitter, ctx->gfx_pipeline_state.depth_stencil_alpha_state);
+ util_blitter_save_vertex_elements(ctx->blitter, ctx->element_state);
+ util_blitter_save_stencil_ref(ctx->blitter, &ctx->stencil_ref);
+ util_blitter_save_rasterizer(ctx->blitter, ctx->rast_state);
+ util_blitter_save_fragment_shader(ctx->blitter, ctx->gfx_stages[PIPE_SHADER_FRAGMENT]);
+ util_blitter_save_vertex_shader(ctx->blitter, ctx->gfx_stages[PIPE_SHADER_VERTEX]);
+ util_blitter_save_framebuffer(ctx->blitter, &ctx->fb_state);
+ util_blitter_save_viewport(ctx->blitter, ctx->viewport_states);
+ util_blitter_save_scissor(ctx->blitter, ctx->scissor_states);
+ util_blitter_save_fragment_sampler_states(ctx->blitter,
+ ctx->num_samplers[PIPE_SHADER_FRAGMENT],
+ (void **)ctx->samplers[PIPE_SHADER_FRAGMENT]);
+ util_blitter_save_fragment_sampler_views(ctx->blitter,
+ ctx->num_image_views[PIPE_SHADER_FRAGMENT],
+ ctx->image_views[PIPE_SHADER_FRAGMENT]);
+ util_blitter_save_fragment_constant_buffer_slot(ctx->blitter, ctx->ubos[PIPE_SHADER_FRAGMENT]);
+ util_blitter_save_vertex_buffer_slot(ctx->blitter, ctx->buffers);
+ util_blitter_save_sample_mask(ctx->blitter, ctx->gfx_pipeline_state.sample_mask);
+
+ util_blitter_blit(ctx->blitter, info);
}
static void