Aeon Engine c550894
AeonGames Open Source Game Engine
Loading...
Searching...
No Matches
VulkanMemoryPoolBuffer.cpp
1/*
2Copyright (C) 2019,2021,2025,2026 Rodrigo Jose Hernandez Cordoba
3
4Licensed under the Apache License, Version 2.0 (the "License");
5you may not use this file except in compliance with the License.
6You may obtain a copy of the License at
7
8http://www.apache.org/licenses/LICENSE-2.0
9
10Unless required by applicable law or agreed to in writing, software
11distributed under the License is distributed on an "AS IS" BASIS,
12WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13See the License for the specific language governing permissions and
14limitations under the License.
15*/
16#include <fstream>
17#include <ostream>
18#include <regex>
19#include <array>
20#include <utility>
21#include <cassert>
22#include "aeongames/AeonEngine.hpp"
23#include "aeongames/CRC.hpp"
24#include "aeongames/Material.hpp"
25#include "aeongames/Vector2.hpp"
26#include "aeongames/Vector3.hpp"
27#include "aeongames/Vector4.hpp"
29#include "VulkanMemoryPoolBuffer.hpp"
30#include "VulkanRenderer.hpp"
31#include "VulkanUtilities.hpp"
32
33namespace AeonGames
34{
35 VulkanMemoryPoolBuffer::VulkanMemoryPoolBuffer ( const VulkanRenderer& aVulkanRenderer, size_t aStackSize ) :
36 mVulkanRenderer { aVulkanRenderer },
37 mUniformBuffer { mVulkanRenderer,
38 ( ( aStackSize - 1 ) | ( mVulkanRenderer.GetPhysicalDeviceProperties().limits.minUniformBufferOffsetAlignment - 1 ) ) + 1, // Adjust for alignment
39 VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT,
40 VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT }
41 {
42 InitializeDescriptorPool();
43 InitializeDescriptorSet();
44 }
45
47 mVulkanRenderer { aVulkanMemoryPoolBuffer.mVulkanRenderer },
48 mUniformBuffer { std::move ( aVulkanMemoryPoolBuffer.mUniformBuffer ) }
49 {
50 std::swap ( mOffset, aVulkanMemoryPoolBuffer.mOffset );
51 std::swap ( mVkDescriptorPool, aVulkanMemoryPoolBuffer.mVkDescriptorPool );
52 std::swap ( mVkDescriptorSet, aVulkanMemoryPoolBuffer.mVkDescriptorSet );
53 }
54
56 mVulkanRenderer { aVulkanRenderer }, mUniformBuffer{aVulkanRenderer} {}
57
58 void VulkanMemoryPoolBuffer::Initialize ( size_t aStackSize )
59 {
60 mUniformBuffer.Initialize ( ( ( aStackSize - 1 ) | ( mVulkanRenderer.GetPhysicalDeviceProperties().limits.minUniformBufferOffsetAlignment - 1 ) ) + 1, // Adjust for alignment
61 VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT,
62 VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT );
63 InitializeDescriptorPool();
64 InitializeDescriptorSet();
65 }
66
67 VulkanMemoryPoolBuffer::~VulkanMemoryPoolBuffer()
68 {
69 Finalize();
70 }
71
73 {
74 FinalizeDescriptorPool();
75 mUniformBuffer.Finalize();
76 }
77
78 void VulkanMemoryPoolBuffer::InitializeDescriptorPool()
79 {
80 mVkDescriptorPool = CreateDescriptorPool ( mVulkanRenderer.GetDevice(), {{VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC, 1}} );
81 }
82
83 void VulkanMemoryPoolBuffer::InitializeDescriptorSet()
84 {
85 VkDescriptorSetLayoutCreateInfo descriptor_set_layout_create_info{};
86 descriptor_set_layout_create_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO;
87 descriptor_set_layout_create_info.bindingCount = 1;
88 VkDescriptorSetLayoutBinding descriptor_set_layout_binding{};
89 descriptor_set_layout_binding.binding = 0;
90 descriptor_set_layout_binding.descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC;
91 descriptor_set_layout_binding.descriptorCount = 1;
92 // Only vertex shaders will access these for now, add a flag for other stages if needed
93 //descriptor_set_layout_binding.stageFlags = VK_SHADER_STAGE_VERTEX_BIT;
94 descriptor_set_layout_binding.stageFlags = VK_SHADER_STAGE_ALL;
95 descriptor_set_layout_binding.pImmutableSamplers = nullptr;
96 descriptor_set_layout_create_info.pBindings = &descriptor_set_layout_binding;
97 mVkDescriptorSet = CreateDescriptorSet ( mVulkanRenderer.GetDevice(), mVkDescriptorPool, mVulkanRenderer.GetDescriptorSetLayout ( descriptor_set_layout_create_info ) );
98
99 VkDescriptorBufferInfo descriptor_buffer_info = { mUniformBuffer.GetBuffer(), 0, mUniformBuffer.GetSize() };
100 VkWriteDescriptorSet write_descriptor_set{};
101 write_descriptor_set.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
102 write_descriptor_set.pNext = nullptr;
103 write_descriptor_set.dstSet = mVkDescriptorSet;
104 write_descriptor_set.dstBinding = 0;
105 write_descriptor_set.dstArrayElement = 0;
106 write_descriptor_set.descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC;
107 write_descriptor_set.descriptorCount = 1;
108 write_descriptor_set.pBufferInfo = &descriptor_buffer_info;
109 write_descriptor_set.pImageInfo = nullptr;
110 write_descriptor_set.pTexelBufferView = nullptr;
111 vkUpdateDescriptorSets ( mVulkanRenderer.GetDevice(), 1, &write_descriptor_set, 0, nullptr );
112 }
113
114 void VulkanMemoryPoolBuffer::FinalizeDescriptorPool()
115 {
116 if ( mVkDescriptorPool != VK_NULL_HANDLE )
117 {
118 vkDestroyDescriptorPool ( mVulkanRenderer.GetDevice(), mVkDescriptorPool, nullptr );
119 mVkDescriptorPool = VK_NULL_HANDLE;
120 }
121 }
122
124 {
125 size_t offset = mOffset;
126 mOffset += ( ( aSize - 1 ) | ( mVulkanRenderer.GetPhysicalDeviceProperties().limits.minUniformBufferOffsetAlignment - 1 ) ) + 1;
127 if ( mOffset > mUniformBuffer.GetSize() )
128 {
129 mOffset = offset;
130 std::cout << LogLevel::Error << "Memory Pool Buffer cannot fulfill allocation request." << std::endl;
131 throw std::runtime_error ( "Memory Pool Buffer cannot fulfill allocation request." );
132 }
133 return BufferAccessor{this, offset, aSize};
134 }
135
137 {
138 mOffset = 0;
139 }
140
141 const VkDescriptorSet& VulkanMemoryPoolBuffer::GetDescriptorSet() const
142 {
143 return mVkDescriptorSet;
144 }
146 {
147 return mUniformBuffer;
148 }
149}
Defines log severity levels and stream output for the AeonGames engine.
Header for the 3D vector class.
Header for the 4D vector class.
Provides access to a region within a memory pool buffer.
Abstract interface for GPU/memory buffer operations.
Definition Buffer.hpp:24
const VkDescriptorSet & GetDescriptorSet() const
Get the Vulkan descriptor set for this pool buffer.
void Initialize(size_t aStackSize)
Initialize the pool buffer with the given size.
VulkanMemoryPoolBuffer(const VulkanRenderer &aVulkanRenderer, size_t aStackSize)
Construct with a renderer and initial pool size.
const Buffer & GetBuffer() const final
Get a reference to the underlying Buffer.
void Finalize()
Release pool buffer and descriptor resources.
BufferAccessor Allocate(size_t aSize) final
Allocate a sub-region from the memory pool.
void Reset() final
Reset the pool, freeing all previous allocations.
Vulkan rendering backend implementing the Renderer interface.
const VkDevice & GetDevice() const
Get the logical device handle.
<- This is here just for the literals
Definition AABB.hpp:31
VkDescriptorPool CreateDescriptorPool(const VkDevice &aVkDevice, const std::vector< VkDescriptorPoolSize > &aVkDescriptorPoolSizes)
Create a Vulkan descriptor pool from the given pool sizes.
@ Error
Error conditions.
Definition LogLevel.hpp:33
VkDescriptorSet CreateDescriptorSet(const VkDevice &aVkDevice, const VkDescriptorPool &aVkDescriptorPool, const VkDescriptorSetLayout &aVkDescriptorSetLayout, uint32_t aDescriptorSetCount)
Allocate a Vulkan descriptor set from the given pool and layout.
STL namespace.