Move<VkCommandPool> makeCommandPool (const DeviceInterface& vk, const VkDevice device, const deUint32 queueFamilyIndex) { const VkCommandPoolCreateInfo commandPoolParams = { VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO, // VkStructureType sType; DE_NULL, // const void* pNext; VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT, // VkCommandPoolCreateFlags flags; queueFamilyIndex, // deUint32 queueFamilyIndex; }; return createCommandPool(vk, device, &commandPoolParams); }
void VulkanBase::prepare() { if (enableValidation) vkDebug::setupDebugging(instance, VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT, NULL); createCommandPool(); createSetupCommandBuffer(); setupSwapChain(); createCommandBuffers(); setupDepthStencil(); setupRenderPass(); createPipelineCache(); setupFrameBuffer(); flushSetupCommandBuffer(); // Recreate setup command buffer for derived class createSetupCommandBuffer(); // Create a simple texture loader class textureLoader = new vkTools::VulkanTextureLoader(physicalDevice, device, queue, cmdPool); }
/** * Create the logical device based on the assigned physical device, also gets default queue family indices * * @param enabledFeatures Can be used to enable certain features upon device creation * @param useSwapChain Set to false for headless rendering to omit the swapchain device extensions * @param requestedQueueTypes Bit flags specifying the queue types to be requested from the device * * @return VkResult of the device creation call */ VkResult createLogicalDevice(VkPhysicalDeviceFeatures enabledFeatures, bool useSwapChain = true, VkQueueFlags requestedQueueTypes = VK_QUEUE_GRAPHICS_BIT | VK_QUEUE_COMPUTE_BIT) { // Desired queues need to be requested upon logical device creation // Due to differing queue family configurations of Vulkan implementations this can be a bit tricky, especially if the application // requests different queue types std::vector<VkDeviceQueueCreateInfo> queueCreateInfos{}; // Get queue family indices for the requested queue family types // Note that the indices may overlap depending on the implementation const float defaultQueuePriority(0.0f); // Graphics queue if (requestedQueueTypes & VK_QUEUE_GRAPHICS_BIT) { queueFamilyIndices.graphics = getQueueFamiliyIndex(VK_QUEUE_GRAPHICS_BIT); VkDeviceQueueCreateInfo queueInfo{}; queueInfo.sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; queueInfo.queueFamilyIndex = queueFamilyIndices.graphics; queueInfo.queueCount = 1; queueInfo.pQueuePriorities = &defaultQueuePriority; queueCreateInfos.push_back(queueInfo); } else { queueFamilyIndices.graphics = VK_NULL_HANDLE; } // Dedicated compute queue if (requestedQueueTypes & VK_QUEUE_COMPUTE_BIT) { queueFamilyIndices.compute = getQueueFamiliyIndex(VK_QUEUE_COMPUTE_BIT); if (queueFamilyIndices.compute != queueFamilyIndices.graphics) { // If compute family index differs, we need an additional queue create info for the compute queue VkDeviceQueueCreateInfo queueInfo{}; queueInfo.sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; queueInfo.queueFamilyIndex = queueFamilyIndices.compute; queueInfo.queueCount = 1; queueInfo.pQueuePriorities = &defaultQueuePriority; queueCreateInfos.push_back(queueInfo); } } else { // Else we use the same queue queueFamilyIndices.compute = queueFamilyIndices.graphics; } // Dedicated transfer queue if (requestedQueueTypes & VK_QUEUE_TRANSFER_BIT) { queueFamilyIndices.transfer = getQueueFamiliyIndex(VK_QUEUE_TRANSFER_BIT); if ((queueFamilyIndices.transfer != queueFamilyIndices.graphics) && (queueFamilyIndices.transfer != queueFamilyIndices.compute)) { // If compute family index differs, we need an additional queue create info for the compute queue VkDeviceQueueCreateInfo queueInfo{}; queueInfo.sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; queueInfo.queueFamilyIndex = queueFamilyIndices.transfer; queueInfo.queueCount = 1; queueInfo.pQueuePriorities = &defaultQueuePriority; queueCreateInfos.push_back(queueInfo); } } else { // Else we use the same queue queueFamilyIndices.transfer = queueFamilyIndices.graphics; } // Create the logical device representation std::vector<const char*> deviceExtensions; if (useSwapChain) { // If the device will be used for presenting to a display via a swapchain we need to request the swapchain extension deviceExtensions.push_back(VK_KHR_SWAPCHAIN_EXTENSION_NAME); } VkDeviceCreateInfo deviceCreateInfo = {}; deviceCreateInfo.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO; deviceCreateInfo.queueCreateInfoCount = static_cast<uint32_t>(queueCreateInfos.size());; deviceCreateInfo.pQueueCreateInfos = queueCreateInfos.data(); deviceCreateInfo.pEnabledFeatures = &enabledFeatures; // Enable the debug marker extension if it is present (likely meaning a debugging tool is present) if (vkTools::checkDeviceExtensionPresent(physicalDevice, VK_EXT_DEBUG_MARKER_EXTENSION_NAME)) { deviceExtensions.push_back(VK_EXT_DEBUG_MARKER_EXTENSION_NAME); enableDebugMarkers = true; } if (deviceExtensions.size() > 0) { deviceCreateInfo.enabledExtensionCount = (uint32_t)deviceExtensions.size(); deviceCreateInfo.ppEnabledExtensionNames = deviceExtensions.data(); } VkResult result = vkCreateDevice(physicalDevice, &deviceCreateInfo, nullptr, &logicalDevice); if (result == VK_SUCCESS) { // Create a default command pool for graphics command buffers commandPool = createCommandPool(queueFamilyIndices.graphics); } return result; }
/** * Create the logical device based on the assigned physical device, also gets default queue family indices * * @param enabledFeatures Can be used to enable certain features upon device creation * @param useSwapChain Set to false for headless rendering to omit the swapchain device extensions * * @return VkResult of the device creation call */ VkResult createLogicalDevice(VkPhysicalDeviceFeatures enabledFeatures, bool useSwapChain = true) { // Get queue family indices for graphics and compute // Note that the indices may overlap depending on the implementation queueFamilyIndices.graphics = getQueueFamiliyIndex(VK_QUEUE_GRAPHICS_BIT); queueFamilyIndices.compute = getQueueFamiliyIndex(VK_QUEUE_COMPUTE_BIT); //todo: Transfer? // Pass queue information for graphics and compute, so examples can later on request queues from both std::vector<float> queuePriorities; std::vector<VkDeviceQueueCreateInfo> queueCreateInfos{}; // We need one queue create info per queue family index // If graphics and compute share the same queue family index we only need one queue create info but // with two queues to request queueCreateInfos.resize(1); // Graphics queuePriorities.push_back(0.0f); queueCreateInfos[0] = {}; queueCreateInfos[0].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; queueCreateInfos[0].queueFamilyIndex = queueFamilyIndices.graphics; queueCreateInfos[0].queueCount = 1; // Compute // If compute has a different queue family index, add another create info, else just add if (queueFamilyIndices.graphics != queueFamilyIndices.compute) { queueCreateInfos.resize(2); queueCreateInfos[1] = {}; queueCreateInfos[1].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; queueCreateInfos[1].queueFamilyIndex = queueFamilyIndices.compute; queueCreateInfos[1].queueCount = 1; queueCreateInfos[1].pQueuePriorities = queuePriorities.data(); } else { queueCreateInfos[0].queueCount++; queuePriorities.push_back(0.0f); } queueCreateInfos[0].pQueuePriorities = queuePriorities.data(); // Create the logical device representation std::vector<const char*> deviceExtensions; if (useSwapChain) { // If the device will be used for presenting to a display via a swapchain // we need to request the swapchain extension deviceExtensions.push_back(VK_KHR_SWAPCHAIN_EXTENSION_NAME); } VkDeviceCreateInfo deviceCreateInfo = {}; deviceCreateInfo.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO; deviceCreateInfo.queueCreateInfoCount = static_cast<uint32_t>(queueCreateInfos.size());; deviceCreateInfo.pQueueCreateInfos = queueCreateInfos.data(); deviceCreateInfo.pEnabledFeatures = &enabledFeatures; // Cnable the debug marker extension if it is present (likely meaning a debugging tool is present) if (vkTools::checkDeviceExtensionPresent(physicalDevice, VK_EXT_DEBUG_MARKER_EXTENSION_NAME)) { deviceExtensions.push_back(VK_EXT_DEBUG_MARKER_EXTENSION_NAME); enableDebugMarkers = true; } if (deviceExtensions.size() > 0) { deviceCreateInfo.enabledExtensionCount = (uint32_t)deviceExtensions.size(); deviceCreateInfo.ppEnabledExtensionNames = deviceExtensions.data(); } VkResult result = vkCreateDevice(physicalDevice, &deviceCreateInfo, nullptr, &logicalDevice); if (result == VK_SUCCESS) { // Create a default command pool for graphics command buffers commandPool = createCommandPool(queueFamilyIndices.graphics); } return result; }