mirror of
https://github.com/PancakeTAS/lsfg-vk.git
synced 2026-05-04 08:11:54 +00:00
refactor(cleanup): pass vulkan instance to layer
This commit is contained in:
parent
864e33200a
commit
5b13d239d2
9 changed files with 80 additions and 114 deletions
|
|
@ -1,42 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <vulkan/vulkan_core.h>
|
|
||||||
|
|
||||||
#include <cstdint>
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
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<VkCommandPool> commandPool;
|
|
||||||
};
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
@ -57,6 +57,11 @@ namespace ls {
|
||||||
/// default constructor
|
/// default constructor
|
||||||
owned_ptr() = default;
|
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
|
/// construct from raw pointer
|
||||||
/// @param ptr raw pointer to own, must be valid for object lifetime
|
/// @param ptr raw pointer to own, must be valid for object lifetime
|
||||||
/// @param deleter custom deleter function, called only on owned instances
|
/// @param deleter custom deleter function, called only on owned instances
|
||||||
|
|
@ -97,8 +102,8 @@ namespace ls {
|
||||||
|
|
||||||
// destructor
|
// destructor
|
||||||
~owned_ptr() {
|
~owned_ptr() {
|
||||||
if (ptr && deleter) {
|
if (ptr) {
|
||||||
deleter(*ptr);
|
if (deleter) deleter(*ptr);
|
||||||
delete ptr;
|
delete ptr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -90,10 +90,11 @@ namespace vk {
|
||||||
PFN_vkDestroyPipelineLayout DestroyPipelineLayout;
|
PFN_vkDestroyPipelineLayout DestroyPipelineLayout;
|
||||||
PFN_vkCreateComputePipelines CreateComputePipelines;
|
PFN_vkCreateComputePipelines CreateComputePipelines;
|
||||||
PFN_vkDestroyPipeline DestroyPipeline;
|
PFN_vkDestroyPipeline DestroyPipeline;
|
||||||
PFN_vkSignalSemaphore SignalSemaphore;
|
|
||||||
PFN_vkWaitSemaphores WaitSemaphores;
|
|
||||||
|
|
||||||
// extension functions
|
// extension functions
|
||||||
|
PFN_vkSignalSemaphoreKHR SignalSemaphoreKHR;
|
||||||
|
PFN_vkWaitSemaphoresKHR WaitSemaphoresKHR;
|
||||||
PFN_vkGetMemoryFdKHR GetMemoryFdKHR;
|
PFN_vkGetMemoryFdKHR GetMemoryFdKHR;
|
||||||
PFN_vkImportSemaphoreFdKHR ImportSemaphoreFdKHR;
|
PFN_vkImportSemaphoreFdKHR ImportSemaphoreFdKHR;
|
||||||
PFN_vkGetSemaphoreFdKHR GetSemaphoreFdKHR;
|
PFN_vkGetSemaphoreFdKHR GetSemaphoreFdKHR;
|
||||||
|
|
@ -130,10 +131,26 @@ namespace vk {
|
||||||
/// @param engineName name of the engine
|
/// @param engineName name of the engine
|
||||||
/// @param engineVersion version of the engine
|
/// @param engineVersion version of the engine
|
||||||
/// @param selectPhysicalDevice function to select the physical device
|
/// @param selectPhysicalDevice function to select the physical device
|
||||||
|
/// @param isGraphical whether the device is graphical (rather than compute)
|
||||||
/// @throws ls::vulkan_error on failure
|
/// @throws ls::vulkan_error on failure
|
||||||
Vulkan(const std::string& appName, version appVersion,
|
Vulkan(const std::string& appName, version appVersion,
|
||||||
const std::string& engineName, version engineVersion,
|
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
|
/// find a memory type index
|
||||||
/// @param validTypes bitset of valid memory types
|
/// @param validTypes bitset of valid memory types
|
||||||
|
|
@ -170,7 +187,7 @@ namespace vk {
|
||||||
VulkanInstanceFuncs instance_funcs;
|
VulkanInstanceFuncs instance_funcs;
|
||||||
|
|
||||||
VkPhysicalDevice physdev;
|
VkPhysicalDevice physdev;
|
||||||
uint32_t computeFamilyIdx;
|
uint32_t queueFamilyIdx;
|
||||||
bool fp16;
|
bool fp16;
|
||||||
|
|
||||||
ls::owned_ptr<VkDevice> device;
|
ls::owned_ptr<VkDevice> device;
|
||||||
|
|
|
||||||
|
|
@ -81,7 +81,7 @@ void TimelineSemaphore::signal(const vk::Vulkan& vk, uint64_t value) const {
|
||||||
.semaphore = *this->semaphore,
|
.semaphore = *this->semaphore,
|
||||||
.value = value
|
.value = value
|
||||||
};
|
};
|
||||||
auto res = vk.df().SignalSemaphore(vk.dev(), &signalInfo);
|
auto res = vk.df().SignalSemaphoreKHR(vk.dev(), &signalInfo);
|
||||||
if (res != VK_SUCCESS)
|
if (res != VK_SUCCESS)
|
||||||
throw ls::vulkan_error(res, "vkSignalSemaphore() failed");
|
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,
|
.pSemaphores = &semaphore,
|
||||||
.pValues = &value
|
.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)
|
if (res != VK_SUCCESS && res != VK_TIMEOUT)
|
||||||
throw ls::vulkan_error(res, "vkWaitSemaphores() failed");
|
throw ls::vulkan_error(res, "vkWaitSemaphores() failed");
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -341,9 +341,9 @@ VulkanDeviceFuncs vk::initVulkanDeviceFuncs(const VulkanInstanceFuncs& f, VkDevi
|
||||||
.CreateComputePipelines = dpa<PFN_vkCreateComputePipelines>(f, d,
|
.CreateComputePipelines = dpa<PFN_vkCreateComputePipelines>(f, d,
|
||||||
"vkCreateComputePipelines"),
|
"vkCreateComputePipelines"),
|
||||||
.DestroyPipeline = dpa<PFN_vkDestroyPipeline>(f, d, "vkDestroyPipeline"),
|
.DestroyPipeline = dpa<PFN_vkDestroyPipeline>(f, d, "vkDestroyPipeline"),
|
||||||
.SignalSemaphore = dpa<PFN_vkSignalSemaphore>(f, d, "vkSignalSemaphore"),
|
|
||||||
.WaitSemaphores = dpa<PFN_vkWaitSemaphores>(f, d, "vkWaitSemaphores"),
|
|
||||||
|
|
||||||
|
.SignalSemaphoreKHR = dpa<PFN_vkSignalSemaphoreKHR>(f, d, "vkSignalSemaphoreKHR"),
|
||||||
|
.WaitSemaphoresKHR = dpa<PFN_vkWaitSemaphoresKHR>(f, d, "vkWaitSemaphoresKHR"),
|
||||||
.GetMemoryFdKHR = dpa<PFN_vkGetMemoryFdKHR>(f, d, "vkGetMemoryFdKHR"),
|
.GetMemoryFdKHR = dpa<PFN_vkGetMemoryFdKHR>(f, d, "vkGetMemoryFdKHR"),
|
||||||
.ImportSemaphoreFdKHR = dpa<PFN_vkImportSemaphoreFdKHR>(f, d, "vkImportSemaphoreFdKHR"),
|
.ImportSemaphoreFdKHR = dpa<PFN_vkImportSemaphoreFdKHR>(f, d, "vkImportSemaphoreFdKHR"),
|
||||||
.GetSemaphoreFdKHR = dpa<PFN_vkGetSemaphoreFdKHR>(f, d, "vkGetSemaphoreFdKHR"),
|
.GetSemaphoreFdKHR = dpa<PFN_vkGetSemaphoreFdKHR>(f, d, "vkGetSemaphoreFdKHR"),
|
||||||
|
|
@ -352,7 +352,8 @@ VulkanDeviceFuncs vk::initVulkanDeviceFuncs(const VulkanInstanceFuncs& f, VkDevi
|
||||||
|
|
||||||
Vulkan::Vulkan(const std::string& appName, version appVersion,
|
Vulkan::Vulkan(const std::string& appName, version appVersion,
|
||||||
const std::string& engineName, version engineVersion,
|
const std::string& engineName, version engineVersion,
|
||||||
PhysicalDeviceSelector selectPhysicalDevice) :
|
PhysicalDeviceSelector selectPhysicalDevice,
|
||||||
|
bool isGraphical) :
|
||||||
instance(createInstance(
|
instance(createInstance(
|
||||||
appName, appVersion,
|
appName, appVersion,
|
||||||
engineName, engineVersion
|
engineName, engineVersion
|
||||||
|
|
@ -362,21 +363,45 @@ Vulkan::Vulkan(const std::string& appName, version appVersion,
|
||||||
*this->instance,
|
*this->instance,
|
||||||
selectPhysicalDevice
|
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)),
|
fp16(checkFP16(this->instance_funcs, this->physdev)),
|
||||||
device(createLogicalDevice(this->instance_funcs,
|
device(createLogicalDevice(this->instance_funcs,
|
||||||
this->physdev,
|
this->physdev,
|
||||||
this->computeFamilyIdx,
|
this->queueFamilyIdx,
|
||||||
this->fp16
|
this->fp16
|
||||||
)),
|
)),
|
||||||
device_funcs(initVulkanDeviceFuncs(
|
device_funcs(initVulkanDeviceFuncs(
|
||||||
this->instance_funcs,
|
this->instance_funcs,
|
||||||
*this->device
|
*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,
|
cmdPool(createCommandPool(this->device_funcs,
|
||||||
*this->device,
|
*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,
|
descPool(createDescriptorPool(this->device_funcs,
|
||||||
*this->device
|
*this->device
|
||||||
|
|
|
||||||
|
|
@ -134,7 +134,7 @@ namespace {
|
||||||
// create device
|
// create device
|
||||||
PFN_vkGetDeviceProcAddr nxvkGetDeviceProcAddr{nullptr};
|
PFN_vkGetDeviceProcAddr nxvkGetDeviceProcAddr{nullptr};
|
||||||
VkResult myvkCreateDevice(
|
VkResult myvkCreateDevice(
|
||||||
VkPhysicalDevice physicalDevice,
|
VkPhysicalDevice physdev,
|
||||||
const VkDeviceCreateInfo* info,
|
const VkDeviceCreateInfo* info,
|
||||||
const VkAllocationCallbacks* alloc,
|
const VkAllocationCallbacks* alloc,
|
||||||
VkDevice* device) {
|
VkDevice* device) {
|
||||||
|
|
@ -194,7 +194,7 @@ namespace {
|
||||||
newInfo.enabledExtensionCount = static_cast<uint32_t>(extensions.size());
|
newInfo.enabledExtensionCount = static_cast<uint32_t>(extensions.size());
|
||||||
newInfo.ppEnabledExtensionNames = extensions.data();
|
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)
|
if (res == VK_ERROR_EXTENSION_NOT_PRESENT)
|
||||||
std::cerr << "lsfg-vk: required Vulkan device extensions are not present. "
|
std::cerr << "lsfg-vk: required Vulkan device extensions are not present. "
|
||||||
"Your GPU driver is not supported.\n";
|
"Your GPU driver is not supported.\n";
|
||||||
|
|
@ -207,9 +207,13 @@ namespace {
|
||||||
global->device2InstanceMap.emplace(
|
global->device2InstanceMap.emplace(
|
||||||
*device,
|
*device,
|
||||||
layer::LayerInstance(
|
layer::LayerInstance(
|
||||||
global->layer, vk::initVulkanDeviceFuncs(global->fi, *device),
|
global->layer,
|
||||||
global->instance, *device,
|
vk::Vulkan(
|
||||||
setLoaderData
|
global->instance, *device,
|
||||||
|
physdev,
|
||||||
|
global->fi,
|
||||||
|
vk::initVulkanDeviceFuncs(global->fi, *device)
|
||||||
|
)
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
} catch (const std::exception& e) {
|
} catch (const std::exception& e) {
|
||||||
|
|
|
||||||
|
|
@ -3,12 +3,9 @@
|
||||||
#include "lsfg-vk-common/vulkan/vulkan.hpp"
|
#include "lsfg-vk-common/vulkan/vulkan.hpp"
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <string>
|
#include <utility>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#include <vulkan/vk_layer.h>
|
|
||||||
#include <vulkan/vulkan_core.h>
|
|
||||||
|
|
||||||
using namespace lsfgvk;
|
using namespace lsfgvk;
|
||||||
using namespace lsfgvk::layer;
|
using namespace lsfgvk::layer;
|
||||||
|
|
||||||
|
|
@ -69,14 +66,12 @@ std::vector<const char*> Layer::deviceExtensions() const {
|
||||||
"VK_KHR_external_memory",
|
"VK_KHR_external_memory",
|
||||||
"VK_KHR_external_memory_fd",
|
"VK_KHR_external_memory_fd",
|
||||||
"VK_KHR_external_semaphore",
|
"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,
|
layer::LayerInstance::LayerInstance(const Layer& layer, vk::Vulkan vk)
|
||||||
VkInstance instance, VkDevice device,
|
: vk(std::move(vk)) {
|
||||||
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<void*>(setLoaderData) << '\n';
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -7,9 +7,6 @@
|
||||||
#include <optional>
|
#include <optional>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#include <vulkan/vk_layer.h>
|
|
||||||
#include <vulkan/vulkan_core.h>
|
|
||||||
|
|
||||||
namespace lsfgvk::layer {
|
namespace lsfgvk::layer {
|
||||||
|
|
||||||
/// lsfg-vk layer
|
/// lsfg-vk layer
|
||||||
|
|
@ -48,15 +45,10 @@ namespace lsfgvk::layer {
|
||||||
public:
|
public:
|
||||||
/// create a new layer instance
|
/// create a new layer instance
|
||||||
/// @param layer parent layer
|
/// @param layer parent layer
|
||||||
/// @param df Vulkan device function pointers
|
/// @param vk vulkan instance
|
||||||
/// @param instance Vulkan instance
|
LayerInstance(const Layer& layer, vk::Vulkan vk);
|
||||||
/// @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);
|
|
||||||
private:
|
private:
|
||||||
Configuration config;
|
vk::Vulkan vk;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,30 +0,0 @@
|
||||||
#include "mini/commandpool.hpp"
|
|
||||||
#include "common/exception.hpp"
|
|
||||||
#include "layer.hpp"
|
|
||||||
|
|
||||||
#include <vulkan/vulkan_core.h>
|
|
||||||
|
|
||||||
#include <cstdint>
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
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<VkCommandPool>(
|
|
||||||
new VkCommandPool(commandPoolHandle),
|
|
||||||
[dev = device](VkCommandPool* commandPoolHandle) {
|
|
||||||
Layer::ovkDestroyCommandPool(dev, *commandPoolHandle, nullptr);
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
Loading…
Add table
Reference in a new issue