VkImage image{VK_NULL_HANDLE};
VkFence present_fence{VK_NULL_HANDLE};
+
+#ifdef USE_ICD_MALI_NIKEM
+ bool is_external{false};
+#endif
};
/**
* otherwise returns VK_SUCCESS.
*/
VkResult queue_present(VkQueue queue, const VkPresentInfoKHR *present_info, const uint32_t image_index, const VkPresentRegionKHR *region);
+#ifdef USE_ICD_MALI_NIKEM
+ VkResult create_swapchain_images(VkImageCreateInfo* pCreateInfo,
+ const VkAllocationCallbacks* pAllocator,
+ VkImage* pImage);
+ VkResult bind_swapchain_images(const uint32_t image_index, VkImage image);
+#endif
protected:
layer::device_private_data &m_device_data;
* @param image Handle to the image about to be released.
*/
virtual void destroy_image(void){};
+#ifdef USE_ICD_MALI_NIKEM
+ virtual VkResult create_external_image(VkImageCreateInfo* pCreateInfo,
+ const VkAllocationCallbacks* pAllocator, VkImage* pImage) = 0;
+ virtual VkResult bind_external_image(const uint32_t image_index, VkImage image) = 0;
+#endif
};
} /* namespace wsi */
{
int buffer_fd;
tbm_surface_h tbm_buffer;
-
- int stride;
- uint32_t offset;
-
+#ifndef USE_ICD_MALI_NIKEM
+ VkDeviceSize stride; // rowPitch
+ VkDeviceSize offset;
+#endif
VkDeviceMemory memory;
};
{
VkResult result = VK_SUCCESS;
+#ifndef USE_ICD_MALI_NIKEM
assert(image_data->stride >= 0);
VkSubresourceLayout image_layout = {};
image_layout.offset = image_data->offset;
- image_layout.rowPitch = static_cast<uint32_t>(image_data->stride);
+ image_layout.rowPitch = image_data->stride;
VkImageDrmFormatModifierExplicitCreateInfoEXT drm_mod_info = {};
drm_mod_info.sType = VK_STRUCTURE_TYPE_IMAGE_DRM_FORMAT_MODIFIER_EXPLICIT_CREATE_INFO_EXT;
drm_mod_info.pNext = image_create_info.pNext;
drm_mod_info.drmFormatModifier = DRM_FORMAT_MOD_LINEAR;
drm_mod_info.drmFormatModifierPlaneCount = 1;
drm_mod_info.pPlaneLayouts = &image_layout;
+#endif
+
VkExternalMemoryImageCreateInfoKHR external_info = {};
external_info.sType = VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_IMAGE_CREATE_INFO_KHR;
+#ifndef USE_ICD_MALI_NIKEM
external_info.pNext = &drm_mod_info;
+#else
+ external_info.pNext = image_create_info.pNext;
+#endif
external_info.handleTypes = VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
VkImageCreateInfo image_info = image_create_info;
goto out;
}
- tbm_surface_info_s info;
tbm_bo bo = tbm_surface_internal_get_bo(buffers[i], 0);
tbm_bo_handle bo_handle = tbm_bo_get_handle(bo, TBM_DEVICE_3D);
- tbm_surface_get_info(buffers[i], &info);
-
image_data->tbm_buffer = buffers[i];
image_data->buffer_fd = bo_handle.u32;//tbm_bo_export_fd(bo);
- image_data->stride = info.planes[0].stride;
- image_data->offset = info.planes[0].offset;
image_data->memory = VK_NULL_HANDLE;
+#ifndef USE_ICD_MALI_NIKEM
+ tbm_surface_info_s info;
+ tbm_surface_get_info(buffers[i], &info);
+ image_data->stride = static_cast<VkDeviceSize>(info.planes[0].stride);
+ image_data->offset = static_cast<VkDeviceSize>(info.planes[0].offset);
+#endif
+
wsi_info("New image[%d] - tbm_buffer [%p], buffer fd [%d]", i, image_data->tbm_buffer, image_data->buffer_fd);
image.data = static_cast<void *>(image_data);
+#ifdef USE_ICD_MALI_NIKEM
+ image.is_external = false;
+#endif
result = allocate_image(image_create_info, image_data, &image.image);
if (result != VK_SUCCESS)
m_device_data.disp.DestroyFence(m_device, image.present_fence, get_allocation_callbacks());
image.present_fence = VK_NULL_HANDLE;
}
+#ifdef USE_ICD_MALI_NIKEM
+ if (image.image != VK_NULL_HANDLE && !image.is_external)
+#else
if (image.image != VK_NULL_HANDLE)
+#endif
{
m_device_data.disp.DestroyImage(m_device, image.image, get_allocation_callbacks());
image.image = VK_NULL_HANDLE;
}
}
+#ifdef USE_ICD_MALI_NIKEM
+VkResult swapchain::create_external_image(VkImageCreateInfo* pCreateInfo,
+ const VkAllocationCallbacks* pAllocator, VkImage* pImage)
+{
+ VkResult result = VK_SUCCESS;
+
+ VkExternalMemoryImageCreateInfoKHR external_info = {};
+ external_info.sType = VK_STRUCTURE_TYPE_EXTERNAL_MEMORY_IMAGE_CREATE_INFO_KHR;
+ external_info.pNext = pCreateInfo->pNext;
+ external_info.handleTypes = VK_EXTERNAL_MEMORY_HANDLE_TYPE_DMA_BUF_BIT_EXT;
+
+ pCreateInfo->pNext = &external_info;
+ pCreateInfo->tiling = VK_IMAGE_TILING_LINEAR;
+
+ for (VkBaseOutStructure *s = (VkBaseOutStructure *)(pCreateInfo); s != nullptr; s = s->pNext) {
+ if (((VkBaseOutStructure *)(s->pNext))->sType == VK_STRUCTURE_TYPE_IMAGE_SWAPCHAIN_CREATE_INFO_KHR) {
+ s->pNext = ((VkBaseOutStructure *)(s->pNext))->pNext;
+ }
+ }
+
+ result = m_device_data.disp.CreateImage(m_device, pCreateInfo, get_allocation_callbacks(), pImage);
+ if (result != VK_SUCCESS) {
+ wsi_error("Image creation failed.\n");
+ }
+
+ return result;
+}
+
+VkResult swapchain::bind_external_image(const uint32_t image_index, VkImage image)
+{
+ VkResult result = VK_SUCCESS;
+ tizen_image_data *image_data = reinterpret_cast<tizen_image_data *>(m_swapchain_images[image_index].data);
+
+ assert(image_data != nullptr);
+ assert(image_data->memory != VK_NULL_HANDLE);
+
+ if (m_swapchain_images[image_index].image != VK_NULL_HANDLE)
+ m_device_data.disp.DestroyImage(m_device, m_swapchain_images[image_index].image, get_allocation_callbacks());
+
+ m_swapchain_images[image_index].image = image;
+
+ result = m_device_data.disp.BindImageMemory(m_device, image, image_data->memory, 0);
+ if (result == VK_SUCCESS) {
+ m_swapchain_images[image_index].is_external = true;
+ }
+
+ return result;
+}
+#endif
+
} // namespace wayland
} // namespace wsi