From ee2fe9fd40af1fce9775436d9a64405d354c1169 Mon Sep 17 00:00:00 2001 From: Jakob Bornecrantz Date: Thu, 14 Sep 2023 21:21:14 +0100 Subject: [PATCH] c/[render|main]: Refactor scratch images This commit does a few things: * Makes the scratch images per view * Introduces a new struct that is managed by the renderer --- src/xrt/compositor/main/comp_renderer.c | 43 ++++--- src/xrt/compositor/render/render_interface.h | 63 +++++++---- src/xrt/compositor/render/render_resources.c | 113 +++++++++++-------- 3 files changed, 129 insertions(+), 90 deletions(-) diff --git a/src/xrt/compositor/main/comp_renderer.c b/src/xrt/compositor/main/comp_renderer.c index 0f7cc86dc..7325d821f 100644 --- a/src/xrt/compositor/main/comp_renderer.c +++ b/src/xrt/compositor/main/comp_renderer.c @@ -87,6 +87,8 @@ struct comp_renderer struct comp_mirror_to_debug_gui mirror_to_debug_gui; + //! Scratch images used for layer squasher. + struct render_scratch_images scratch; //! @} //! @name Image-dependent members @@ -812,6 +814,9 @@ renderer_fini(struct comp_renderer *r) // Do this after the mirror struct. comp_layer_renderer_destroy(&(r->lr)); + + // Destroy any scratch images created. + render_scratch_images_close(&r->c->nr, &r->scratch); } static VkImageView @@ -1033,13 +1038,13 @@ ensure_scratch_image(struct comp_renderer *r, struct render_viewport_data r_viewport_data = { .w = w, .h = h, - .x = w, + .x = 0, .y = 0, }; - VkExtent2D extent = {w * 2, h}; + VkExtent2D extent = {w, h}; - if (!render_ensure_scratch_image(&r->c->nr, extent)) { + if (!render_scratch_images_ensure(&r->c->nr, &r->scratch, extent)) { U_LOG_E("Failed to create scratch image!"); assert(false); } @@ -1059,13 +1064,13 @@ do_layers(struct comp_renderer *r, // Create scratch image and get target views. ensure_scratch_image(r, &target_views[0], &target_views[1]); VkImage target_images[2] = { - crc->r->scratch.color.image, - crc->r->scratch.color.image, + r->scratch.color[0].image, + r->scratch.color[1].image, }; VkImageView target_image_views[2] = { - crc->r->scratch.color.unorm_view, // Have to write in linear - crc->r->scratch.color.unorm_view, + r->scratch.color[0].unorm_view, // Have to write in linear + r->scratch.color[1].unorm_view, }; struct xrt_normalized_rect pre_transforms[2] = { @@ -1101,25 +1106,27 @@ do_distortion(struct comp_renderer *r, struct render_compute *crc, const struct VkImage target_image = r->c->target->images[r->acquired_buffer].handle; VkImageView target_image_view = r->c->target->images[r->acquired_buffer].view; - VkImageView view = crc->r->scratch.color.srgb_view; // Read with gamma curve. VkSampler sampler = crc->r->samplers.clamp_to_border_black; - VkImageView src_image_views[2] = {view, view}; + VkImageView src_image_views[2] = { + r->scratch.color[0].srgb_view, // Read with gamma curve. + r->scratch.color[1].srgb_view, + }; VkSampler src_samplers[2] = {sampler, sampler}; struct xrt_normalized_rect src_norm_rects[2] = { { - // Left, takes up half the screen. + // Left, takes up the full view of the first image. .x = 0.0f, .y = 0.0f, - .w = 0.5f, + .w = 1.0f, .h = 1.0f, }, { - // Right, takes up half the screen. - .x = 0.5f, + // Right, takes up the full view of the second image. + .x = 0.0f, .y = 0.0f, - .w = 0.5f, + .w = 1.0f, .h = 1.0f, }, }; @@ -1626,17 +1633,17 @@ comp_renderer_draw(struct comp_renderer *r) if (use_compute) { // Covers only the first half of the view. - struct xrt_normalized_rect rect = {0, 0, 0.5f, 1.0f}; + struct xrt_normalized_rect rect = {0, 0, 1.0f, 1.0f}; comp_mirror_do_blit( // &r->mirror_to_debug_gui, // &c->base.vk, // frame_id, // predicted_display_time_ns, // - c->nr.scratch.color.image, // - c->nr.scratch.color.srgb_view, // + r->scratch.color[0].image, // + r->scratch.color[0].srgb_view, // clamp_to_edge, // - c->nr.scratch.extent, // + r->scratch.extent, // rect); // } else { // Covers the whole view. diff --git a/src/xrt/compositor/render/render_interface.h b/src/xrt/compositor/render/render_interface.h index c42c1fa5d..b21a4b014 100644 --- a/src/xrt/compositor/render/render_interface.h +++ b/src/xrt/compositor/render/render_interface.h @@ -299,22 +299,6 @@ struct render_resources struct render_buffer ubos[2]; } mesh; - /*! - * Used as a scratch buffer by the compute layer renderer. - */ - struct - { - VkExtent2D extent; - - struct - { - VkDeviceMemory memory; - VkImage image; - VkImageView srgb_view; - VkImageView unorm_view; - } color; - } scratch; - /*! * Used as a default image empty image when none is given or to pad * out fixed sized descriptor sets. @@ -452,12 +436,6 @@ render_distortion_images_ensure(struct render_resources *r, void render_distortion_images_close(struct render_resources *r); -/*! - * Ensure that the scratch image is created and has the given extent. - */ -bool -render_ensure_scratch_image(struct render_resources *r, VkExtent2D extent); - /*! * Returns the timestamps for when the latest GPU work started and stopped that * was submitted using @ref render_gfx or @ref render_compute cmd buf builders. @@ -489,6 +467,47 @@ bool render_resources_get_duration(struct render_resources *r, uint64_t *out_gpu_duration_ns); +/* + * + * Scratch images. + * + */ + +/*! + * Small helper struct to hold a scratch image, intended to be used with the + * compute pipeline where both srgb and unorm views are needed. + */ +struct render_scratch_color_image +{ + VkDeviceMemory device_memory; + VkImage image; + VkImageView srgb_view; + VkImageView unorm_view; +}; + +/*! + * Helper struct to hold scratch images. + */ +struct render_scratch_images +{ + VkExtent2D extent; + + struct render_scratch_color_image color[2]; +}; + +/*! + * Ensure that the scratch images are created and have the given extent. + */ +bool +render_scratch_images_ensure(struct render_resources *r, struct render_scratch_images *rsi, VkExtent2D extent); + +/*! + * Close all resources on the given @ref render_scatch_images. + */ +void +render_scratch_images_close(struct render_resources *r, struct render_scratch_images *rsi); + + /* * * Shared between both gfx and compute. diff --git a/src/xrt/compositor/render/render_resources.c b/src/xrt/compositor/render/render_resources.c index ef779db60..2abd10016 100644 --- a/src/xrt/compositor/render/render_resources.c +++ b/src/xrt/compositor/render/render_resources.c @@ -448,12 +448,7 @@ prepare_mock_image_locked(struct vk_bundle *vk, VkCommandBuffer cmd, VkImage dst */ static bool -create_scratch_image_and_view(struct vk_bundle *vk, - VkExtent2D extent, - VkDeviceMemory *out_device_memory, - VkImage *out_image, - VkImageView *out_srgb_view, - VkImageView *out_unorm_view) +create_scratch_image_and_view(struct vk_bundle *vk, VkExtent2D extent, struct render_scratch_color_image *rsci) { VkFormat srgb_format = VK_FORMAT_R8G8B8A8_SRGB; VkFormat unorm_format = VK_FORMAT_R8G8B8A8_UNORM; @@ -506,24 +501,21 @@ create_scratch_image_and_view(struct vk_bundle *vk, subresource_range, // subresource_range &unorm_view)); // out_image_view - *out_device_memory = device_memory; - *out_image = image; - *out_srgb_view = srgb_view; - *out_unorm_view = unorm_view; + rsci->device_memory = device_memory; + rsci->image = image; + rsci->srgb_view = srgb_view; + rsci->unorm_view = unorm_view; return true; } static void -teardown_scratch_image(struct render_resources *r) +teardown_scratch_color_image(struct vk_bundle *vk, struct render_scratch_color_image *rsci) { - struct vk_bundle *vk = r->vk; - - D(ImageView, r->scratch.color.unorm_view); - D(ImageView, r->scratch.color.srgb_view); - D(Image, r->scratch.color.image); - DF(Memory, r->scratch.color.memory); - U_ZERO(&r->scratch.extent); + D(ImageView, rsci->unorm_view); + D(ImageView, rsci->srgb_view); + D(Image, rsci->image); + DF(Memory, rsci->device_memory); } @@ -942,36 +934,6 @@ render_resources_init(struct render_resources *r, return true; } -bool -render_ensure_scratch_image(struct render_resources *r, VkExtent2D extent) -{ - bool bret; - - if (r->scratch.extent.width == extent.width && // - r->scratch.extent.height == extent.height && // - r->scratch.color.srgb_view != VK_NULL_HANDLE && // - r->scratch.color.unorm_view != VK_NULL_HANDLE) { - return true; - } - - teardown_scratch_image(r); - - bret = create_scratch_image_and_view( // - r->vk, // - extent, // - &r->scratch.color.memory, // - &r->scratch.color.image, // - &r->scratch.color.srgb_view, // - &r->scratch.color.unorm_view); // - if (!bret) { - return false; - } - - r->scratch.extent = extent; - - return true; -} - void render_resources_close(struct render_resources *r) { @@ -1021,8 +983,6 @@ render_resources_close(struct render_resources *r) } render_buffer_close(vk, &r->compute.distortion.ubo); - teardown_scratch_image(r); - vk_cmd_pool_destroy(vk, &r->distortion_pool); D(CommandPool, r->cmd_pool); @@ -1120,3 +1080,56 @@ render_resources_get_duration(struct render_resources *r, uint64_t *out_gpu_dura return true; } + + +/* + * + * 'Exported' scratch functions. + * + */ + +bool +render_scratch_images_ensure(struct render_resources *r, struct render_scratch_images *rsi, VkExtent2D extent) +{ + bool bret; + + if (rsi->extent.width == extent.width && // + rsi->extent.height == extent.height && // + rsi->color[0].srgb_view != VK_NULL_HANDLE && // + rsi->color[0].unorm_view != VK_NULL_HANDLE) { + return true; + } + + render_scratch_images_close(r, rsi); + + for (uint32_t i = 0; i < ARRAY_SIZE(rsi->color); i++) { + bret = create_scratch_image_and_view( // + r->vk, // + extent, // + &rsi->color[i]); // + if (!bret) { + break; + } + } + + if (!bret) { + render_scratch_images_close(r, rsi); + return false; + } + + rsi->extent = extent; + + return true; +} + +void +render_scratch_images_close(struct render_resources *r, struct render_scratch_images *rsi) +{ + struct vk_bundle *vk = r->vk; + + for (uint32_t i = 0; i < ARRAY_SIZE(rsi->color); i++) { + teardown_scratch_color_image(vk, &rsi->color[i]); + } + + U_ZERO(&rsi->extent); +}