示例#1
0
文件: main.cpp 项目: Unix4ever/engine
static void cleanup_vulkan()
{
    vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator);
    for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
    {
        vkDestroyFence(g_Device, g_Fence[i], g_Allocator);
        vkFreeCommandBuffers(g_Device, g_CommandPool[i], 1, &g_CommandBuffer[i]);
        vkDestroyCommandPool(g_Device, g_CommandPool[i], g_Allocator);
        vkDestroySemaphore(g_Device, g_PresentCompleteSemaphore[i], g_Allocator);
        vkDestroySemaphore(g_Device, g_RenderCompleteSemaphore[i], g_Allocator);
    }
    for (uint32_t i = 0; i < g_BackBufferCount; i++)
    {
        vkDestroyImageView(g_Device, g_BackBufferView[i], g_Allocator);
        vkDestroyFramebuffer(g_Device, g_Framebuffer[i], g_Allocator);
    }
    vkDestroyRenderPass(g_Device, g_RenderPass, g_Allocator);
    vkDestroySwapchainKHR(g_Device, g_Swapchain, g_Allocator);
    vkDestroySurfaceKHR(g_Instance, g_Surface, g_Allocator);

#ifdef IMGUI_VULKAN_DEBUG_REPORT
    // get the proc address of the function pointer, required for used extensions
    auto vkDestroyDebugReportCallbackEXT = (PFN_vkDestroyDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkDestroyDebugReportCallbackEXT");
    vkDestroyDebugReportCallbackEXT(g_Instance, g_Debug_Report, g_Allocator);
#endif // IMGUI_VULKAN_DEBUG_REPORT

    vkDestroyDevice(g_Device, g_Allocator);
    vkDestroyInstance(g_Instance, g_Allocator);
}
void VulkanTexturedQuad::ShutdownImpl()
{
    vkDestroyPipeline(device_, pipeline_, nullptr);
    vkDestroyPipelineLayout(device_, pipelineLayout_, nullptr);

    vkDestroyBuffer(device_, vertexBuffer_, nullptr);
    vkDestroyBuffer(device_, indexBuffer_, nullptr);
    vkFreeMemory(device_, deviceBufferMemory_, nullptr);

    vkDestroyImageView (device_, rubyImageView_, nullptr);
    vkDestroyImage (device_, rubyImage_, nullptr);
    vkFreeMemory (device_, deviceImageMemory_, nullptr);

    vkDestroyBuffer (device_, uploadImageBuffer_, nullptr);
    vkFreeMemory (device_, uploadImageMemory_, nullptr);

    vkDestroyBuffer (device_, uploadBufferBuffer_, nullptr);
    vkFreeMemory (device_, uploadBufferMemory_, nullptr);

    vkDestroyDescriptorSetLayout (device_, descriptorSetLayout_, nullptr);
    vkDestroyDescriptorPool (device_, descriptorPool_, nullptr);

    vkDestroySampler (device_, sampler_, nullptr);

    vkDestroyShaderModule(device_, vertexShader_, nullptr);
    vkDestroyShaderModule(device_, fragmentShader_, nullptr);

    VulkanSample::ShutdownImpl();
}
void CommandBufferManager::DestroyCommandBuffers()
{
  VkDevice device = g_vulkan_context->GetDevice();

  for (FrameResources& resources : m_frame_resources)
  {
    // The Vulkan spec section 5.2 says: "When a pool is destroyed, all command buffers allocated
    // from the pool are freed.". So we don't need to free the command buffers, just the pools.
    // We destroy the command pool first, to avoid any warnings from the validation layers about
    // objects which are pending destruction being in-use.
    if (resources.command_pool != VK_NULL_HANDLE)
      vkDestroyCommandPool(device, resources.command_pool, nullptr);

    // Destroy any pending objects.
    for (auto& it : resources.cleanup_resources)
      it();

    if (resources.semaphore != VK_NULL_HANDLE)
      vkDestroySemaphore(device, resources.semaphore, nullptr);

    if (resources.fence != VK_NULL_HANDLE)
      vkDestroyFence(device, resources.fence, nullptr);

    if (resources.descriptor_pool != VK_NULL_HANDLE)
      vkDestroyDescriptorPool(device, resources.descriptor_pool, nullptr);
  }

  vkDestroySemaphore(device, m_present_semaphore, nullptr);
}
示例#4
0
void Application::deInitGraphicsDescriptor()
{
	//vkFreeDescriptorSets(renderer.getVkDevice(), descriptorPool, 1, &descriptorSet);

	vkDestroyDescriptorPool(renderer.getVkDevice(), graphicsDescriptorPool, nullptr);
	vkDestroyDescriptorSetLayout(renderer.getVkDevice(), graphicsDescriptorSetLayout, nullptr);
}
示例#5
0
void CommandBufferManager::DestroyCommandBuffers()
{
  VkDevice device = g_vulkan_context->GetDevice();

  for (FrameResources& resources : m_frame_resources)
  {
    for (auto& it : resources.cleanup_resources)
      it();
    resources.cleanup_resources.clear();

    if (resources.fence != VK_NULL_HANDLE)
    {
      vkDestroyFence(device, resources.fence, nullptr);
      resources.fence = VK_NULL_HANDLE;
    }
    if (resources.descriptor_pool != VK_NULL_HANDLE)
    {
      vkDestroyDescriptorPool(device, resources.descriptor_pool, nullptr);
      resources.descriptor_pool = VK_NULL_HANDLE;
    }
    if (resources.command_buffers[0] != VK_NULL_HANDLE)
    {
      vkFreeCommandBuffers(device, resources.command_pool,
                           static_cast<u32>(resources.command_buffers.size()),
                           resources.command_buffers.data());

      resources.command_buffers.fill(VK_NULL_HANDLE);
    }
    if (resources.command_pool != VK_NULL_HANDLE)
    {
      vkDestroyCommandPool(device, resources.command_pool, nullptr);
      resources.command_pool = VK_NULL_HANDLE;
    }
  }
}
示例#6
0
/**
 * Destroy the graphics pipeline.
 */
VkcPipeline::~VkcPipeline()
{
    if (logicalDevice != VK_NULL_HANDLE)
    {
        if (descriptorSet != VK_NULL_HANDLE)
            vkFreeDescriptorSets(logicalDevice, descriptorPool, 1, &descriptorSet);

        if (setLayout != VK_NULL_HANDLE)
            vkDestroyDescriptorSetLayout(logicalDevice, setLayout, nullptr);

        if (descriptorPool != VK_NULL_HANDLE)
            vkDestroyDescriptorPool(logicalDevice, descriptorPool, nullptr);

        if (vertShader != VK_NULL_HANDLE)
            vkDestroyShaderModule(logicalDevice, vertShader, nullptr);

        if (fragShader != VK_NULL_HANDLE)
            vkDestroyShaderModule(logicalDevice, fragShader, nullptr);

        if (layout != VK_NULL_HANDLE)
            vkDestroyPipelineLayout(logicalDevice, layout, nullptr);

        if (handle != VK_NULL_HANDLE)
            vkDestroyPipeline(logicalDevice, handle, nullptr);
    }
}
示例#7
0
void
VKDevice::destroy_desc_pool (VkDescriptorPool pool)
{
    XCAM_ASSERT (XCAM_IS_VALID_VK_ID (_dev_id));
    XCAM_ASSERT (XCAM_IS_VALID_VK_ID (pool));
    vkDestroyDescriptorPool (_dev_id, pool, _allocator.ptr ());
}
示例#8
0
/* Please see header for specification */
void Anvil::DescriptorPool::bake()
{
    VkDescriptorPoolCreateInfo descriptor_pool_create_info;
    VkDescriptorPoolSize       descriptor_pool_sizes[VK_DESCRIPTOR_TYPE_RANGE_SIZE];
    uint32_t                   n_descriptor_types_used = 0;
    VkResult                   result_vk;

    if (m_pool != VK_NULL_HANDLE)
    {
        vkDestroyDescriptorPool(m_device_ptr->get_device_vk(),
                                m_pool,
                                nullptr /* pAllocator */);

        m_pool = VK_NULL_HANDLE;
    }

    /* Convert the counters to an arrayed, linear representation */
    for (uint32_t n_descriptor_type = 0;
                  n_descriptor_type < VK_DESCRIPTOR_TYPE_RANGE_SIZE;
                ++n_descriptor_type)
    {
        if (m_descriptor_count[n_descriptor_type] > 0)
        {
            uint32_t current_index = n_descriptor_types_used;

            descriptor_pool_sizes[current_index].descriptorCount = m_descriptor_count[n_descriptor_type];
            descriptor_pool_sizes[current_index].type            = (VkDescriptorType) n_descriptor_type;

            n_descriptor_types_used++;
        }
    }

    if (n_descriptor_types_used == 0)
    {
        /* If an empty pool is needed, request space for a single dummy descriptor. */
        descriptor_pool_sizes[0].descriptorCount = 1;
        descriptor_pool_sizes[0].type            = VK_DESCRIPTOR_TYPE_SAMPLER;

        n_descriptor_types_used = 1;
    }

    /* Set up the descriptor pool instance */
    descriptor_pool_create_info.flags         = (m_releaseable_sets) ? VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT
                                                                     : 0;
    descriptor_pool_create_info.maxSets       = m_n_max_sets;
    descriptor_pool_create_info.pNext         = nullptr;
    descriptor_pool_create_info.poolSizeCount = n_descriptor_types_used;
    descriptor_pool_create_info.pPoolSizes    = descriptor_pool_sizes;
    descriptor_pool_create_info.sType         = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO;

    result_vk = vkCreateDescriptorPool(m_device_ptr->get_device_vk(),
                                      &descriptor_pool_create_info,
                                       nullptr, /* pAllocator */
                                      &m_pool);

    anvil_assert_vk_call_succeeded(result_vk);

    m_baked = true;
}
 void VulkanUniformBuffer::FinalizeDescriptorPool()
 {
     if ( mVkDescriptorPool != VK_NULL_HANDLE )
     {
         vkDestroyDescriptorPool ( mVulkanRenderer.GetDevice(), mVkDescriptorPool, nullptr );
         mVkDescriptorPool = VK_NULL_HANDLE;
     }
 }
示例#10
0
VulkanExampleBase::~VulkanExampleBase()
{
	// Clean up Vulkan resources
	swapChain.cleanup();
	if (descriptorPool != VK_NULL_HANDLE)
	{
		vkDestroyDescriptorPool(device, descriptorPool, nullptr);
	}
	if (setupCmdBuffer != VK_NULL_HANDLE)
	{
		vkFreeCommandBuffers(device, cmdPool, 1, &setupCmdBuffer);

	}
	destroyCommandBuffers();
	vkDestroyRenderPass(device, renderPass, nullptr);
	for (uint32_t i = 0; i < frameBuffers.size(); i++)
	{
		vkDestroyFramebuffer(device, frameBuffers[i], nullptr);
	}

	for (auto& shaderModule : shaderModules)
	{
		vkDestroyShaderModule(device, shaderModule, nullptr);
	}
	vkDestroyImageView(device, depthStencil.view, nullptr);
	vkDestroyImage(device, depthStencil.image, nullptr);
	vkFreeMemory(device, depthStencil.mem, nullptr);

	vkDestroyPipelineCache(device, pipelineCache, nullptr);

	if (textureLoader)
	{
		delete textureLoader;
	}

	vkDestroyCommandPool(device, cmdPool, nullptr);

	vkDestroySemaphore(device, semaphores.presentComplete, nullptr);
	vkDestroySemaphore(device, semaphores.renderComplete, nullptr);

	vkDestroyDevice(device, nullptr);

	if (enableValidation)
	{
		vkDebug::freeDebugCallback(instance);
	}

	vkDestroyInstance(instance, nullptr);

#if defined(__linux)
#if defined(__ANDROID__)
	// todo : android cleanup (if required)
#else
	xcb_destroy_window(connection, window);
	xcb_disconnect(connection);
#endif
#endif
}
示例#11
0
void DescriptorSetAllocator::destroy()
{
	if(m_globalDPool)
	{
		vkDestroyDescriptorPool(m_dev, m_globalDPool, nullptr);
		m_globalDPool = VK_NULL_HANDLE;
	}

	m_layoutFactory.destroy();
}
void DescriptorSetAllocator::clear()
{
	set_nodes.clear();
	for (auto &pool : pools)
	{
		vkResetDescriptorPool(device->get_device(), pool, 0);
		vkDestroyDescriptorPool(device->get_device(), pool, nullptr);
	}
	pools.clear();
}
//------------------------------------------------------------------------------
//
//------------------------------------------------------------------------------
bool RendererVk::terminateGraphics()
{
    if(!m_bValid)
        return true;
    // destroy the super-sampling pass system
    m_nvFBOBox.Finish();
    // destroys commandBuffers: but not really needed since m_cmdPool later gets destroyed
    nvk.vkDestroyFence(m_sceneFence[0]);
    m_sceneFence[0] = NULL;
    nvk.vkDestroyFence(m_sceneFence[1]);
    m_sceneFence[1] = NULL;
    nvk.vkFreeCommandBuffer(m_cmdPool, m_cmdScene[0]);
    m_cmdScene[0] = NULL;
    nvk.vkFreeCommandBuffer(m_cmdPool, m_cmdScene[1]);
    m_cmdScene[1] = NULL;

	nvk.vkDestroyCommandPool(m_cmdPool); // destroys commands that are inside, obviously

	for(int i=0; i<DSET_TOTALAMOUNT; i++)
	{
		vkDestroyDescriptorSetLayout(nvk.m_device, m_descriptorSetLayouts[i], NULL); // general layout and objects layout
		m_descriptorSetLayouts[i] = 0;
	}
	//vkFreeDescriptorSets(nvk.m_device, m_descPool, 1, &m_descriptorSetGlobal); // no really necessary: we will destroy the pool after that
    m_descriptorSetGlobal = NULL;

    vkDestroyDescriptorPool(nvk.m_device, m_descPool, NULL);
    m_descPool = NULL;

	vkDestroyPipelineLayout(nvk.m_device, m_pipelineLayout, NULL);
    m_pipelineLayout = NULL;

    vkDestroyPipeline(nvk.m_device, m_pipelinefur, NULL);
    m_pipelinefur = NULL;

    m_furBuffer.release();
    m_matrix.release();

    deinitTimers();

    nvk.vkDestroySemaphore(m_semOpenGLReadDone);
    nvk.vkDestroySemaphore(m_semVKRenderingDone);
    m_semOpenGLReadDone = NULL;
    m_semVKRenderingDone = NULL;
    //glGetVkInstanceProcAddrNV = NULL;
    glWaitVkSemaphoreNV = NULL;
    glSignalVkSemaphoreNV = NULL;
    glSignalVkFenceNV = NULL;
    glDrawVkImageNV = NULL;

    nvk.DestroyDevice();

    m_bValid = false;
    return false;
}
示例#14
0
文件: main.cpp 项目: Kimau/ludumdare
static void CleanupVulkan()
{
    ImGui_ImplVulkanH_WindowData* wd = &g_WindowData;
    ImGui_ImplVulkanH_DestroyWindowData(g_Instance, g_Device, wd, g_Allocator);
    vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator);

#ifdef IMGUI_VULKAN_DEBUG_REPORT
    // Remove the debug report callback
    auto vkDestroyDebugReportCallbackEXT = (PFN_vkDestroyDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkDestroyDebugReportCallbackEXT");
    vkDestroyDebugReportCallbackEXT(g_Instance, g_DebugReport, g_Allocator);
#endif // IMGUI_VULKAN_DEBUG_REPORT

    vkDestroyDevice(g_Device, g_Allocator);
    vkDestroyInstance(g_Instance, g_Allocator);
}
示例#15
0
/* Please see header for specification */
Anvil::DescriptorPool::~DescriptorPool()
{
    if (m_pool != VK_NULL_HANDLE)
    {
        vkDestroyDescriptorPool(m_device_ptr->get_device_vk(),
                                m_pool,
                                nullptr /* pAllocator */);

        m_pool = VK_NULL_HANDLE;
    }

    /* Unregister the instance */
    Anvil::ObjectTracker::get()->unregister_object(Anvil::ObjectTracker::OBJECT_TYPE_DESCRIPTOR_POOL,
                                                    this);
}
示例#16
0
	/**
	* Default destructor, frees up all Vulkan resources acquired by the text overlay
	*/
	~VulkanTextOverlay()
	{
		// Free up all Vulkan resources requested by the text overlay
		vertexBuffer.destroy();
		vkDestroySampler(vulkanDevice->logicalDevice, sampler, nullptr);
		vkDestroyImage(vulkanDevice->logicalDevice, image, nullptr);
		vkDestroyImageView(vulkanDevice->logicalDevice, view, nullptr);
		vkFreeMemory(vulkanDevice->logicalDevice, imageMemory, nullptr);
		vkDestroyDescriptorSetLayout(vulkanDevice->logicalDevice, descriptorSetLayout, nullptr);
		vkDestroyDescriptorPool(vulkanDevice->logicalDevice, descriptorPool, nullptr);
		vkDestroyPipelineLayout(vulkanDevice->logicalDevice, pipelineLayout, nullptr);
		vkDestroyPipelineCache(vulkanDevice->logicalDevice, pipelineCache, nullptr);
		vkDestroyPipeline(vulkanDevice->logicalDevice, pipeline, nullptr);
		vkDestroyRenderPass(vulkanDevice->logicalDevice, renderPass, nullptr);
		vkFreeCommandBuffers(vulkanDevice->logicalDevice, commandPool, static_cast<uint32_t>(cmdBuffers.size()), cmdBuffers.data());
		vkDestroyCommandPool(vulkanDevice->logicalDevice, commandPool, nullptr);
		vkDestroyFence(vulkanDevice->logicalDevice, fence, nullptr);
	}
示例#17
0
void WMaterial::_DestroyResources() {
	VkDevice device = m_app->GetVulkanDevice();

	W_SAFE_REMOVEREF(m_effect);

	for (int i = 0; i < m_uniformBuffers.size(); i++) {
		vkFreeMemory(device, m_uniformBuffers[i].memory, nullptr);
		vkDestroyBuffer(device, m_uniformBuffers[i].descriptor.buffer, nullptr);
	}
	m_uniformBuffers.clear();

	for (int i = 0; i < m_sampler_info.size(); i++) {
		if (m_sampler_info[i].img)
			m_sampler_info[i].img->RemoveReference();
	}
	m_sampler_info.clear();

	if (m_descriptorPool)
		vkDestroyDescriptorPool(device, m_descriptorPool, nullptr);

	m_descriptorSet = VK_NULL_HANDLE;
	m_descriptorPool = VK_NULL_HANDLE;
}
示例#18
0
VulkanBase::~VulkanBase() {
	swapChain.cleanup();
	vkDestroyDescriptorPool(device, descriptorPool, nullptr);

	if (setupCmdBuffer != VK_NULL_HANDLE)
		vkFreeCommandBuffers(device, cmdPool, 1, &setupCmdBuffer);

	destroyCommandBuffers();
	vkDestroyRenderPass(device, renderPass, nullptr);

	for (uint32_t i = 0; i < frameBuffers.size(); i++)
		vkDestroyFramebuffer(device, frameBuffers[i], nullptr);

	for (auto& shaderModule : shaderModules)
		vkDestroyShaderModule(device, shaderModule, nullptr);

	vkDestroyImageView(device, depthStencil.view, nullptr);
	vkDestroyImage(device, depthStencil.image, nullptr);
	vkFreeMemory(device, depthStencil.mem, nullptr);

	vkDestroyPipelineCache(device, pipelineCache, nullptr);

	if (textureLoader)
		delete textureLoader;

	vkDestroyCommandPool(device, cmdPool, nullptr);

	vkDestroySemaphore(device, semaphores.presentComplete, nullptr);
	vkDestroySemaphore(device, semaphores.renderComplete, nullptr);

	vkDestroyDevice(device, nullptr);

	if (enableValidation)
		vkDebug::freeDebugCallback(instance);

	vkDestroyInstance(instance, nullptr);
}
示例#19
0
int sample_main(int argc, char *argv[]) {
    VkResult U_ASSERT_ONLY res;
    struct sample_info info = {};
    char sample_title[] = "Multiple Descriptor Sets";

    process_command_line_args(info, argc, argv);
    init_global_layer_properties(info);
    init_instance_extension_names(info);
    init_device_extension_names(info);
    init_instance(info, sample_title);
    init_enumerate_device(info);
    init_window_size(info, 500, 500);
    init_connection(info);
    init_window(info);
    init_swapchain_extension(info);
    init_device(info);
    init_command_pool(info);
    init_command_buffer(info);
    execute_begin_command_buffer(info);
    init_device_queue(info);
    init_swap_chain(info);
    init_depth_buffer(info);
    // Sample from a green texture to easily see that we've pulled correct texel
    // value
    const char *textureName = "green.ppm";
    init_texture(info, textureName);
    init_uniform_buffer(info);
    init_renderpass(info, true);
    init_shaders(info, vertShaderText, fragShaderText);
    init_framebuffers(info, true);
    init_vertex_buffer(info, g_vb_texture_Data, sizeof(g_vb_texture_Data), sizeof(g_vb_texture_Data[0]), true);

    /* VULKAN_KEY_START */

    // Set up two descriptor sets
    static const unsigned descriptor_set_count = 2;

    // Create first layout to contain uniform buffer data
    VkDescriptorSetLayoutBinding uniform_binding[1] = {};
    uniform_binding[0].binding = 0;
    uniform_binding[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    uniform_binding[0].descriptorCount = 1;
    uniform_binding[0].stageFlags = VK_SHADER_STAGE_VERTEX_BIT;
    uniform_binding[0].pImmutableSamplers = NULL;
    VkDescriptorSetLayoutCreateInfo uniform_layout_info[1] = {};
    uniform_layout_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO;
    uniform_layout_info[0].pNext = NULL;
    uniform_layout_info[0].bindingCount = 1;
    uniform_layout_info[0].pBindings = uniform_binding;

    // Create second layout containing combined sampler/image data
    VkDescriptorSetLayoutBinding sampler2D_binding[1] = {};
    sampler2D_binding[0].binding = 0;
    sampler2D_binding[0].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    sampler2D_binding[0].descriptorCount = 1;
    sampler2D_binding[0].stageFlags = VK_SHADER_STAGE_VERTEX_BIT;
    sampler2D_binding[0].pImmutableSamplers = NULL;
    VkDescriptorSetLayoutCreateInfo sampler2D_layout_info[1] = {};
    sampler2D_layout_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO;
    sampler2D_layout_info[0].pNext = NULL;
    sampler2D_layout_info[0].bindingCount = 1;
    sampler2D_layout_info[0].pBindings = sampler2D_binding;

    // Create multiple sets, using each createInfo
    static const unsigned uniform_set_index = 0;
    static const unsigned sampler_set_index = 1;
    VkDescriptorSetLayout descriptor_layouts[descriptor_set_count] = {};
    res = vkCreateDescriptorSetLayout(info.device, uniform_layout_info, NULL, &descriptor_layouts[uniform_set_index]);
    assert(res == VK_SUCCESS);
    res = vkCreateDescriptorSetLayout(info.device, sampler2D_layout_info, NULL, &descriptor_layouts[sampler_set_index]);
    assert(res == VK_SUCCESS);

    // Create pipeline layout with multiple descriptor sets
    VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo[1] = {};
    pipelineLayoutCreateInfo[0].sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
    pipelineLayoutCreateInfo[0].pNext = NULL;
    pipelineLayoutCreateInfo[0].pushConstantRangeCount = 0;
    pipelineLayoutCreateInfo[0].pPushConstantRanges = NULL;
    pipelineLayoutCreateInfo[0].setLayoutCount = descriptor_set_count;
    pipelineLayoutCreateInfo[0].pSetLayouts = descriptor_layouts;
    res = vkCreatePipelineLayout(info.device, pipelineLayoutCreateInfo, NULL, &info.pipeline_layout);
    assert(res == VK_SUCCESS);

    // Create a single pool to contain data for our two descriptor sets
    VkDescriptorPoolSize type_count[2] = {};
    type_count[0].type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    type_count[0].descriptorCount = 1;
    type_count[1].type = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    type_count[1].descriptorCount = 1;

    VkDescriptorPoolCreateInfo pool_info[1] = {};
    pool_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO;
    pool_info[0].pNext = NULL;
    pool_info[0].maxSets = descriptor_set_count;
    pool_info[0].poolSizeCount = sizeof(type_count) / sizeof(VkDescriptorPoolSize);
    pool_info[0].pPoolSizes = type_count;

    VkDescriptorPool descriptor_pool[1] = {};
    res = vkCreateDescriptorPool(info.device, pool_info, NULL, descriptor_pool);
    assert(res == VK_SUCCESS);

    VkDescriptorSetAllocateInfo alloc_info[1];
    alloc_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
    alloc_info[0].pNext = NULL;
    alloc_info[0].descriptorPool = descriptor_pool[0];
    alloc_info[0].descriptorSetCount = descriptor_set_count;
    alloc_info[0].pSetLayouts = descriptor_layouts;

    // Populate descriptor sets
    VkDescriptorSet descriptor_sets[descriptor_set_count] = {};
    res = vkAllocateDescriptorSets(info.device, alloc_info, descriptor_sets);
    assert(res == VK_SUCCESS);

    // Using empty brace initializer on the next line triggers a bug in older
    // versions of gcc, so memset instead
    VkWriteDescriptorSet descriptor_writes[2];
    memset(descriptor_writes, 0, sizeof(descriptor_writes));

    // Populate with info about our uniform buffer
    descriptor_writes[0] = {};
    descriptor_writes[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descriptor_writes[0].pNext = NULL;
    descriptor_writes[0].dstSet = descriptor_sets[uniform_set_index];
    descriptor_writes[0].descriptorCount = 1;
    descriptor_writes[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    descriptor_writes[0].pBufferInfo = &info.uniform_data.buffer_info;  // populated by init_uniform_buffer()
    descriptor_writes[0].dstArrayElement = 0;
    descriptor_writes[0].dstBinding = 0;

    // Populate with info about our sampled image
    descriptor_writes[1] = {};
    descriptor_writes[1].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descriptor_writes[1].pNext = NULL;
    descriptor_writes[1].dstSet = descriptor_sets[sampler_set_index];
    descriptor_writes[1].descriptorCount = 1;
    descriptor_writes[1].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    descriptor_writes[1].pImageInfo = &info.texture_data.image_info;  // populated by init_texture()
    descriptor_writes[1].dstArrayElement = 0;
    descriptor_writes[1].dstBinding = 0;

    vkUpdateDescriptorSets(info.device, descriptor_set_count, descriptor_writes, 0, NULL);

    /* VULKAN_KEY_END */

    // Call remaining boilerplate utils
    init_pipeline_cache(info);
    init_pipeline(info, true);

    // The remaining is identical to drawtexturedcube
    VkClearValue clear_values[2];
    clear_values[0].color.float32[0] = 0.2f;
    clear_values[0].color.float32[1] = 0.2f;
    clear_values[0].color.float32[2] = 0.2f;
    clear_values[0].color.float32[3] = 0.2f;
    clear_values[1].depthStencil.depth = 1.0f;
    clear_values[1].depthStencil.stencil = 0;

    VkSemaphore imageAcquiredSemaphore;
    VkSemaphoreCreateInfo imageAcquiredSemaphoreCreateInfo;
    imageAcquiredSemaphoreCreateInfo.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO;
    imageAcquiredSemaphoreCreateInfo.pNext = NULL;
    imageAcquiredSemaphoreCreateInfo.flags = 0;

    res = vkCreateSemaphore(info.device, &imageAcquiredSemaphoreCreateInfo, NULL, &imageAcquiredSemaphore);
    assert(res == VK_SUCCESS);

    // Get the index of the next available swapchain image:
    res = vkAcquireNextImageKHR(info.device, info.swap_chain, UINT64_MAX, imageAcquiredSemaphore, VK_NULL_HANDLE,
                                &info.current_buffer);
    // TODO: Deal with the VK_SUBOPTIMAL_KHR and VK_ERROR_OUT_OF_DATE_KHR
    // return codes
    assert(res == VK_SUCCESS);

    VkRenderPassBeginInfo rp_begin;
    rp_begin.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO;
    rp_begin.pNext = NULL;
    rp_begin.renderPass = info.render_pass;
    rp_begin.framebuffer = info.framebuffers[info.current_buffer];
    rp_begin.renderArea.offset.x = 0;
    rp_begin.renderArea.offset.y = 0;
    rp_begin.renderArea.extent.width = info.width;
    rp_begin.renderArea.extent.height = info.height;
    rp_begin.clearValueCount = 2;
    rp_begin.pClearValues = clear_values;

    vkCmdBeginRenderPass(info.cmd, &rp_begin, VK_SUBPASS_CONTENTS_INLINE);

    vkCmdBindPipeline(info.cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, info.pipeline);
    vkCmdBindDescriptorSets(info.cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, info.pipeline_layout, 0, descriptor_set_count,
                            descriptor_sets, 0, NULL);

    const VkDeviceSize offsets[1] = {0};
    vkCmdBindVertexBuffers(info.cmd, 0, 1, &info.vertex_buffer.buf, offsets);

    init_viewports(info);
    init_scissors(info);

    vkCmdDraw(info.cmd, 12 * 3, 1, 0, 0);
    vkCmdEndRenderPass(info.cmd);
    res = vkEndCommandBuffer(info.cmd);
    assert(res == VK_SUCCESS);

    const VkCommandBuffer cmd_bufs[] = {info.cmd};
    VkFenceCreateInfo fenceInfo;
    VkFence drawFence;
    fenceInfo.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO;
    fenceInfo.pNext = NULL;
    fenceInfo.flags = 0;
    vkCreateFence(info.device, &fenceInfo, NULL, &drawFence);

    VkPipelineStageFlags pipe_stage_flags = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT;
    VkSubmitInfo submit_info[1] = {};
    submit_info[0].pNext = NULL;
    submit_info[0].sType = VK_STRUCTURE_TYPE_SUBMIT_INFO;
    submit_info[0].waitSemaphoreCount = 1;
    submit_info[0].pWaitSemaphores = &imageAcquiredSemaphore;
    submit_info[0].pWaitDstStageMask = &pipe_stage_flags;
    submit_info[0].commandBufferCount = 1;
    submit_info[0].pCommandBuffers = cmd_bufs;
    submit_info[0].signalSemaphoreCount = 0;
    submit_info[0].pSignalSemaphores = NULL;

    /* Queue the command buffer for execution */
    res = vkQueueSubmit(info.graphics_queue, 1, submit_info, drawFence);
    assert(res == VK_SUCCESS);

    /* Now present the image in the window */

    VkPresentInfoKHR present;
    present.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
    present.pNext = NULL;
    present.swapchainCount = 1;
    present.pSwapchains = &info.swap_chain;
    present.pImageIndices = &info.current_buffer;
    present.pWaitSemaphores = NULL;
    present.waitSemaphoreCount = 0;
    present.pResults = NULL;

    /* Make sure command buffer is finished before presenting */
    do {
        res = vkWaitForFences(info.device, 1, &drawFence, VK_TRUE, FENCE_TIMEOUT);
    } while (res == VK_TIMEOUT);
    assert(res == VK_SUCCESS);
    res = vkQueuePresentKHR(info.present_queue, &present);
    assert(res == VK_SUCCESS);

    wait_seconds(1);
    if (info.save_images) write_ppm(info, "multiple_sets");

    vkDestroySemaphore(info.device, imageAcquiredSemaphore, NULL);
    vkDestroyFence(info.device, drawFence, NULL);
    destroy_pipeline(info);
    destroy_pipeline_cache(info);
    destroy_textures(info);

    // instead of destroy_descriptor_pool(info);
    vkDestroyDescriptorPool(info.device, descriptor_pool[0], NULL);

    destroy_vertex_buffer(info);
    destroy_framebuffers(info);
    destroy_shaders(info);
    destroy_renderpass(info);

    // instead of destroy_descriptor_and_pipeline_layouts(info);
    for (int i = 0; i < descriptor_set_count; i++) vkDestroyDescriptorSetLayout(info.device, descriptor_layouts[i], NULL);
    vkDestroyPipelineLayout(info.device, info.pipeline_layout, NULL);

    destroy_uniform_buffer(info);
    destroy_depth_buffer(info);
    destroy_swap_chain(info);
    destroy_command_buffer(info);
    destroy_command_pool(info);
    destroy_device(info);
    destroy_window(info);
    destroy_instance(info);
    return 0;
}
示例#20
0
DescriptorPool::~DescriptorPool()
{
	// TODO: Make sure all descriptor sets allocated from pool have been destroyed
	vkDestroyDescriptorPool(m_Device->GetHandle(), m_Handle, nullptr);
}
示例#21
0
void VulkanDeleteList::PerformDeletes(VkDevice device) {
	for (auto &cmdPool : cmdPools_) {
		vkDestroyCommandPool(device, cmdPool, nullptr);
	}
	cmdPools_.clear();
	for (auto &descPool : descPools_) {
		vkDestroyDescriptorPool(device, descPool, nullptr);
	}
	descPools_.clear();
	for (auto &module : modules_) {
		vkDestroyShaderModule(device, module, nullptr);
	}
	modules_.clear();
	for (auto &buf : buffers_) {
		vkDestroyBuffer(device, buf, nullptr);
	}
	buffers_.clear();
	for (auto &bufView : bufferViews_) {
		vkDestroyBufferView(device, bufView, nullptr);
	}
	bufferViews_.clear();
	for (auto &image : images_) {
		vkDestroyImage(device, image, nullptr);
	}
	images_.clear();
	for (auto &imageView : imageViews_) {
		vkDestroyImageView(device, imageView, nullptr);
	}
	imageViews_.clear();
	for (auto &mem : deviceMemory_) {
		vkFreeMemory(device, mem, nullptr);
	}
	deviceMemory_.clear();
	for (auto &sampler : samplers_) {
		vkDestroySampler(device, sampler, nullptr);
	}
	samplers_.clear();
	for (auto &pipeline : pipelines_) {
		vkDestroyPipeline(device, pipeline, nullptr);
	}
	pipelines_.clear();
	for (auto &pcache : pipelineCaches_) {
		vkDestroyPipelineCache(device, pcache, nullptr);
	}
	pipelineCaches_.clear();
	for (auto &renderPass : renderPasses_) {
		vkDestroyRenderPass(device, renderPass, nullptr);
	}
	renderPasses_.clear();
	for (auto &framebuffer : framebuffers_) {
		vkDestroyFramebuffer(device, framebuffer, nullptr);
	}
	framebuffers_.clear();
	for (auto &pipeLayout : pipelineLayouts_) {
		vkDestroyPipelineLayout(device, pipeLayout, nullptr);
	}
	pipelineLayouts_.clear();
	for (auto &descSetLayout : descSetLayouts_) {
		vkDestroyDescriptorSetLayout(device, descSetLayout, nullptr);
	}
	descSetLayouts_.clear();
	for (auto &callback : callbacks_) {
		callback.func(callback.userdata);
	}
	callbacks_.clear();
}
int sample_main(int argc, char *argv[]) {
    VkResult U_ASSERT_ONLY res;
    struct sample_info info = {};
    char sample_title[] = "Separate Image Sampler";
    const bool depthPresent = true;

    process_command_line_args(info, argc, argv);
    init_global_layer_properties(info);
    init_instance_extension_names(info);
    init_device_extension_names(info);
    init_instance(info, sample_title);
    init_enumerate_device(info);
    init_window_size(info, 500, 500);
    init_connection(info);
    init_window(info);
    init_swapchain_extension(info);
    init_device(info);
    init_command_pool(info);
    init_command_buffer(info);
    execute_begin_command_buffer(info);
    init_device_queue(info);
    init_swap_chain(info);
    init_depth_buffer(info);
    init_uniform_buffer(info);
    init_renderpass(info, depthPresent);
    init_shaders(info, vertShaderText, fragShaderText);
    init_framebuffers(info, depthPresent);
    init_vertex_buffer(info, g_vb_texture_Data, sizeof(g_vb_texture_Data), sizeof(g_vb_texture_Data[0]), true);

    /* VULKAN_KEY_START */

    // Sample from a green texture to easily see that we've pulled correct texel
    // value

    // Create our separate image
    struct texture_object texObj;
    const char *textureName = "green.ppm";
    init_image(info, texObj, textureName);

    info.textures.push_back(texObj);

    info.texture_data.image_info.sampler = 0;
    info.texture_data.image_info.imageView = info.textures[0].view;
    info.texture_data.image_info.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;

    // Create our separate sampler
    VkSampler separateSampler = {};
    init_sampler(info, separateSampler);

    VkDescriptorImageInfo samplerInfo = {};
    samplerInfo.sampler = separateSampler;

    // Set up one descriptor set
    static const unsigned descriptor_set_count = 1;
    static const unsigned resource_count = 3;
    static const unsigned resource_type_count = 3;

    // Create binding and layout for the following, matching contents of shader
    //   binding 0 = uniform buffer (MVP)
    //   binding 1 = texture2D
    //   binding 2 = sampler

    VkDescriptorSetLayoutBinding resource_binding[resource_count] = {};
    resource_binding[0].binding = 0;
    resource_binding[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    resource_binding[0].descriptorCount = 1;
    resource_binding[0].stageFlags = VK_SHADER_STAGE_VERTEX_BIT;
    resource_binding[0].pImmutableSamplers = NULL;
    resource_binding[1].binding = 1;
    resource_binding[1].descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
    resource_binding[1].descriptorCount = 1;
    resource_binding[1].stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT;
    resource_binding[1].pImmutableSamplers = NULL;
    resource_binding[2].binding = 2;
    resource_binding[2].descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER;
    resource_binding[2].descriptorCount = 1;
    resource_binding[2].stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT;
    resource_binding[2].pImmutableSamplers = NULL;

    VkDescriptorSetLayoutCreateInfo resource_layout_info[1] = {};
    resource_layout_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO;
    resource_layout_info[0].pNext = NULL;
    resource_layout_info[0].bindingCount = resource_count;
    resource_layout_info[0].pBindings = resource_binding;

    VkDescriptorSetLayout descriptor_layouts[1] = {};
    res = vkCreateDescriptorSetLayout(info.device, resource_layout_info, NULL, &descriptor_layouts[0]);

    assert(res == VK_SUCCESS);

    // Create pipeline layout
    VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo[1] = {};
    pipelineLayoutCreateInfo[0].sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
    pipelineLayoutCreateInfo[0].pNext = NULL;
    pipelineLayoutCreateInfo[0].pushConstantRangeCount = 0;
    pipelineLayoutCreateInfo[0].pPushConstantRanges = NULL;
    pipelineLayoutCreateInfo[0].setLayoutCount = descriptor_set_count;
    pipelineLayoutCreateInfo[0].pSetLayouts = descriptor_layouts;
    res = vkCreatePipelineLayout(info.device, pipelineLayoutCreateInfo, NULL, &info.pipeline_layout);
    assert(res == VK_SUCCESS);

    // Create a single pool to contain data for our descriptor set
    VkDescriptorPoolSize pool_sizes[resource_type_count] = {};
    pool_sizes[0].type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    pool_sizes[0].descriptorCount = 1;
    pool_sizes[1].type = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
    pool_sizes[1].descriptorCount = 1;
    pool_sizes[2].type = VK_DESCRIPTOR_TYPE_SAMPLER;
    pool_sizes[2].descriptorCount = 1;

    VkDescriptorPoolCreateInfo pool_info[1] = {};
    pool_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO;
    pool_info[0].pNext = NULL;
    pool_info[0].maxSets = descriptor_set_count;
    pool_info[0].poolSizeCount = resource_type_count;
    pool_info[0].pPoolSizes = pool_sizes;

    VkDescriptorPool descriptor_pool[1] = {};
    res = vkCreateDescriptorPool(info.device, pool_info, NULL, descriptor_pool);
    assert(res == VK_SUCCESS);

    VkDescriptorSetAllocateInfo alloc_info[1];
    alloc_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
    alloc_info[0].pNext = NULL;
    alloc_info[0].descriptorPool = descriptor_pool[0];
    alloc_info[0].descriptorSetCount = descriptor_set_count;
    alloc_info[0].pSetLayouts = descriptor_layouts;

    // Populate descriptor sets
    VkDescriptorSet descriptor_sets[descriptor_set_count] = {};
    res = vkAllocateDescriptorSets(info.device, alloc_info, descriptor_sets);
    assert(res == VK_SUCCESS);

    VkWriteDescriptorSet descriptor_writes[resource_count];

    // Populate with info about our uniform buffer for MVP
    descriptor_writes[0] = {};
    descriptor_writes[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descriptor_writes[0].pNext = NULL;
    descriptor_writes[0].dstSet = descriptor_sets[0];
    descriptor_writes[0].descriptorCount = 1;
    descriptor_writes[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    descriptor_writes[0].pBufferInfo = &info.uniform_data.buffer_info;  // populated by init_uniform_buffer()
    descriptor_writes[0].dstArrayElement = 0;
    descriptor_writes[0].dstBinding = 0;

    // Populate with info about our image
    descriptor_writes[1] = {};
    descriptor_writes[1].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descriptor_writes[1].pNext = NULL;
    descriptor_writes[1].dstSet = descriptor_sets[0];
    descriptor_writes[1].descriptorCount = 1;
    descriptor_writes[1].descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
    descriptor_writes[1].pImageInfo = &info.texture_data.image_info;  // populated by init_texture()
    descriptor_writes[1].dstArrayElement = 0;
    descriptor_writes[1].dstBinding = 1;

    // Populate with info about our sampler
    descriptor_writes[2] = {};
    descriptor_writes[2].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descriptor_writes[2].pNext = NULL;
    descriptor_writes[2].dstSet = descriptor_sets[0];
    descriptor_writes[2].descriptorCount = 1;
    descriptor_writes[2].descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER;
    descriptor_writes[2].pImageInfo = &samplerInfo;
    descriptor_writes[2].dstArrayElement = 0;
    descriptor_writes[2].dstBinding = 2;

    vkUpdateDescriptorSets(info.device, resource_count, descriptor_writes, 0, NULL);

    /* VULKAN_KEY_END */

    init_pipeline_cache(info);
    init_pipeline(info, depthPresent);
    init_presentable_image(info);

    VkClearValue clear_values[2];
    init_clear_color_and_depth(info, clear_values);

    VkRenderPassBeginInfo rp_begin;
    init_render_pass_begin_info(info, rp_begin);
    rp_begin.clearValueCount = 2;
    rp_begin.pClearValues = clear_values;

    vkCmdBeginRenderPass(info.cmd, &rp_begin, VK_SUBPASS_CONTENTS_INLINE);

    vkCmdBindPipeline(info.cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, info.pipeline);
    vkCmdBindDescriptorSets(info.cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, info.pipeline_layout, 0, NUM_DESCRIPTOR_SETS,
                            descriptor_sets, 0, NULL);

    const VkDeviceSize offsets[1] = {0};
    vkCmdBindVertexBuffers(info.cmd, 0, 1, &info.vertex_buffer.buf, offsets);

    init_viewports(info);
    init_scissors(info);

    vkCmdDraw(info.cmd, 12 * 3, 1, 0, 0);
    vkCmdEndRenderPass(info.cmd);
    res = vkEndCommandBuffer(info.cmd);
    assert(res == VK_SUCCESS);

    VkFence drawFence = {};
    init_fence(info, drawFence);
    VkPipelineStageFlags pipe_stage_flags = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT;
    VkSubmitInfo submit_info = {};
    init_submit_info(info, submit_info, pipe_stage_flags);

    /* Queue the command buffer for execution */
    res = vkQueueSubmit(info.graphics_queue, 1, &submit_info, drawFence);
    assert(res == VK_SUCCESS);

    /* Now present the image in the window */
    VkPresentInfoKHR present = {};
    init_present_info(info, present);

    /* Make sure command buffer is finished before presenting */
    do {
        res = vkWaitForFences(info.device, 1, &drawFence, VK_TRUE, FENCE_TIMEOUT);
    } while (res == VK_TIMEOUT);
    assert(res == VK_SUCCESS);
    res = vkQueuePresentKHR(info.present_queue, &present);
    assert(res == VK_SUCCESS);

    wait_seconds(1);
    if (info.save_images) write_ppm(info, "separate_image_sampler");

    vkDestroyFence(info.device, drawFence, NULL);
    vkDestroySemaphore(info.device, info.imageAcquiredSemaphore, NULL);
    destroy_pipeline(info);
    destroy_pipeline_cache(info);

    vkDestroySampler(info.device, separateSampler, NULL);
    vkDestroyImageView(info.device, info.textures[0].view, NULL);
    vkDestroyImage(info.device, info.textures[0].image, NULL);
    vkFreeMemory(info.device, info.textures[0].mem, NULL);

    // instead of destroy_descriptor_pool(info);
    vkDestroyDescriptorPool(info.device, descriptor_pool[0], NULL);

    destroy_vertex_buffer(info);
    destroy_framebuffers(info);
    destroy_shaders(info);
    destroy_renderpass(info);

    // instead of destroy_descriptor_and_pipeline_layouts(info);
    for (int i = 0; i < descriptor_set_count; i++) vkDestroyDescriptorSetLayout(info.device, descriptor_layouts[i], NULL);
    vkDestroyPipelineLayout(info.device, info.pipeline_layout, NULL);

    destroy_uniform_buffer(info);
    destroy_depth_buffer(info);
    destroy_swap_chain(info);
    destroy_command_buffer(info);
    destroy_command_pool(info);
    destroy_device(info);
    destroy_window(info);
    destroy_instance(info);
    return 0;
}
int sample_main(int argc, char *argv[]) {
    VkResult U_ASSERT_ONLY res;
    struct sample_info info = {};
    char sample_title[] = "Simple Push Constants";
    const bool depthPresent = true;

    process_command_line_args(info, argc, argv);
    init_global_layer_properties(info);
    init_instance_extension_names(info);
    init_device_extension_names(info);
    init_instance(info, sample_title);
    init_enumerate_device(info);
    init_window_size(info, 500, 500);
    init_connection(info);
    init_window(info);
    init_swapchain_extension(info);
    init_device(info);
    init_command_pool(info);
    init_command_buffer(info);
    execute_begin_command_buffer(info);
    init_device_queue(info);
    init_swap_chain(info);
    init_depth_buffer(info);
    init_uniform_buffer(info);
    init_renderpass(info, depthPresent);
    init_shaders(info, vertShaderText, fragShaderText);
    init_framebuffers(info, depthPresent);
    init_vertex_buffer(info, g_vb_texture_Data, sizeof(g_vb_texture_Data), sizeof(g_vb_texture_Data[0]), true);

    // Set up one descriptor sets
    static const unsigned descriptor_set_count = 1;
    static const unsigned resource_count = 1;

    // Create binding and layout for the following, matching contents of shader
    //   binding 0 = uniform buffer (MVP)

    VkDescriptorSetLayoutBinding resource_binding[resource_count] = {};
    resource_binding[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    resource_binding[0].descriptorCount = 1;
    resource_binding[0].stageFlags = VK_SHADER_STAGE_VERTEX_BIT;
    resource_binding[0].pImmutableSamplers = NULL;

    VkDescriptorSetLayoutCreateInfo resource_layout_info[1] = {};
    resource_layout_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO;
    resource_layout_info[0].pNext = NULL;
    resource_layout_info[0].bindingCount = resource_count;
    resource_layout_info[0].pBindings = resource_binding;

    VkDescriptorSetLayout descriptor_layouts[1] = {};
    res = vkCreateDescriptorSetLayout(info.device, resource_layout_info, NULL, &descriptor_layouts[0]);
    assert(res == VK_SUCCESS);

    /* VULKAN_KEY_START */

    // Set up our push constant range, which mirrors the declaration of
    const unsigned push_constant_range_count = 1;
    VkPushConstantRange push_constant_ranges[push_constant_range_count] = {};
    push_constant_ranges[0].stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT;
    push_constant_ranges[0].offset = 0;
    push_constant_ranges[0].size = 8;

    // Create pipeline layout, including push constant info.

    // Create pipeline layout with multiple descriptor sets
    VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo[1] = {};
    pipelineLayoutCreateInfo[0].sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
    pipelineLayoutCreateInfo[0].pNext = NULL;
    pipelineLayoutCreateInfo[0].pushConstantRangeCount = push_constant_range_count;
    pipelineLayoutCreateInfo[0].pPushConstantRanges = push_constant_ranges;
    pipelineLayoutCreateInfo[0].setLayoutCount = descriptor_set_count;
    pipelineLayoutCreateInfo[0].pSetLayouts = descriptor_layouts;
    res = vkCreatePipelineLayout(info.device, pipelineLayoutCreateInfo, NULL, &info.pipeline_layout);
    assert(res == VK_SUCCESS);

    // Create a single pool to contain data for our descriptor set
    VkDescriptorPoolSize type_count[2] = {};
    type_count[0].type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    type_count[0].descriptorCount = 1;
    type_count[1].type = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    type_count[1].descriptorCount = 1;

    VkDescriptorPoolCreateInfo pool_info[1] = {};
    pool_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO;
    pool_info[0].pNext = NULL;
    pool_info[0].maxSets = descriptor_set_count;
    pool_info[0].poolSizeCount = sizeof(type_count) / sizeof(VkDescriptorPoolSize);
    pool_info[0].pPoolSizes = type_count;

    VkDescriptorPool descriptor_pool[1] = {};
    res = vkCreateDescriptorPool(info.device, pool_info, NULL, descriptor_pool);
    assert(res == VK_SUCCESS);

    VkDescriptorSetAllocateInfo alloc_info[1];
    alloc_info[0].sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
    alloc_info[0].pNext = NULL;
    alloc_info[0].descriptorPool = descriptor_pool[0];
    alloc_info[0].descriptorSetCount = descriptor_set_count;
    alloc_info[0].pSetLayouts = descriptor_layouts;

    // Populate descriptor sets
    VkDescriptorSet descriptor_sets[descriptor_set_count] = {};
    res = vkAllocateDescriptorSets(info.device, alloc_info, descriptor_sets);
    assert(res == VK_SUCCESS);

    // Using empty brace initializer on the next line triggers a bug in older
    // versions of gcc, so memset instead
    VkWriteDescriptorSet descriptor_writes[resource_count];
    memset(descriptor_writes, 0, sizeof(descriptor_writes));

    // Populate with info about our uniform buffer for MVP
    descriptor_writes[0] = {};
    descriptor_writes[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descriptor_writes[0].pNext = NULL;
    descriptor_writes[0].dstSet = descriptor_sets[0];
    descriptor_writes[0].descriptorCount = 1;
    descriptor_writes[0].descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    descriptor_writes[0].pBufferInfo = &info.uniform_data.buffer_info;  // populated by init_uniform_buffer()
    descriptor_writes[0].dstArrayElement = 0;
    descriptor_writes[0].dstBinding = 0;

    vkUpdateDescriptorSets(info.device, resource_count, descriptor_writes, 0, NULL);

    // Create our push constant data, which matches shader expectations
    unsigned pushConstants[2] = {};
    pushConstants[0] = (unsigned)2;
    pushConstants[1] = (unsigned)0x3F800000;

    // Ensure we have enough room for push constant data
    if (sizeof(pushConstants) > info.gpu_props.limits.maxPushConstantsSize) assert(0 && "Too many push constants");

    vkCmdPushConstants(info.cmd, info.pipeline_layout, VK_SHADER_STAGE_FRAGMENT_BIT, 0, sizeof(pushConstants), pushConstants);

    /* VULKAN_KEY_END */

    init_pipeline_cache(info);
    init_pipeline(info, depthPresent);
    init_presentable_image(info);

    VkClearValue clear_values[2];
    init_clear_color_and_depth(info, clear_values);

    VkRenderPassBeginInfo rp_begin;
    init_render_pass_begin_info(info, rp_begin);
    rp_begin.clearValueCount = 2;
    rp_begin.pClearValues = clear_values;

    vkCmdBeginRenderPass(info.cmd, &rp_begin, VK_SUBPASS_CONTENTS_INLINE);

    vkCmdBindPipeline(info.cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, info.pipeline);
    vkCmdBindDescriptorSets(info.cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, info.pipeline_layout, 0, NUM_DESCRIPTOR_SETS,
                            descriptor_sets, 0, NULL);

    const VkDeviceSize offsets[1] = {0};
    vkCmdBindVertexBuffers(info.cmd, 0, 1, &info.vertex_buffer.buf, offsets);

    init_viewports(info);
    init_scissors(info);

    vkCmdDraw(info.cmd, 12 * 3, 1, 0, 0);
    vkCmdEndRenderPass(info.cmd);
    res = vkEndCommandBuffer(info.cmd);
    assert(res == VK_SUCCESS);

    VkFence drawFence = {};
    init_fence(info, drawFence);
    VkPipelineStageFlags pipe_stage_flags = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT;
    VkSubmitInfo submit_info = {};
    init_submit_info(info, submit_info, pipe_stage_flags);

    /* Queue the command buffer for execution */
    res = vkQueueSubmit(info.graphics_queue, 1, &submit_info, drawFence);
    assert(res == VK_SUCCESS);

    /* Now present the image in the window */
    VkPresentInfoKHR present = {};
    init_present_info(info, present);

    /* Make sure command buffer is finished before presenting */
    do {
        res = vkWaitForFences(info.device, 1, &drawFence, VK_TRUE, FENCE_TIMEOUT);
    } while (res == VK_TIMEOUT);
    assert(res == VK_SUCCESS);
    res = vkQueuePresentKHR(info.present_queue, &present);
    assert(res == VK_SUCCESS);

    wait_seconds(1);
    if (info.save_images) write_ppm(info, "push_constants");

    vkDestroyFence(info.device, drawFence, NULL);
    vkDestroySemaphore(info.device, info.imageAcquiredSemaphore, NULL);
    destroy_pipeline(info);
    destroy_pipeline_cache(info);
    // instead of destroy_descriptor_pool(info);
    vkDestroyDescriptorPool(info.device, descriptor_pool[0], NULL);
    destroy_vertex_buffer(info);
    destroy_framebuffers(info);
    destroy_shaders(info);
    destroy_renderpass(info);
    // instead of destroy_descriptor_and_pipeline_layouts(info);
    for (int i = 0; i < descriptor_set_count; i++) vkDestroyDescriptorSetLayout(info.device, descriptor_layouts[i], NULL);
    vkDestroyPipelineLayout(info.device, info.pipeline_layout, NULL);
    destroy_uniform_buffer(info);
    destroy_depth_buffer(info);
    destroy_swap_chain(info);
    destroy_command_buffer(info);
    destroy_command_pool(info);
    destroy_device(info);
    destroy_window(info);
    destroy_instance(info);
    return 0;
}
示例#24
0
void Renderer::_DeInitDescriptorPool() {
	vkDestroyDescriptorPool(_device, _descriptor_pool, nullptr);
	_descriptor_pool = nullptr;
}
示例#25
0
void BaseImage::ValidateContent(RandomNumberGenerator& rand)
{
    /*
    dstBuf has following layout:
    For each of texels to be sampled, [0..valueCount):
    struct {
        in uint32_t pixelX;
        in uint32_t pixelY;
        out uint32_t pixelColor;
    }
    */

    const uint32_t valueCount = 128;

    VkBufferCreateInfo dstBufCreateInfo = { VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO };
    dstBufCreateInfo.usage = VK_BUFFER_USAGE_STORAGE_BUFFER_BIT;
    dstBufCreateInfo.size = valueCount * sizeof(uint32_t) * 3;

    VmaAllocationCreateInfo dstBufAllocCreateInfo = {};
    dstBufAllocCreateInfo.flags = VMA_ALLOCATION_CREATE_MAPPED_BIT;
    dstBufAllocCreateInfo.usage = VMA_MEMORY_USAGE_GPU_TO_CPU;

    VkBuffer dstBuf = nullptr;
    VmaAllocation dstBufAlloc = nullptr;
    VmaAllocationInfo dstBufAllocInfo = {};
    TEST( vmaCreateBuffer(g_hAllocator, &dstBufCreateInfo, &dstBufAllocCreateInfo, &dstBuf, &dstBufAlloc, &dstBufAllocInfo) == VK_SUCCESS );

    // Fill dstBuf input data.
    {
        uint32_t* dstBufContent = (uint32_t*)dstBufAllocInfo.pMappedData;
        for(uint32_t i = 0; i < valueCount; ++i)
        {
            const uint32_t x = rand.Generate() % m_CreateInfo.extent.width;
            const uint32_t y = rand.Generate() % m_CreateInfo.extent.height;
            dstBufContent[i * 3    ] = x;
            dstBufContent[i * 3 + 1] = y;
            dstBufContent[i * 3 + 2] = 0;
        }
    }

    VkSamplerCreateInfo samplerCreateInfo = { VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO };
    samplerCreateInfo.magFilter = VK_FILTER_NEAREST;
    samplerCreateInfo.minFilter = VK_FILTER_NEAREST;
    samplerCreateInfo.mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST;
    samplerCreateInfo.addressModeU = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE;
    samplerCreateInfo.addressModeV = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE;
    samplerCreateInfo.addressModeW = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE;
    samplerCreateInfo.unnormalizedCoordinates = VK_TRUE;

    VkSampler sampler = nullptr;
    TEST( vkCreateSampler( g_hDevice, &samplerCreateInfo, nullptr, &sampler) == VK_SUCCESS );

    VkDescriptorSetLayoutBinding bindings[2] = {};
    bindings[0].binding = 0;
    bindings[0].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    bindings[0].descriptorCount = 1;
    bindings[0].stageFlags = VK_SHADER_STAGE_COMPUTE_BIT;
    bindings[0].pImmutableSamplers = &sampler;
    bindings[1].binding = 1;
    bindings[1].descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
    bindings[1].descriptorCount = 1;
    bindings[1].stageFlags = VK_SHADER_STAGE_COMPUTE_BIT;

    VkDescriptorSetLayoutCreateInfo descSetLayoutCreateInfo = { VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO };
    descSetLayoutCreateInfo.bindingCount = 2;
    descSetLayoutCreateInfo.pBindings = bindings;

    VkDescriptorSetLayout descSetLayout = nullptr;
    TEST( vkCreateDescriptorSetLayout(g_hDevice, &descSetLayoutCreateInfo, nullptr, &descSetLayout) == VK_SUCCESS );

    VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo = { VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO };
    pipelineLayoutCreateInfo.setLayoutCount = 1;
    pipelineLayoutCreateInfo.pSetLayouts = &descSetLayout;

    VkPipelineLayout pipelineLayout = nullptr;
    TEST( vkCreatePipelineLayout(g_hDevice, &pipelineLayoutCreateInfo, nullptr, &pipelineLayout) == VK_SUCCESS );

    std::vector<char> shaderCode;
    LoadShader(shaderCode, "SparseBindingTest.comp.spv");

    VkShaderModuleCreateInfo shaderModuleCreateInfo = { VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO };
    shaderModuleCreateInfo.codeSize = shaderCode.size();
    shaderModuleCreateInfo.pCode = (const uint32_t*)shaderCode.data();

    VkShaderModule shaderModule = nullptr;
    TEST( vkCreateShaderModule(g_hDevice, &shaderModuleCreateInfo, nullptr, &shaderModule) == VK_SUCCESS );

    VkComputePipelineCreateInfo pipelineCreateInfo = { VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO };
    pipelineCreateInfo.stage.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
    pipelineCreateInfo.stage.stage = VK_SHADER_STAGE_COMPUTE_BIT;
    pipelineCreateInfo.stage.module = shaderModule;
    pipelineCreateInfo.stage.pName = "main";
    pipelineCreateInfo.layout = pipelineLayout;

    VkPipeline pipeline = nullptr;
    TEST( vkCreateComputePipelines(g_hDevice, nullptr, 1, &pipelineCreateInfo, nullptr, &pipeline) == VK_SUCCESS );

    VkDescriptorPoolSize poolSizes[2] = {};
    poolSizes[0].type = bindings[0].descriptorType;
    poolSizes[0].descriptorCount = bindings[0].descriptorCount;
    poolSizes[1].type = bindings[1].descriptorType;
    poolSizes[1].descriptorCount = bindings[1].descriptorCount;

    VkDescriptorPoolCreateInfo descPoolCreateInfo = { VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO };
    descPoolCreateInfo.maxSets = 1;
    descPoolCreateInfo.poolSizeCount = 2;
    descPoolCreateInfo.pPoolSizes = poolSizes;

    VkDescriptorPool descPool = nullptr;
    TEST( vkCreateDescriptorPool(g_hDevice, &descPoolCreateInfo, nullptr, &descPool) == VK_SUCCESS );

    VkDescriptorSetAllocateInfo descSetAllocInfo = { VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO };
    descSetAllocInfo.descriptorPool = descPool;
    descSetAllocInfo.descriptorSetCount = 1;
    descSetAllocInfo.pSetLayouts = &descSetLayout;

    VkDescriptorSet descSet = nullptr;
    TEST( vkAllocateDescriptorSets(g_hDevice, &descSetAllocInfo, &descSet) == VK_SUCCESS );

    VkImageViewCreateInfo imageViewCreateInfo = { VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO };
    imageViewCreateInfo.image = m_Image;
    imageViewCreateInfo.viewType = VK_IMAGE_VIEW_TYPE_2D;
    imageViewCreateInfo.format = m_CreateInfo.format;
    imageViewCreateInfo.subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
    imageViewCreateInfo.subresourceRange.layerCount = 1;
    imageViewCreateInfo.subresourceRange.levelCount = 1;

    VkImageView imageView = nullptr;
    TEST( vkCreateImageView(g_hDevice, &imageViewCreateInfo, nullptr, &imageView) == VK_SUCCESS );

    VkDescriptorImageInfo descImageInfo = {};
    descImageInfo.imageView = imageView;
    descImageInfo.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;

    VkDescriptorBufferInfo descBufferInfo = {};
    descBufferInfo.buffer = dstBuf;
    descBufferInfo.offset = 0;
    descBufferInfo.range = VK_WHOLE_SIZE;

    VkWriteDescriptorSet descWrites[2] = {};
    descWrites[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descWrites[0].dstSet = descSet;
    descWrites[0].dstBinding = bindings[0].binding;
    descWrites[0].dstArrayElement = 0;
    descWrites[0].descriptorCount = 1;
    descWrites[0].descriptorType = bindings[0].descriptorType;
    descWrites[0].pImageInfo = &descImageInfo;
    descWrites[1].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
    descWrites[1].dstSet = descSet;
    descWrites[1].dstBinding = bindings[1].binding;
    descWrites[1].dstArrayElement = 0;
    descWrites[1].descriptorCount = 1;
    descWrites[1].descriptorType = bindings[1].descriptorType;
    descWrites[1].pBufferInfo = &descBufferInfo;
    vkUpdateDescriptorSets(g_hDevice, 2, descWrites, 0, nullptr);

    BeginSingleTimeCommands();
    vkCmdBindPipeline(g_hTemporaryCommandBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline);
    vkCmdBindDescriptorSets(g_hTemporaryCommandBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipelineLayout, 0, 1, &descSet, 0, nullptr);
    vkCmdDispatch(g_hTemporaryCommandBuffer, valueCount, 1, 1);
    EndSingleTimeCommands();

    // Validate dstBuf output data.
    {
        const uint32_t* dstBufContent = (const uint32_t*)dstBufAllocInfo.pMappedData;
        for(uint32_t i = 0; i < valueCount; ++i)
        {
            const uint32_t x     = dstBufContent[i * 3    ];
            const uint32_t y     = dstBufContent[i * 3 + 1];
            const uint32_t color = dstBufContent[i * 3 + 2];
            const uint8_t a = (uint8_t)(color >> 24);
            const uint8_t b = (uint8_t)(color >> 16);
            const uint8_t g = (uint8_t)(color >>  8);
            const uint8_t r = (uint8_t)color;
            TEST(r == (uint8_t)x && g == (uint8_t)y && b == 13 && a == 25);
        }
    }

    vkDestroyImageView(g_hDevice, imageView, nullptr);
    vkDestroyDescriptorPool(g_hDevice, descPool, nullptr);
    vmaDestroyBuffer(g_hAllocator, dstBuf, dstBufAlloc);
    vkDestroyPipeline(g_hDevice, pipeline, nullptr);
    vkDestroyShaderModule(g_hDevice, shaderModule, nullptr);
    vkDestroyPipelineLayout(g_hDevice, pipelineLayout, nullptr);
    vkDestroyDescriptorSetLayout(g_hDevice, descSetLayout, nullptr);
    vkDestroySampler(g_hDevice, sampler, nullptr);
}
示例#26
0
void Arguments::destroy()
{
    vkFreeDescriptorSets(device, descriptorPool, 1, &descriptorSet);
    vkDestroyDescriptorPool(device, descriptorPool, nullptr);
}
示例#27
0
//
// Vulkan termination.
//
void Example::terminate(const vkts::IUpdateThreadContext& updateContext)
{
	if (device.get())
	{
		terminateResources(updateContext);

		//

		if (swapchain.get())
		{
			swapchain->destroy();
		}

		if (pipelineLayout.get())
		{
			pipelineLayout->destroy();
		}

		if (pipelineCache.get())
		{
			pipelineCache->destroy();
		}

		if (vertexShaderModule.get())
		{
			vertexShaderModule->destroy();
		}

		if (fragmentShaderModule.get())
		{
			fragmentShaderModule->destroy();
		}

		if (vertexBuffer.get())
		{
			vertexBuffer->destroy();
		}

		if (deviceMemoryVertexBuffer.get())
		{
			deviceMemoryVertexBuffer->destroy();
		}

		if (descriptorSet != VK_NULL_HANDLE)
		{
			vkFreeDescriptorSets(device->getDevice(), descriptorPool, 1, &descriptorSet);

			descriptorSet = VK_NULL_HANDLE;
		}

		if (descriptorPool != VK_NULL_HANDLE)
		{
			vkDestroyDescriptorPool(device->getDevice(), descriptorPool, nullptr);

			descriptorPool = VK_NULL_HANDLE;
		}

		if (descriptorSetLayout != VK_NULL_HANDLE)
		{
			vkDestroyDescriptorSetLayout(device->getDevice(), descriptorSetLayout, nullptr);

			descriptorSetLayout = VK_NULL_HANDLE;
		}

		if (imageView.get())
		{
			imageView->destroy();
		}

		if (sampler.get())
		{
			sampler->destroy();
		}

		destroyTexture(image, deviceMemoryImage);

        if (renderingCompleteSemaphore.get())
        {
            renderingCompleteSemaphore->destroy();
        }

        if (imageAcquiredSemaphore.get())
        {
            imageAcquiredSemaphore->destroy();
        }

		if (commandPool.get())
		{
			commandPool->destroy();
		}

		if (surface.get())
		{
			surface->destroy();
		}

		device->destroy();
	}

	if (instance.get())
	{
		instance->destroy();
	}
}