MayaFlux 0.3.0
Digital-First Multimedia Processing Framework
Loading...
Searching...
No Matches
VKCommandManager.cpp
Go to the documentation of this file.
2
4
5namespace MayaFlux::Core {
6
11
12bool VKCommandManager::initialize(vk::Device device, uint32_t graphics_queue_family, uint32_t compute_queue_family)
13{
14 m_device = device;
15 m_graphics_queue_family = graphics_queue_family;
16 m_compute_queue_family = compute_queue_family;
17
18 vk::CommandPoolCreateInfo pool_info {};
19 pool_info.queueFamilyIndex = graphics_queue_family;
20 pool_info.flags = vk::CommandPoolCreateFlagBits::eResetCommandBuffer;
21
22 try {
23 m_command_pool = device.createCommandPool(pool_info);
24 } catch (const vk::SystemError& e) {
26 "Failed to create command pool: {}", e.what());
27 return false;
28 }
29
30 pool_info.queueFamilyIndex = compute_queue_family;
31 try {
32 m_compute_command_pool = device.createCommandPool(pool_info);
33 } catch (const vk::SystemError& e) {
35 "Failed to create compute command pool: {}", e.what());
36 return false;
37 }
38
40 "Command manager initialized");
41
42 return true;
43}
44
46{
48 if (!m_compute_allocated_buffers.empty()) {
51 }
52 m_device.destroyCommandPool(m_compute_command_pool);
53 m_compute_command_pool = nullptr;
54 }
55
56 if (m_command_pool) {
57 if (!m_allocated_buffers.empty()) {
58 m_device.freeCommandBuffers(m_command_pool, m_allocated_buffers);
59 m_allocated_buffers.clear();
60 }
61
62 m_device.destroyCommandPool(m_command_pool);
63 m_command_pool = nullptr;
64 }
65}
66
67vk::CommandBuffer VKCommandManager::allocate_command_buffer(vk::CommandBufferLevel level)
68{
69 vk::CommandBufferAllocateInfo alloc_info {};
70 alloc_info.commandPool = m_command_pool;
71 alloc_info.level = level;
72 alloc_info.commandBufferCount = 1;
73
74 vk::CommandBuffer cmd_buffer;
75 try {
76 auto result = m_device.allocateCommandBuffers(&alloc_info, &cmd_buffer);
77 if (result != vk::Result::eSuccess) {
79 "Failed to allocate command buffer");
80 return nullptr;
81 }
82 m_allocated_buffers.push_back(cmd_buffer);
83 } catch (const vk::SystemError& e) {
85 "Failed to allocate command buffer: {}", e.what());
86 return nullptr;
87 }
88
90 "Allocated {} command buffer",
91 level == vk::CommandBufferLevel::ePrimary ? "primary" : "secondary");
92
93 return cmd_buffer;
94}
95
96void VKCommandManager::free_command_buffer(vk::CommandBuffer command_buffer)
97{
98 if (!command_buffer) {
99 return;
100 }
101
102 auto it = std::ranges::find(m_allocated_buffers, command_buffer);
103 if (it != m_allocated_buffers.end()) {
104 m_device.freeCommandBuffers(m_command_pool, 1, &command_buffer);
105 m_allocated_buffers.erase(it);
106 }
107
108 auto it2 = std::ranges::find(m_compute_allocated_buffers, command_buffer);
109 if (it2 != m_compute_allocated_buffers.end()) {
110 m_device.freeCommandBuffers(m_compute_command_pool, 1, &command_buffer);
112 }
113}
114
116{
117 vk::CommandBuffer command_buffer = allocate_command_buffer();
118
119 vk::CommandBufferBeginInfo begin_info {};
120 begin_info.flags = vk::CommandBufferUsageFlagBits::eOneTimeSubmit;
121
122 command_buffer.begin(begin_info);
123
124 return command_buffer;
125}
126
128{
129 vk::CommandBufferAllocateInfo alloc_info {};
130 alloc_info.commandPool = m_compute_command_pool;
131 alloc_info.level = vk::CommandBufferLevel::ePrimary;
132 alloc_info.commandBufferCount = 1;
133
134 vk::CommandBuffer cmd = m_device.allocateCommandBuffers(alloc_info).front();
135 m_compute_allocated_buffers.push_back(cmd);
136
137 vk::CommandBufferBeginInfo begin_info {};
138 begin_info.flags = vk::CommandBufferUsageFlagBits::eOneTimeSubmit;
139 cmd.begin(begin_info);
140 return cmd;
141}
142
143void VKCommandManager::end_single_time_commands(vk::CommandBuffer command_buffer, vk::Queue queue)
144{
145 command_buffer.end();
146
147 vk::SubmitInfo submit_info {};
148 submit_info.commandBufferCount = 1;
149 submit_info.pCommandBuffers = &command_buffer;
150
151 if (auto result = queue.submit(1, &submit_info, nullptr); result != vk::Result::eSuccess) {
153 "Failed to submit single time command buffer: {}", vk::to_string(result));
154 }
155 queue.waitIdle();
156
157 free_command_buffer(command_buffer);
158}
159
161{
162 m_device.resetCommandPool(m_command_pool, vk::CommandPoolResetFlags {});
163}
164
165} // namespace MayaFlux::Core
#define MF_INFO(comp, ctx,...)
#define MF_ERROR(comp, ctx,...)
#define MF_RT_TRACE(comp, ctx,...)
void reset_pool()
Reset command pool (invalidates all allocated buffers)
void end_single_time_commands(vk::CommandBuffer command_buffer, vk::Queue queue)
End and submit single-time command.
std::vector< vk::CommandBuffer > m_compute_allocated_buffers
vk::CommandBuffer begin_single_time_commands_compute()
Begin single-time command for compute operations.
void free_command_buffer(vk::CommandBuffer command_buffer)
Free a command buffer back to the pool.
vk::CommandBuffer begin_single_time_commands()
Begin single-time command (for transfers, etc.)
std::vector< vk::CommandBuffer > m_allocated_buffers
bool initialize(vk::Device device, uint32_t graphics_queue_family, uint32_t compute_queue_family)
Initialize command manager.
void cleanup()
Cleanup all command pools and buffers.
vk::CommandBuffer allocate_command_buffer(vk::CommandBufferLevel level=vk::CommandBufferLevel::ePrimary)
Allocate a command buffer with specified level.
@ GraphicsBackend
Graphics/visual rendering backend (Vulkan, OpenGL)
@ Core
Core engine, backend, subsystems.