diff --git a/include/mini/commandpool.hpp b/include/mini/commandpool.hpp deleted file mode 100644 index 08c0295..0000000 --- a/include/mini/commandpool.hpp +++ /dev/null @@ -1,42 +0,0 @@ -#pragma once - -#include - -#include -#include - -namespace Mini { - - /// - /// C++ wrapper class for a Vulkan command pool. - /// - /// This class manages the lifetime of a Vulkan command pool. - /// - class CommandPool { - public: - CommandPool() noexcept = default; - - /// - /// Create the command pool. - /// - /// @param device Vulkan device - /// @param graphicsFamilyIdx Index of the graphics queue family - /// - /// @throws LSFG::vulkan_error if object creation fails. - /// - CommandPool(VkDevice device, uint32_t graphicsFamilyIdx); - - /// Get the Vulkan handle. - [[nodiscard]] auto handle() const { return *this->commandPool; } - - /// Trivially copyable, moveable and destructible - CommandPool(const CommandPool&) noexcept = default; - CommandPool& operator=(const CommandPool&) noexcept = default; - CommandPool(CommandPool&&) noexcept = default; - CommandPool& operator=(CommandPool&&) noexcept = default; - ~CommandPool() = default; - private: - std::shared_ptr commandPool; - }; - -} diff --git a/lsfg-vk-common/include/lsfg-vk-common/helpers/pointers.hpp b/lsfg-vk-common/include/lsfg-vk-common/helpers/pointers.hpp index 98a5bf9..9c4d373 100644 --- a/lsfg-vk-common/include/lsfg-vk-common/helpers/pointers.hpp +++ b/lsfg-vk-common/include/lsfg-vk-common/helpers/pointers.hpp @@ -57,6 +57,11 @@ namespace ls { /// default constructor owned_ptr() = default; + /// construct from raw pointer without deleter + /// @param ptr raw pointer to own, must be valid for object lifetime + explicit owned_ptr(T* ptr) + : ptr(ptr) {} + /// construct from raw pointer /// @param ptr raw pointer to own, must be valid for object lifetime /// @param deleter custom deleter function, called only on owned instances @@ -97,8 +102,8 @@ namespace ls { // destructor ~owned_ptr() { - if (ptr && deleter) { - deleter(*ptr); + if (ptr) { + if (deleter) deleter(*ptr); delete ptr; } } diff --git a/lsfg-vk-common/include/lsfg-vk-common/vulkan/vulkan.hpp b/lsfg-vk-common/include/lsfg-vk-common/vulkan/vulkan.hpp index a24890b..5fffb75 100644 --- a/lsfg-vk-common/include/lsfg-vk-common/vulkan/vulkan.hpp +++ b/lsfg-vk-common/include/lsfg-vk-common/vulkan/vulkan.hpp @@ -90,10 +90,11 @@ namespace vk { PFN_vkDestroyPipelineLayout DestroyPipelineLayout; PFN_vkCreateComputePipelines CreateComputePipelines; PFN_vkDestroyPipeline DestroyPipeline; - PFN_vkSignalSemaphore SignalSemaphore; - PFN_vkWaitSemaphores WaitSemaphores; + // extension functions + PFN_vkSignalSemaphoreKHR SignalSemaphoreKHR; + PFN_vkWaitSemaphoresKHR WaitSemaphoresKHR; PFN_vkGetMemoryFdKHR GetMemoryFdKHR; PFN_vkImportSemaphoreFdKHR ImportSemaphoreFdKHR; PFN_vkGetSemaphoreFdKHR GetSemaphoreFdKHR; @@ -130,10 +131,26 @@ namespace vk { /// @param engineName name of the engine /// @param engineVersion version of the engine /// @param selectPhysicalDevice function to select the physical device + /// @param isGraphical whether the device is graphical (rather than compute) /// @throws ls::vulkan_error on failure Vulkan(const std::string& appName, version appVersion, const std::string& engineName, version engineVersion, - PhysicalDeviceSelector selectPhysicalDevice); + PhysicalDeviceSelector selectPhysicalDevice, + bool isGraphical = false); + + /// create based on an existing externally managed vulkan instance. + /// @param instance vulkan instance handle + /// @param device logical device handle + /// @param physdev physical device handle + /// @param instanceFuncs instance function pointers + /// @param deviceFuncs device function pointers + /// @param isGraphical whether the device is graphical (rather than compute) + /// @throws ls::vulkan_error on failure + Vulkan(VkInstance instance, VkDevice device, + VkPhysicalDevice physdev, + VulkanInstanceFuncs instanceFuncs, + VulkanDeviceFuncs deviceFuncs, + bool isGraphical = true); /// find a memory type index /// @param validTypes bitset of valid memory types @@ -170,7 +187,7 @@ namespace vk { VulkanInstanceFuncs instance_funcs; VkPhysicalDevice physdev; - uint32_t computeFamilyIdx; + uint32_t queueFamilyIdx; bool fp16; ls::owned_ptr device; diff --git a/lsfg-vk-common/src/vulkan/timeline_semaphore.cpp b/lsfg-vk-common/src/vulkan/timeline_semaphore.cpp index 3114080..9cbf05a 100644 --- a/lsfg-vk-common/src/vulkan/timeline_semaphore.cpp +++ b/lsfg-vk-common/src/vulkan/timeline_semaphore.cpp @@ -81,7 +81,7 @@ void TimelineSemaphore::signal(const vk::Vulkan& vk, uint64_t value) const { .semaphore = *this->semaphore, .value = value }; - auto res = vk.df().SignalSemaphore(vk.dev(), &signalInfo); + auto res = vk.df().SignalSemaphoreKHR(vk.dev(), &signalInfo); if (res != VK_SUCCESS) throw ls::vulkan_error(res, "vkSignalSemaphore() failed"); } @@ -94,7 +94,7 @@ bool TimelineSemaphore::wait(const vk::Vulkan& vk, uint64_t value, uint64_t time .pSemaphores = &semaphore, .pValues = &value }; - auto res = vk.df().WaitSemaphores(vk.dev(), &waitInfo, timeout); + auto res = vk.df().WaitSemaphoresKHR(vk.dev(), &waitInfo, timeout); if (res != VK_SUCCESS && res != VK_TIMEOUT) throw ls::vulkan_error(res, "vkWaitSemaphores() failed"); diff --git a/lsfg-vk-common/src/vulkan/vulkan.cpp b/lsfg-vk-common/src/vulkan/vulkan.cpp index 838260d..96ada55 100644 --- a/lsfg-vk-common/src/vulkan/vulkan.cpp +++ b/lsfg-vk-common/src/vulkan/vulkan.cpp @@ -341,9 +341,9 @@ VulkanDeviceFuncs vk::initVulkanDeviceFuncs(const VulkanInstanceFuncs& f, VkDevi .CreateComputePipelines = dpa(f, d, "vkCreateComputePipelines"), .DestroyPipeline = dpa(f, d, "vkDestroyPipeline"), - .SignalSemaphore = dpa(f, d, "vkSignalSemaphore"), - .WaitSemaphores = dpa(f, d, "vkWaitSemaphores"), + .SignalSemaphoreKHR = dpa(f, d, "vkSignalSemaphoreKHR"), + .WaitSemaphoresKHR = dpa(f, d, "vkWaitSemaphoresKHR"), .GetMemoryFdKHR = dpa(f, d, "vkGetMemoryFdKHR"), .ImportSemaphoreFdKHR = dpa(f, d, "vkImportSemaphoreFdKHR"), .GetSemaphoreFdKHR = dpa(f, d, "vkGetSemaphoreFdKHR"), @@ -352,7 +352,8 @@ VulkanDeviceFuncs vk::initVulkanDeviceFuncs(const VulkanInstanceFuncs& f, VkDevi Vulkan::Vulkan(const std::string& appName, version appVersion, const std::string& engineName, version engineVersion, - PhysicalDeviceSelector selectPhysicalDevice) : + PhysicalDeviceSelector selectPhysicalDevice, + bool isGraphical) : instance(createInstance( appName, appVersion, engineName, engineVersion @@ -362,21 +363,45 @@ Vulkan::Vulkan(const std::string& appName, version appVersion, *this->instance, selectPhysicalDevice )), - computeFamilyIdx(findQFI(this->instance_funcs, this->physdev, VK_QUEUE_COMPUTE_BIT)), + queueFamilyIdx(findQFI(this->instance_funcs, this->physdev, + isGraphical ? VK_QUEUE_GRAPHICS_BIT : VK_QUEUE_COMPUTE_BIT)), fp16(checkFP16(this->instance_funcs, this->physdev)), device(createLogicalDevice(this->instance_funcs, this->physdev, - this->computeFamilyIdx, + this->queueFamilyIdx, this->fp16 )), device_funcs(initVulkanDeviceFuncs( this->instance_funcs, *this->device )), - computeQueue(getQueue(this->device_funcs, *this->device, this->computeFamilyIdx)), + computeQueue(getQueue(this->device_funcs, *this->device, this->queueFamilyIdx)), cmdPool(createCommandPool(this->device_funcs, *this->device, - this->computeFamilyIdx + this->queueFamilyIdx + )), + descPool(createDescriptorPool(this->device_funcs, + *this->device + )) { +} + +Vulkan::Vulkan(VkInstance instance, VkDevice device, + VkPhysicalDevice physdev, + VulkanInstanceFuncs instanceFuncs, + VulkanDeviceFuncs deviceFuncs, + bool isGraphical) : + instance(new VkInstance(instance)), + instance_funcs(instanceFuncs), + physdev(physdev), + queueFamilyIdx(findQFI(this->instance_funcs, this->physdev, + isGraphical ? VK_QUEUE_GRAPHICS_BIT : VK_QUEUE_COMPUTE_BIT)), + fp16(false), + device(new VkDevice(device)), + device_funcs(deviceFuncs), + computeQueue(getQueue(this->device_funcs, *this->device, this->queueFamilyIdx)), + cmdPool(createCommandPool(this->device_funcs, + *this->device, + this->queueFamilyIdx )), descPool(createDescriptorPool(this->device_funcs, *this->device diff --git a/lsfg-vk-layer/src/entrypoint.cpp b/lsfg-vk-layer/src/entrypoint.cpp index ba7fe6e..96b3b97 100644 --- a/lsfg-vk-layer/src/entrypoint.cpp +++ b/lsfg-vk-layer/src/entrypoint.cpp @@ -134,7 +134,7 @@ namespace { // create device PFN_vkGetDeviceProcAddr nxvkGetDeviceProcAddr{nullptr}; VkResult myvkCreateDevice( - VkPhysicalDevice physicalDevice, + VkPhysicalDevice physdev, const VkDeviceCreateInfo* info, const VkAllocationCallbacks* alloc, VkDevice* device) { @@ -194,7 +194,7 @@ namespace { newInfo.enabledExtensionCount = static_cast(extensions.size()); newInfo.ppEnabledExtensionNames = extensions.data(); - auto res = global->fi.CreateDevice(physicalDevice, &newInfo, alloc, device); + auto res = global->fi.CreateDevice(physdev, &newInfo, alloc, device); if (res == VK_ERROR_EXTENSION_NOT_PRESENT) std::cerr << "lsfg-vk: required Vulkan device extensions are not present. " "Your GPU driver is not supported.\n"; @@ -207,9 +207,13 @@ namespace { global->device2InstanceMap.emplace( *device, layer::LayerInstance( - global->layer, vk::initVulkanDeviceFuncs(global->fi, *device), - global->instance, *device, - setLoaderData + global->layer, + vk::Vulkan( + global->instance, *device, + physdev, + global->fi, + vk::initVulkanDeviceFuncs(global->fi, *device) + ) ) ); } catch (const std::exception& e) { diff --git a/lsfg-vk-layer/src/layer.cpp b/lsfg-vk-layer/src/layer.cpp index 25c3c22..db9caf8 100644 --- a/lsfg-vk-layer/src/layer.cpp +++ b/lsfg-vk-layer/src/layer.cpp @@ -3,12 +3,9 @@ #include "lsfg-vk-common/vulkan/vulkan.hpp" #include -#include +#include #include -#include -#include - using namespace lsfgvk; using namespace lsfgvk::layer; @@ -69,14 +66,12 @@ std::vector Layer::deviceExtensions() const { "VK_KHR_external_memory", "VK_KHR_external_memory_fd", "VK_KHR_external_semaphore", - "VK_KHR_external_semaphore_fd" + "VK_KHR_external_semaphore_fd", + "VK_KHR_timeline_semaphore" }; } -layer::LayerInstance::LayerInstance(const Layer& layer, vk::VulkanDeviceFuncs df, - VkInstance instance, VkDevice device, - PFN_vkSetDeviceLoaderData setLoaderData) { - std::cerr << "lsfg-vk: Hello, world!\n"; - std::cerr << "lsfg-vk: instance=" << instance << ", device=" << device << '\n'; - std::cerr << "lsfg-vk: setLoaderData=" << reinterpret_cast(setLoaderData) << '\n'; +layer::LayerInstance::LayerInstance(const Layer& layer, vk::Vulkan vk) + : vk(std::move(vk)) { + } diff --git a/lsfg-vk-layer/src/layer.hpp b/lsfg-vk-layer/src/layer.hpp index b3da8e2..0e5314b 100644 --- a/lsfg-vk-layer/src/layer.hpp +++ b/lsfg-vk-layer/src/layer.hpp @@ -7,9 +7,6 @@ #include #include -#include -#include - namespace lsfgvk::layer { /// lsfg-vk layer @@ -48,15 +45,10 @@ namespace lsfgvk::layer { public: /// create a new layer instance /// @param layer parent layer - /// @param df Vulkan device function pointers - /// @param instance Vulkan instance - /// @param device Vulkan device - /// @param setLoaderData function to set device loader data - LayerInstance(const Layer& layer, vk::VulkanDeviceFuncs df, - VkInstance instance, VkDevice device, - PFN_vkSetDeviceLoaderData setLoaderData); + /// @param vk vulkan instance + LayerInstance(const Layer& layer, vk::Vulkan vk); private: - Configuration config; + vk::Vulkan vk; }; } diff --git a/src/mini/commandpool.cpp b/src/mini/commandpool.cpp deleted file mode 100644 index e43c7db..0000000 --- a/src/mini/commandpool.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include "mini/commandpool.hpp" -#include "common/exception.hpp" -#include "layer.hpp" - -#include - -#include -#include - -using namespace Mini; - -CommandPool::CommandPool(VkDevice device, uint32_t graphicsFamilyIdx) { - // create command pool - const VkCommandPoolCreateInfo desc{ - .sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO, - .queueFamilyIndex = graphicsFamilyIdx - }; - VkCommandPool commandPoolHandle{}; - auto res = Layer::ovkCreateCommandPool(device, &desc, nullptr, &commandPoolHandle); - if (res != VK_SUCCESS || commandPoolHandle == VK_NULL_HANDLE) - throw LSFG::vulkan_error(res, "Unable to create command pool"); - - // store command pool in shared ptr - this->commandPool = std::shared_ptr( - new VkCommandPool(commandPoolHandle), - [dev = device](VkCommandPool* commandPoolHandle) { - Layer::ovkDestroyCommandPool(dev, *commandPoolHandle, nullptr); - } - ); -}