mirror of
https://gitlab.freedesktop.org/mesa/vulkan-wsi-layer.git
synced 2025-12-25 07:00:09 +01:00
Separate image creation from create_and_bind_swapchain
Change-Id: Ifbc6a5fb57c962006550838667944b03654ce0e4 Signed-off-by: Iason Paraskevopoulos <iason.paraskevopoulos@arm.com> Signed-off-by: Fufu Fang <fufu.fang@arm.com>
This commit is contained in:
parent
bb31e7fba0
commit
cbf6c9765c
7 changed files with 123 additions and 81 deletions
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2022 Arm Limited.
|
||||
* Copyright (c) 2022-2024 Arm Limited.
|
||||
*
|
||||
* SPDX-License-Identifier: MIT
|
||||
*
|
||||
|
|
@ -68,7 +68,7 @@ uint32_t external_memory::get_num_planes()
|
|||
{
|
||||
for (uint32_t plane = 0; plane < MAX_PLANES; plane++)
|
||||
{
|
||||
if (m_buffer_fds[plane] == -1)
|
||||
if (m_strides[plane] == -1)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -76,32 +76,11 @@ VkResult swapchain::init_platform(VkDevice device, const VkSwapchainCreateInfoKH
|
|||
return VK_SUCCESS;
|
||||
}
|
||||
|
||||
VkResult swapchain::create_and_bind_swapchain_image(VkImageCreateInfo image_create, wsi::swapchain_image &image)
|
||||
VkResult swapchain::allocate_and_bind_swapchain_image(VkImageCreateInfo image_create, swapchain_image &image)
|
||||
{
|
||||
VkResult res = VK_SUCCESS;
|
||||
const std::lock_guard<std::recursive_mutex> lock(m_image_status_mutex);
|
||||
|
||||
m_image_create_info = image_create;
|
||||
#if WSI_IMAGE_COMPRESSION_CONTROL_SWAPCHAIN
|
||||
if (m_device_data.is_swapchain_compression_control_enabled())
|
||||
{
|
||||
/* Initialize compression control */
|
||||
m_image_compression_control.sType = VK_STRUCTURE_TYPE_IMAGE_COMPRESSION_CONTROL_EXT;
|
||||
m_image_compression_control.compressionControlPlaneCount =
|
||||
m_image_compression_control_params.compression_control_plane_count;
|
||||
m_image_compression_control.flags = m_image_compression_control_params.flags;
|
||||
m_image_compression_control.pFixedRateFlags = m_image_compression_control_params.fixed_rate_flags.data();
|
||||
m_image_compression_control.pNext = m_image_create_info.pNext;
|
||||
|
||||
m_image_create_info.pNext = &m_image_compression_control;
|
||||
}
|
||||
#endif
|
||||
res = m_device_data.disp.CreateImage(m_device, &m_image_create_info, get_allocation_callbacks(), &image.image);
|
||||
if (res != VK_SUCCESS)
|
||||
{
|
||||
return res;
|
||||
}
|
||||
|
||||
VkMemoryRequirements memory_requirements = {};
|
||||
m_device_data.disp.GetImageMemoryRequirements(m_device, image.image, &memory_requirements);
|
||||
|
||||
|
|
@ -161,6 +140,27 @@ VkResult swapchain::create_and_bind_swapchain_image(VkImageCreateInfo image_crea
|
|||
return res;
|
||||
}
|
||||
|
||||
VkResult swapchain::create_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image)
|
||||
{
|
||||
m_image_create_info = image_create_info;
|
||||
#if WSI_IMAGE_COMPRESSION_CONTROL_SWAPCHAIN
|
||||
if (m_device_data.is_swapchain_compression_control_enabled())
|
||||
{
|
||||
/* Initialize compression control */
|
||||
m_image_compression_control.sType = VK_STRUCTURE_TYPE_IMAGE_COMPRESSION_CONTROL_EXT;
|
||||
m_image_compression_control.compressionControlPlaneCount =
|
||||
m_image_compression_control_params.compression_control_plane_count;
|
||||
m_image_compression_control.flags = m_image_compression_control_params.flags;
|
||||
m_image_compression_control.pFixedRateFlags = m_image_compression_control_params.fixed_rate_flags.data();
|
||||
m_image_compression_control.pNext = m_image_create_info.pNext;
|
||||
|
||||
m_image_create_info.pNext = &m_image_compression_control;
|
||||
}
|
||||
#endif
|
||||
|
||||
return m_device_data.disp.CreateImage(m_device, &m_image_create_info, get_allocation_callbacks(), &image.image);
|
||||
}
|
||||
|
||||
void swapchain::present_image(uint32_t pending_index)
|
||||
{
|
||||
unpresent_image(pending_index);
|
||||
|
|
|
|||
|
|
@ -60,16 +60,26 @@ protected:
|
|||
bool &use_presentation_thread) override;
|
||||
|
||||
/**
|
||||
* @brief Creates and binds a new swapchain image.
|
||||
* @brief Allocates and binds a new swapchain image.
|
||||
*
|
||||
* @param image_create_info Data to be used to create the image.
|
||||
* @param image Handle to the image.
|
||||
*
|
||||
* @return Returns VK_SUCCESS on success, otherwise an appropriate error code.
|
||||
*/
|
||||
VkResult allocate_and_bind_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) override;
|
||||
|
||||
/**
|
||||
* @brief Creates a new swapchain image.
|
||||
*
|
||||
* @param image_create_info Data to be used to create the image.
|
||||
* @param image Handle to the image.
|
||||
*
|
||||
* @return If image creation is successful returns VK_SUCCESS, otherwise
|
||||
* will return VK_ERROR_OUT_OF_DEVICE_MEMORY or VK_ERROR_INITIALIZATION_FAILED
|
||||
* depending on the error that occured.
|
||||
* depending on the error that occurred.
|
||||
*/
|
||||
VkResult create_and_bind_swapchain_image(VkImageCreateInfo image_create_info, wsi::swapchain_image &image) override;
|
||||
VkResult create_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) override;
|
||||
|
||||
/**
|
||||
* @brief Method to perform a present - just calls unpresent_image on headless
|
||||
|
|
|
|||
|
|
@ -322,17 +322,18 @@ VkResult swapchain_base::init(VkDevice device, const VkSwapchainCreateInfoKHR *s
|
|||
}
|
||||
|
||||
const bool image_deferred_allocation =
|
||||
image_create_info.flags & VK_SWAPCHAIN_CREATE_DEFERRED_MEMORY_ALLOCATION_BIT_EXT;
|
||||
swapchain_create_info->flags & VK_SWAPCHAIN_CREATE_DEFERRED_MEMORY_ALLOCATION_BIT_EXT;
|
||||
for (auto &img : m_swapchain_images)
|
||||
{
|
||||
TRY(create_swapchain_image(image_create_info, img));
|
||||
|
||||
if (image_deferred_allocation)
|
||||
{
|
||||
m_image_create_info = image_create_info;
|
||||
img.status = swapchain_image::UNALLOCATED;
|
||||
}
|
||||
else
|
||||
{
|
||||
TRY_LOG_CALL(create_and_bind_swapchain_image(image_create_info, img));
|
||||
TRY_LOG_CALL(allocate_and_bind_swapchain_image(image_create_info, img));
|
||||
}
|
||||
|
||||
VkSemaphoreCreateInfo semaphore_info = {};
|
||||
|
|
@ -465,7 +466,7 @@ VkResult swapchain_base::acquire_next_image(uint64_t timeout, VkSemaphore semaph
|
|||
{
|
||||
if (m_swapchain_images[i].status == swapchain_image::UNALLOCATED)
|
||||
{
|
||||
auto res = create_and_bind_swapchain_image(m_image_create_info, m_swapchain_images[i]);
|
||||
auto res = allocate_and_bind_swapchain_image(m_image_create_info, m_swapchain_images[i]);
|
||||
if (res != VK_SUCCESS)
|
||||
{
|
||||
WSI_LOG_ERROR("Failed to allocate swapchain image.");
|
||||
|
|
|
|||
|
|
@ -414,16 +414,26 @@ protected:
|
|||
void teardown();
|
||||
|
||||
/**
|
||||
* @brief Creates and binds a new swapchain image.
|
||||
* @brief Allocates and binds a new swapchain image.
|
||||
*
|
||||
* @param image_create_info Data to be used to create the image.
|
||||
* @param image Handle to the image.
|
||||
*
|
||||
* @return Returns VK_SUCCESS on success, otherwise an appropriate error code.
|
||||
*/
|
||||
virtual VkResult allocate_and_bind_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) = 0;
|
||||
|
||||
/**
|
||||
* @brief Creates a new swapchain image.
|
||||
*
|
||||
* @param image_create_info Data to be used to create the image.
|
||||
* @param image Handle to the image.
|
||||
*
|
||||
* @return If image creation is successful returns VK_SUCCESS, otherwise
|
||||
* will return VK_ERROR_OUT_OF_DEVICE_MEMORY or VK_ERROR_INITIALIZATION_FAILED
|
||||
* depending on the error that occured.
|
||||
* depending on the error that occurred.
|
||||
*/
|
||||
virtual VkResult create_and_bind_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) = 0;
|
||||
virtual VkResult create_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) = 0;
|
||||
|
||||
/**
|
||||
* @brief Method to present and image
|
||||
|
|
|
|||
|
|
@ -257,10 +257,14 @@ VkResult swapchain::get_surface_compatible_formats(const VkImageCreateInfo &info
|
|||
|
||||
VkResult swapchain::allocate_wsialloc(VkImageCreateInfo &image_create_info, wayland_image_data *image_data,
|
||||
util::vector<wsialloc_format> &importable_formats,
|
||||
wsialloc_format *allocated_format)
|
||||
wsialloc_format *allocated_format, bool avoid_allocation)
|
||||
{
|
||||
bool is_protected_memory = (image_create_info.flags & VK_IMAGE_CREATE_PROTECTED_BIT) != 0;
|
||||
uint64_t allocation_flags = is_protected_memory ? WSIALLOC_ALLOCATE_PROTECTED : 0;
|
||||
if (avoid_allocation)
|
||||
{
|
||||
allocation_flags |= WSIALLOC_ALLOCATE_NO_MEMORY;
|
||||
}
|
||||
|
||||
#if WSI_IMAGE_COMPRESSION_CONTROL_SWAPCHAIN
|
||||
if (m_image_compression_control_params.flags & VK_IMAGE_COMPRESSION_FIXED_RATE_EXPLICIT_EXT)
|
||||
|
|
@ -274,10 +278,11 @@ VkResult swapchain::allocate_wsialloc(VkImageCreateInfo &image_create_info, wayl
|
|||
allocation_flags };
|
||||
|
||||
wsialloc_allocate_result alloc_result = { 0 };
|
||||
/* Clear fds for error purposes */
|
||||
/* Clear buffer_fds and average_row_strides for error purposes */
|
||||
for (int i = 0; i < WSIALLOC_MAX_PLANES; ++i)
|
||||
{
|
||||
alloc_result.buffer_fds[i] = -1;
|
||||
alloc_result.average_row_strides[i] = -1;
|
||||
}
|
||||
const auto res = wsialloc_alloc(m_wsi_allocator, &alloc_info, &alloc_result);
|
||||
if (res != WSIALLOC_ERROR_NONE)
|
||||
|
|
@ -318,43 +323,16 @@ static VkResult fill_image_create_info(VkImageCreateInfo &image_create_info,
|
|||
return VK_SUCCESS;
|
||||
}
|
||||
|
||||
VkResult swapchain::allocate_image(VkImageCreateInfo &image_create_info, wayland_image_data *image_data, VkImage *image)
|
||||
VkResult swapchain::allocate_image(VkImageCreateInfo &image_create_info, wayland_image_data *image_data)
|
||||
{
|
||||
util::vector<wsialloc_format> importable_formats(util::allocator(m_allocator, VK_SYSTEM_ALLOCATION_SCOPE_COMMAND));
|
||||
auto &m_allocated_format = m_image_creation_parameters.m_allocated_format;
|
||||
if (m_image_create_info.format != VK_FORMAT_UNDEFINED)
|
||||
if (!importable_formats.try_push_back(m_allocated_format))
|
||||
{
|
||||
if (!importable_formats.try_push_back(m_allocated_format))
|
||||
{
|
||||
return VK_ERROR_OUT_OF_HOST_MEMORY;
|
||||
}
|
||||
TRY_LOG_CALL(allocate_wsialloc(m_image_create_info, image_data, importable_formats, &m_allocated_format));
|
||||
return VK_ERROR_OUT_OF_HOST_MEMORY;
|
||||
}
|
||||
else
|
||||
{
|
||||
util::vector<uint64_t> exportable_modifiers(util::allocator(m_allocator, VK_SYSTEM_ALLOCATION_SCOPE_COMMAND));
|
||||
TRY_LOG_CALL(get_surface_compatible_formats(image_create_info, importable_formats, exportable_modifiers));
|
||||
TRY_LOG_CALL(allocate_wsialloc(m_image_create_info, image_data, importable_formats, &m_allocated_format, false));
|
||||
|
||||
/* TODO: Handle exportable images which use ICD allocated memory in preference to an external allocator. */
|
||||
if (importable_formats.empty())
|
||||
{
|
||||
WSI_LOG_ERROR("Export/Import not supported.");
|
||||
return VK_ERROR_INITIALIZATION_FAILED;
|
||||
}
|
||||
|
||||
wsialloc_format allocated_format = { 0 };
|
||||
TRY_LOG_CALL(allocate_wsialloc(image_create_info, image_data, importable_formats, &allocated_format));
|
||||
|
||||
TRY_LOG_CALL(fill_image_create_info(
|
||||
image_create_info, m_image_creation_parameters.m_image_layout, m_image_creation_parameters.m_drm_mod_info,
|
||||
m_image_creation_parameters.m_external_info, *image_data, allocated_format.modifier));
|
||||
|
||||
m_image_create_info = image_create_info;
|
||||
m_allocated_format = allocated_format;
|
||||
}
|
||||
|
||||
TRY_LOG(m_device_data.disp.CreateImage(m_device, &m_image_create_info, get_allocation_callbacks(), image),
|
||||
"Image creation failed");
|
||||
return VK_SUCCESS;
|
||||
}
|
||||
|
||||
|
|
@ -389,20 +367,14 @@ VkResult swapchain::create_wl_buffer(const VkImageCreateInfo &image_create_info,
|
|||
return VK_SUCCESS;
|
||||
}
|
||||
|
||||
VkResult swapchain::create_and_bind_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image)
|
||||
VkResult swapchain::allocate_and_bind_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image)
|
||||
{
|
||||
/* Create image_data */
|
||||
auto image_data = m_allocator.create<wayland_image_data>(1, m_device, m_allocator);
|
||||
if (image_data == nullptr)
|
||||
{
|
||||
return VK_ERROR_OUT_OF_HOST_MEMORY;
|
||||
}
|
||||
|
||||
std::unique_lock<std::recursive_mutex> image_status_lock(m_image_status_mutex);
|
||||
image.data = image_data;
|
||||
image.status = swapchain_image::FREE;
|
||||
|
||||
TRY_LOG(allocate_image(image_create_info, image_data, &image.image), "Failed to allocate image");
|
||||
assert(image.data != nullptr);
|
||||
auto image_data = static_cast<wayland_image_data *>(image.data);
|
||||
TRY_LOG(allocate_image(image_create_info, image_data), "Failed to allocate image");
|
||||
image_status_lock.unlock();
|
||||
|
||||
TRY_LOG(create_wl_buffer(image_create_info, image, image_data), "Failed to create wl_buffer");
|
||||
|
|
@ -421,6 +393,44 @@ VkResult swapchain::create_and_bind_swapchain_image(VkImageCreateInfo image_crea
|
|||
return VK_SUCCESS;
|
||||
}
|
||||
|
||||
VkResult swapchain::create_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image)
|
||||
{
|
||||
/* Create image_data */
|
||||
auto image_data = m_allocator.create<wayland_image_data>(1, m_device, m_allocator);
|
||||
if (image_data == nullptr)
|
||||
{
|
||||
return VK_ERROR_OUT_OF_HOST_MEMORY;
|
||||
}
|
||||
image.data = image_data;
|
||||
|
||||
if (m_image_create_info.format == VK_FORMAT_UNDEFINED)
|
||||
{
|
||||
util::vector<wsialloc_format> importable_formats(
|
||||
util::allocator(m_allocator, VK_SYSTEM_ALLOCATION_SCOPE_COMMAND));
|
||||
util::vector<uint64_t> exportable_modifiers(util::allocator(m_allocator, VK_SYSTEM_ALLOCATION_SCOPE_COMMAND));
|
||||
TRY_LOG_CALL(get_surface_compatible_formats(image_create_info, importable_formats, exportable_modifiers));
|
||||
|
||||
/* TODO: Handle exportable images which use ICD allocated memory in preference to an external allocator. */
|
||||
if (importable_formats.empty())
|
||||
{
|
||||
WSI_LOG_ERROR("Export/Import not supported.");
|
||||
return VK_ERROR_INITIALIZATION_FAILED;
|
||||
}
|
||||
|
||||
wsialloc_format allocated_format = { 0 };
|
||||
TRY_LOG_CALL(allocate_wsialloc(image_create_info, image_data, importable_formats, &allocated_format, true));
|
||||
|
||||
TRY_LOG_CALL(fill_image_create_info(
|
||||
image_create_info, m_image_creation_parameters.m_image_layout, m_image_creation_parameters.m_drm_mod_info,
|
||||
m_image_creation_parameters.m_external_info, *image_data, allocated_format.modifier));
|
||||
|
||||
m_image_create_info = image_create_info;
|
||||
m_image_creation_parameters.m_allocated_format = allocated_format;
|
||||
}
|
||||
|
||||
return m_device_data.disp.CreateImage(m_device, &m_image_create_info, get_allocation_callbacks(), &image.image);
|
||||
}
|
||||
|
||||
void swapchain::present_image(uint32_t pendingIndex)
|
||||
{
|
||||
int res;
|
||||
|
|
|
|||
|
|
@ -94,7 +94,17 @@ protected:
|
|||
bool &use_presentation_thread) override;
|
||||
|
||||
/**
|
||||
* @brief Creates and binds a new swapchain image.
|
||||
* @brief Allocates and binds a new swapchain image.
|
||||
*
|
||||
* @param image_create_info Data to be used to create the image.
|
||||
* @param image Handle to the image.
|
||||
*
|
||||
* @return Returns VK_SUCCESS on success, otherwise an appropriate error code.
|
||||
*/
|
||||
VkResult allocate_and_bind_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) override;
|
||||
|
||||
/**
|
||||
* @brief Creates a new swapchain image.
|
||||
*
|
||||
* @param image_create_info Data to be used to create the image.
|
||||
* @param image Handle to the image.
|
||||
|
|
@ -103,7 +113,7 @@ protected:
|
|||
* will return VK_ERROR_OUT_OF_DEVICE_MEMORY or VK_ERROR_INITIALIZATION_FAILED
|
||||
* depending on the error that occurred.
|
||||
*/
|
||||
VkResult create_and_bind_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) override;
|
||||
VkResult create_swapchain_image(VkImageCreateInfo image_create_info, swapchain_image &image) override;
|
||||
|
||||
/**
|
||||
* @brief Method to present an image
|
||||
|
|
@ -158,9 +168,10 @@ protected:
|
|||
private:
|
||||
VkResult create_wl_buffer(const VkImageCreateInfo &image_create_info, swapchain_image &image,
|
||||
wayland_image_data *image_data);
|
||||
VkResult allocate_image(VkImageCreateInfo &image_create_info, wayland_image_data *image_data, VkImage *image);
|
||||
VkResult allocate_image(VkImageCreateInfo &image_create_info, wayland_image_data *image_data);
|
||||
VkResult allocate_wsialloc(VkImageCreateInfo &image_create_info, wayland_image_data *image_data,
|
||||
util::vector<wsialloc_format> &importable_formats, wsialloc_format *allocated_format);
|
||||
util::vector<wsialloc_format> &importable_formats, wsialloc_format *allocated_format,
|
||||
bool avoid_allocation);
|
||||
|
||||
struct wl_display *m_display;
|
||||
struct wl_surface *m_surface;
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue