From d6795f97ef1410982622df04c3d5d2c97b332c4f Mon Sep 17 00:00:00 2001 From: Kbz-8 Date: Sat, 11 Nov 2023 03:30:29 +0100 Subject: [PATCH] fixing physical device pick issues --- Makefile | 7 ++++- src/renderer/buffers/vk_buffer.cpp | 23 +++++++------- src/renderer/buffers/vk_buffer.h | 12 +++----- src/renderer/buffers/vk_ibo.h | 4 +-- src/renderer/buffers/vk_vbo.h | 8 ++--- src/renderer/core/memory.cpp | 41 ++++++++++++++----------- src/renderer/core/vk_device.cpp | 49 ++++++++++++++++++++++-------- src/renderer/core/vk_device.h | 7 +++-- test/.gdb_history | 10 ++++++ 9 files changed, 100 insertions(+), 61 deletions(-) create mode 100644 test/.gdb_history diff --git a/Makefile b/Makefile index b3056d1..25852ed 100644 --- a/Makefile +++ b/Makefile @@ -6,7 +6,7 @@ # By: maldavid +#+ +:+ +#+ # # +#+#+#+#+#+ +#+ # # Created: 2022/10/04 16:43:41 by maldavid #+# #+# # -# Updated: 2023/10/20 00:03:33 by maldavid ### ########.fr # +# Updated: 2023/11/10 23:55:12 by maldavid ### ########.fr # # # # **************************************************************************** # @@ -23,6 +23,7 @@ OS = $(shell uname -s) DEBUG ?= false TOOLCHAIN ?= clang IMAGES_OPTIMIZED ?= true +FORCE_INTEGRATED_GPU ?= false CXX = clang++ @@ -43,6 +44,10 @@ ifeq ($(DEBUG), true) CXXFLAGS += -g -D DEBUG endif +ifeq ($(FORCE_INTEGRATED_GPU), true) + CXXFLAGS += -D FORCE_INTEGRATED_GPU +endif + ifeq ($(IMAGES_OPTIMIZED), true) CXXFLAGS += -D IMAGE_OPTIMIZED endif diff --git a/src/renderer/buffers/vk_buffer.cpp b/src/renderer/buffers/vk_buffer.cpp index 21bdeff..67ad5c7 100644 --- a/src/renderer/buffers/vk_buffer.cpp +++ b/src/renderer/buffers/vk_buffer.cpp @@ -6,7 +6,7 @@ /* By: maldavid +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2022/10/08 18:55:57 by maldavid #+# #+# */ -/* Updated: 2023/11/10 08:14:42 by maldavid ### ########.fr */ +/* Updated: 2023/11/11 03:27:31 by maldavid ### ########.fr */ /* */ /* ************************************************************************** */ @@ -15,12 +15,15 @@ #include #include #include +#include namespace mlx { void Buffer::create(Buffer::kind type, VkDeviceSize size, VkBufferUsageFlags usage, const void* data) { + _usage = usage; VmaAllocationCreateInfo alloc_info{}; + alloc_info.flags = VMA_ALLOCATION_CREATE_HOST_ACCESS_RANDOM_BIT; if(type == Buffer::kind::constant) { if(data == nullptr) @@ -28,19 +31,13 @@ namespace mlx core::error::report(e_kind::warning, "Vulkan : trying to create constant buffer without data (constant buffers cannot be modified after creation)"); return; } - _usage = usage | VK_BUFFER_USAGE_TRANSFER_SRC_BIT; - alloc_info.usage = VMA_MEMORY_USAGE_GPU_ONLY; + _usage |= VK_BUFFER_USAGE_TRANSFER_SRC_BIT; + alloc_info.usage = VMA_MEMORY_USAGE_AUTO_PREFER_HOST; } else if(type == Buffer::kind::uniform) - { - _usage = usage; - alloc_info.usage = VMA_MEMORY_USAGE_CPU_TO_GPU; - } + alloc_info.usage = VMA_MEMORY_USAGE_AUTO_PREFER_HOST; else - { - _usage = usage; - alloc_info.usage = VMA_MEMORY_USAGE_GPU_TO_CPU; - } + alloc_info.usage = VMA_MEMORY_USAGE_AUTO; createBuffer(_usage, alloc_info, size); @@ -58,6 +55,8 @@ namespace mlx void Buffer::destroy() noexcept { + if(_is_mapped) + unmapMem(); Render_Core::get().getAllocator().destroyBuffer(_allocation, _buffer); } @@ -75,7 +74,7 @@ namespace mlx void Buffer::pushToGPU() noexcept { VmaAllocationCreateInfo alloc_info{}; - alloc_info.usage = VMA_MEMORY_USAGE_GPU_ONLY; + alloc_info.usage = VMA_MEMORY_USAGE_AUTO_PREFER_DEVICE; Buffer newBuffer; newBuffer._usage = (_usage & 0xFFFFFFFC) | VK_BUFFER_USAGE_TRANSFER_DST_BIT; diff --git a/src/renderer/buffers/vk_buffer.h b/src/renderer/buffers/vk_buffer.h index e5c4126..9b7b2b0 100644 --- a/src/renderer/buffers/vk_buffer.h +++ b/src/renderer/buffers/vk_buffer.h @@ -6,7 +6,7 @@ /* By: maldavid +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2022/10/06 23:18:52 by maldavid #+# #+# */ -/* Updated: 2023/11/09 19:38:30 by maldavid ### ########.fr */ +/* Updated: 2023/11/11 03:29:40 by maldavid ### ########.fr */ /* */ /* ************************************************************************** */ @@ -23,14 +23,11 @@ namespace mlx public: enum class kind { dynamic, uniform, constant }; +:q void create(kind type, VkDeviceSize size, VkBufferUsageFlags usage, const void* data = nullptr); void destroy() noexcept; - inline void mapMem(void** data = nullptr) noexcept - { - Render_Core::get().getAllocator().mapMemory(_allocation, data); - _is_mapped = true; - } + inline void mapMem(void** data = nullptr) noexcept { Render_Core::get().getAllocator().mapMemory(_allocation, data); _is_mapped = true; } inline bool isMapped() const noexcept { return _is_mapped; } inline void unmapMem() noexcept { Render_Core::get().getAllocator().unmapMemory(_allocation);_is_mapped = false; } @@ -39,7 +36,7 @@ namespace mlx inline VkBuffer& operator()() noexcept { return _buffer; } inline VkBuffer& get() noexcept { return _buffer; } inline VkDeviceSize getSize() const noexcept { return _alloc_infos.size; } - inline VkDeviceSize getOffset() const noexcept { return _alloc_infos.offset; } + inline VkDeviceSize getOffset() const noexcept { return _offset; } protected: void pushToGPU() noexcept; @@ -49,6 +46,7 @@ namespace mlx VmaAllocation _allocation; VmaAllocationInfo _alloc_infos; VkBuffer _buffer = VK_NULL_HANDLE; + VkDeviceSize _offset = 0; private: void createBuffer(VkBufferUsageFlags usage, VmaAllocationCreateInfo info, VkDeviceSize size); diff --git a/src/renderer/buffers/vk_ibo.h b/src/renderer/buffers/vk_ibo.h index d986fa3..016c097 100644 --- a/src/renderer/buffers/vk_ibo.h +++ b/src/renderer/buffers/vk_ibo.h @@ -6,7 +6,7 @@ /* By: maldavid +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2023/01/25 15:05:05 by maldavid #+# #+# */ -/* Updated: 2023/11/10 07:53:26 by maldavid ### ########.fr */ +/* Updated: 2023/11/11 03:08:10 by maldavid ### ########.fr */ /* */ /* ************************************************************************** */ @@ -23,7 +23,7 @@ namespace mlx { public: inline void create(uint32_t size, const uint16_t* data) { Buffer::create(Buffer::kind::constant, size, VK_BUFFER_USAGE_INDEX_BUFFER_BIT, data); } - inline void bind(Renderer& renderer) noexcept { vkCmdBindIndexBuffer(renderer.getActiveCmdBuffer().get(), _buffer, getOffset(), VK_INDEX_TYPE_UINT16); } + inline void bind(Renderer& renderer) noexcept { vkCmdBindIndexBuffer(renderer.getActiveCmdBuffer().get(), _buffer, 0, VK_INDEX_TYPE_UINT16); } }; } diff --git a/src/renderer/buffers/vk_vbo.h b/src/renderer/buffers/vk_vbo.h index d4c9a61..2e1f67b 100644 --- a/src/renderer/buffers/vk_vbo.h +++ b/src/renderer/buffers/vk_vbo.h @@ -6,7 +6,7 @@ /* By: maldavid +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2022/10/06 18:27:38 by maldavid #+# #+# */ -/* Updated: 2023/11/10 07:54:15 by maldavid ### ########.fr */ +/* Updated: 2023/11/11 03:22:44 by maldavid ### ########.fr */ /* */ /* ************************************************************************** */ @@ -22,17 +22,15 @@ namespace mlx { public: inline void create(uint32_t size) { Buffer::create(Buffer::kind::dynamic, size, VK_BUFFER_USAGE_VERTEX_BUFFER_BIT); } - void setData(uint32_t size, const void* data); - - inline void bind(Renderer& renderer) noexcept { vkCmdBindVertexBuffers(renderer.getActiveCmdBuffer().get(), 0, 1, &_buffer, &_alloc_infos.offset); } + inline void bind(Renderer& renderer) noexcept { vkCmdBindVertexBuffers(renderer.getActiveCmdBuffer().get(), 0, 1, &_buffer, &_offset); } }; class C_VBO : public Buffer { public: inline void create(uint32_t size, const void* data) { Buffer::create(Buffer::kind::constant, size, VK_BUFFER_USAGE_VERTEX_BUFFER_BIT, data); } - inline void bind(Renderer& renderer) noexcept { vkCmdBindVertexBuffers(renderer.getActiveCmdBuffer().get(), 0, 1, &_buffer, &_alloc_infos.offset); } + inline void bind(Renderer& renderer) noexcept { vkCmdBindVertexBuffers(renderer.getActiveCmdBuffer().get(), 0, 1, &_buffer, &_offset); } }; } diff --git a/src/renderer/core/memory.cpp b/src/renderer/core/memory.cpp index 3a36be9..1104e15 100644 --- a/src/renderer/core/memory.cpp +++ b/src/renderer/core/memory.cpp @@ -6,7 +6,7 @@ /* By: kbz_8 +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2023/10/20 22:02:37 by kbz_8 #+# #+# */ -/* Updated: 2023/11/10 09:07:33 by maldavid ### ########.fr */ +/* Updated: 2023/11/10 23:29:56 by maldavid ### ########.fr */ /* */ /* ************************************************************************** */ @@ -34,23 +34,28 @@ namespace mlx void GPUallocator::init() noexcept { VmaVulkanFunctions vma_vulkan_func{}; - vma_vulkan_func.vkAllocateMemory = vkAllocateMemory; - vma_vulkan_func.vkBindBufferMemory = vkBindBufferMemory; - vma_vulkan_func.vkBindImageMemory = vkBindImageMemory; - vma_vulkan_func.vkCreateBuffer = vkCreateBuffer; - vma_vulkan_func.vkCreateImage = vkCreateImage; - vma_vulkan_func.vkDestroyBuffer = vkDestroyBuffer; - vma_vulkan_func.vkDestroyImage = vkDestroyImage; - vma_vulkan_func.vkFlushMappedMemoryRanges = vkFlushMappedMemoryRanges; - vma_vulkan_func.vkFreeMemory = vkFreeMemory; - vma_vulkan_func.vkGetBufferMemoryRequirements = vkGetBufferMemoryRequirements; - vma_vulkan_func.vkGetImageMemoryRequirements = vkGetImageMemoryRequirements; - vma_vulkan_func.vkGetPhysicalDeviceMemoryProperties = vkGetPhysicalDeviceMemoryProperties; - vma_vulkan_func.vkGetPhysicalDeviceProperties = vkGetPhysicalDeviceProperties; - vma_vulkan_func.vkInvalidateMappedMemoryRanges = vkInvalidateMappedMemoryRanges; - vma_vulkan_func.vkMapMemory = vkMapMemory; - vma_vulkan_func.vkUnmapMemory = vkUnmapMemory; - vma_vulkan_func.vkCmdCopyBuffer = vkCmdCopyBuffer; + vma_vulkan_func.vkAllocateMemory = vkAllocateMemory; + vma_vulkan_func.vkBindBufferMemory = vkBindBufferMemory; + vma_vulkan_func.vkBindImageMemory = vkBindImageMemory; + vma_vulkan_func.vkCreateBuffer = vkCreateBuffer; + vma_vulkan_func.vkCreateImage = vkCreateImage; + vma_vulkan_func.vkDestroyBuffer = vkDestroyBuffer; + vma_vulkan_func.vkDestroyImage = vkDestroyImage; + vma_vulkan_func.vkFlushMappedMemoryRanges = vkFlushMappedMemoryRanges; + vma_vulkan_func.vkFreeMemory = vkFreeMemory; + vma_vulkan_func.vkGetBufferMemoryRequirements = vkGetBufferMemoryRequirements; + vma_vulkan_func.vkGetImageMemoryRequirements = vkGetImageMemoryRequirements; + vma_vulkan_func.vkGetPhysicalDeviceMemoryProperties = vkGetPhysicalDeviceMemoryProperties; + vma_vulkan_func.vkGetPhysicalDeviceProperties = vkGetPhysicalDeviceProperties; + vma_vulkan_func.vkInvalidateMappedMemoryRanges = vkInvalidateMappedMemoryRanges; + vma_vulkan_func.vkMapMemory = vkMapMemory; + vma_vulkan_func.vkUnmapMemory = vkUnmapMemory; + vma_vulkan_func.vkCmdCopyBuffer = vkCmdCopyBuffer; + vma_vulkan_func.vkGetBufferMemoryRequirements2KHR = vkGetBufferMemoryRequirements2; + vma_vulkan_func.vkGetImageMemoryRequirements2KHR = vkGetImageMemoryRequirements2; + vma_vulkan_func.vkBindBufferMemory2KHR = vkBindBufferMemory2; + vma_vulkan_func.vkBindImageMemory2KHR = vkBindImageMemory2; + vma_vulkan_func.vkGetPhysicalDeviceMemoryProperties2KHR = vkGetPhysicalDeviceMemoryProperties2; VmaAllocatorCreateInfo allocatorCreateInfo{}; allocatorCreateInfo.vulkanApiVersion = VK_API_VERSION_1_2; diff --git a/src/renderer/core/vk_device.cpp b/src/renderer/core/vk_device.cpp index 5306e15..4aaa523 100644 --- a/src/renderer/core/vk_device.cpp +++ b/src/renderer/core/vk_device.cpp @@ -6,7 +6,7 @@ /* By: maldavid +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2022/10/08 19:14:29 by maldavid #+# #+# */ -/* Updated: 2023/11/08 20:14:08 by maldavid ### ########.fr */ +/* Updated: 2023/11/11 02:14:58 by maldavid ### ########.fr */ /* */ /* ************************************************************************** */ @@ -16,6 +16,7 @@ #include #include #include +#include namespace mlx { @@ -81,35 +82,57 @@ namespace mlx if(SDL_Vulkan_CreateSurface(window, Render_Core::get().getInstance().get(), &surface) != SDL_TRUE) core::error::report(e_kind::fatal_error, "Vulkan : failed to create a surface to pick physical device"); + std::vector> devices_score; + for(const auto& device : devices) - { - if(isDeviceSuitable(device, surface)) - { - _physicalDevice = device; - break; - } - } + devices_score.emplace_back(deviceScore(device, surface), device); vkDestroySurfaceKHR(Render_Core::get().getInstance().get(), surface, nullptr); SDL_DestroyWindow(window); + using device_pair = std::pair; + std::sort(devices_score.begin(), devices_score.end(), [](const device_pair& a, const device_pair& b) + { + return a.first > b.first; + }); + + if(devices_score.front().first > 0) + _physicalDevice = devices_score.front().second; + if(_physicalDevice == VK_NULL_HANDLE) core::error::report(e_kind::fatal_error, "Vulkan : failed to find a suitable GPU"); + VkPhysicalDeviceProperties props; + vkGetPhysicalDeviceProperties(_physicalDevice, &props); #ifdef DEBUG - core::error::report(e_kind::message, "Vulkan : picked a physical device"); + core::error::report(e_kind::message, "Vulkan : picked a physical device, %s", props.deviceName); #endif } - - bool Device::isDeviceSuitable(VkPhysicalDevice device, VkSurfaceKHR surface) + + int Device::deviceScore(VkPhysicalDevice device, VkSurfaceKHR surface) { Queues::QueueFamilyIndices indices = Render_Core::get().getQueue().findQueueFamilies(device, surface); - bool extensionsSupported = checkDeviceExtensionSupport(device); uint32_t formatCount = 0; if(extensionsSupported) vkGetPhysicalDeviceSurfaceFormatsKHR(device, surface, &formatCount, nullptr); - return indices.isComplete() && extensionsSupported && formatCount != 0; + + VkPhysicalDeviceProperties props; + vkGetPhysicalDeviceProperties(device, &props); + if(!indices.isComplete() || !extensionsSupported || formatCount == 0) + return -1; + + int score = 0; + #ifndef FORCE_INTEGRATED_GPU + if(props.deviceType == VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU) + score += 1000; + #else + if(props.deviceType != VK_PHYSICAL_DEVICE_TYPE_INTEGRATED_GPU) + return -1; + #endif + score += props.limits.maxImageDimension2D; + score += props.limits.maxBoundDescriptorSets; + return score; } bool Device::checkDeviceExtensionSupport(VkPhysicalDevice device) diff --git a/src/renderer/core/vk_device.h b/src/renderer/core/vk_device.h index eb9a116..4078c96 100644 --- a/src/renderer/core/vk_device.h +++ b/src/renderer/core/vk_device.h @@ -6,7 +6,7 @@ /* By: maldavid +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2022/10/08 19:13:42 by maldavid #+# #+# */ -/* Updated: 2022/12/18 22:55:30 by maldavid ### ########.fr */ +/* Updated: 2023/11/11 01:51:26 by maldavid ### ########.fr */ /* */ /* ************************************************************************** */ @@ -28,12 +28,13 @@ namespace mlx inline VkDevice& get() noexcept { return _device; } inline VkPhysicalDevice& getPhysicalDevice() noexcept { return _physicalDevice; } - + private: void pickPhysicalDevice(); - bool isDeviceSuitable(VkPhysicalDevice device, VkSurfaceKHR surface); bool checkDeviceExtensionSupport(VkPhysicalDevice device); + int deviceScore(VkPhysicalDevice device, VkSurfaceKHR surface); + private: VkPhysicalDevice _physicalDevice = VK_NULL_HANDLE; VkDevice _device = VK_NULL_HANDLE; }; diff --git a/test/.gdb_history b/test/.gdb_history new file mode 100644 index 0000000..aae9e21 --- /dev/null +++ b/test/.gdb_history @@ -0,0 +1,10 @@ +b mlx::Buffer::create +run +q +b mlx::Buffer::create +run +bt +n +tui e +n +q