Browse Source

Semaphore wrapper.

master
Draklaw 4 years ago
parent
commit
c73d773845
  1. 1
      CMakeLists.txt
  2. 26
      src/VulkanTutorial.cpp
  3. 9
      src/VulkanTutorial.h
  4. 65
      src/vk/Semaphore.cpp
  5. 61
      src/vk/Semaphore.h
  6. 29
      src/vk/Swapchain.cpp
  7. 5
      src/vk/Swapchain.h

1
CMakeLists.txt

@ -38,6 +38,7 @@ add_executable(vk_expe
src/vk/Context.cpp
src/vk/Fence.cpp
src/vk/Semaphore.cpp
src/vk/Swapchain.cpp
src/vk/Memory.cpp
src/vk/Buffer.cpp

26
src/VulkanTutorial.cpp

@ -187,8 +187,6 @@ void VulkanTutorial::shutdown() {
m_vertex_buffer.destroy();
m_context.destroy_descriptor_set_layout(m_descriptor_set_layout);
for(VkSemaphore semaphore: m_render_done)
m_context.destroy_semaphore(semaphore);
m_render_done.clear();
m_swapchain.shutdown();
@ -254,6 +252,9 @@ void VulkanTutorial::draw_frame() {
VkSemaphore wait_semaphores[] = {
m_swapchain.ready_to_render(),
};
VkSemaphore done_semaphores[] = {
m_render_done[image_index],
};
VkPipelineStageFlags stages[] = {
VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT,
};
@ -265,7 +266,7 @@ void VulkanTutorial::draw_frame() {
.commandBufferCount = 1,
.pCommandBuffers = &m_command_buffers[image_index],
.signalSemaphoreCount = 1,
.pSignalSemaphores = &m_render_done[image_index],
.pSignalSemaphores = done_semaphores,
};
if(vkQueueSubmit(
@ -275,7 +276,7 @@ void VulkanTutorial::draw_frame() {
))
throw std::runtime_error("failed to submit draw command buffer");
m_swapchain.swap_buffers({1, &m_render_done[image_index]});
m_swapchain.swap_buffers({1, done_semaphores});
}
void VulkanTutorial::invalidate_swapchain() {
@ -291,20 +292,9 @@ void VulkanTutorial::create_swapchain_objects(uint32_t image_count) {
create_graphic_pipeline();
create_command_buffers();
m_render_done.resize(m_swapchain.image_count());
VkSemaphoreCreateInfo semaphore_info {
.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO,
};
for(size_t index = 0; index < m_render_done.size(); index += 1) {
if(vkCreateSemaphore(
m_context.device(),
&semaphore_info,
nullptr,
&m_render_done[index]
) != VK_SUCCESS)
throw std::runtime_error("failed to create semaphore");
m_render_done.clear();
for(size_t index = 0; index < m_swapchain.image_count(); index += 1) {
m_render_done.emplace_back(m_context);
}
}

9
src/VulkanTutorial.h

@ -1,10 +1,11 @@
// Copyright 2022 Simon Boyé
#pragma once
#include <vk/Context.h>
#include <vk/Swapchain.h>
#include <vk/Buffer.h>
#include <vk/Semaphore.h>
#include <vk/RenderPass.h>
#include <vk/Buffer.h>
#include <vk/Swapchain.h>
#include <vk/Context.h>
#include <core/math.h>
@ -84,7 +85,7 @@ private:
VkDescriptorPool m_descriptor_pool = VK_NULL_HANDLE;
std::vector<VkDescriptorSet> m_descriptor_sets;
std::vector<VkCommandBuffer> m_command_buffers;
std::vector<VkSemaphore> m_render_done;
std::vector<vk::Semaphore> m_render_done;
Vector3 m_camera_position = Vector3(0.0f, 0.0f, -3.0f);
Vector3 m_camera_z = Vector3(0.0f, 0.0f, 1.0f);

65
src/vk/Semaphore.cpp

@ -0,0 +1,65 @@
// Copyright 2022 Simon Boyé
#include <vk/Semaphore.h>
#include <vk/Context.h>
#include <cassert>
namespace vk {
Semaphore::Semaphore() noexcept {
}
Semaphore::Semaphore(Context& context)
: m_context(&context)
{
assert(m_context);
VkSemaphoreCreateInfo create_info {
.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO,
};
if(vkCreateSemaphore(
context.device(),
&create_info,
nullptr,
&m_semaphore
) != VK_SUCCESS)
throw std::runtime_error("failed to create semaphore");
}
Semaphore::Semaphore(Semaphore&& other) noexcept
{
swap(*this, other);
}
Semaphore::~Semaphore() noexcept {
if(!is_null())
destroy();
}
Semaphore& Semaphore::operator=(Semaphore&& other) noexcept {
swap(*this, other);
if(other)
other.destroy();
return *this;
}
void Semaphore::destroy() noexcept {
assert(!is_null());
assert(m_context);
vkDestroySemaphore(
m_context->device(),
m_semaphore,
nullptr
);
m_semaphore = nullptr;
}
}

61
src/vk/Semaphore.h

@ -0,0 +1,61 @@
// Copyright 2022 Simon Boyé
#pragma once
#include <vk/forward.h>
#include <vulkan/vulkan.h>
namespace vk {
class Semaphore {
public:
Semaphore() noexcept;
Semaphore(Context& context);
Semaphore(const Semaphore&) = delete;
Semaphore(Semaphore&& other) noexcept;
~Semaphore() noexcept;
Semaphore& operator=(const Semaphore&) = delete;
Semaphore& operator=(Semaphore&& other) noexcept;
explicit inline operator bool() const noexcept {
return !is_null();
}
inline bool is_null() const noexcept {
return m_semaphore == VK_NULL_HANDLE;
}
inline const Context* context() const noexcept {
return m_context;
}
inline Context* context() noexcept {
return m_context;
}
inline operator VkSemaphore() noexcept {
return m_semaphore;
}
inline VkSemaphore semaphore() noexcept {
return m_semaphore;
}
friend inline void swap(Semaphore& semaphore_0, Semaphore& semaphore_1) noexcept {
using std::swap;
swap(semaphore_0.m_context, semaphore_1.m_context);
swap(semaphore_0.m_semaphore, semaphore_1.m_semaphore);
}
void destroy() noexcept;
private:
Context* m_context = nullptr;
VkSemaphore m_semaphore = VK_NULL_HANDLE;
};
}

29
src/vk/Swapchain.cpp

@ -80,7 +80,7 @@ VkImageView Swapchain::image_view(size_t image_index) {
return m_image_resources[image_index].view;
}
VkSemaphore Swapchain::ready_to_render() {
Semaphore& Swapchain::ready_to_render() {
return m_frame_resources[m_frame_resources_index].ready_to_render;
}
@ -325,22 +325,11 @@ void Swapchain::create() {
image_resources.render_done = Fence(*m_context, VK_FENCE_CREATE_SIGNALED_BIT);
}
m_frame_resources.resize(MAX_FRAMES_IN_FLIGHT, {});
int index = 0;
for(auto& frame_resources: m_frame_resources) {
VkSemaphoreCreateInfo semaphore_info {
.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO,
};
if(vkCreateSemaphore(
m_context->device(),
&semaphore_info,
nullptr,
&frame_resources.ready_to_render
) != VK_SUCCESS)
throw std::runtime_error("failed to create semaphore");
index += 1;
m_frame_resources.clear();
for(int index = 0; index < MAX_FRAMES_IN_FLIGHT; index += 1) {
m_frame_resources.emplace_back(FrameResources {
.ready_to_render = Semaphore(*m_context),
});
}
for(auto& callback: m_creation_callbacks)
@ -351,11 +340,7 @@ void Swapchain::destroy() {
for(auto& callback: m_destruction_callbacks)
callback();
for(auto& frame_resources: m_frame_resources) {
m_context->destroy_semaphore(frame_resources.ready_to_render);
// This is a reference to an ImageResources.render_done
frame_resources.render_done = nullptr;
}
m_frame_resources.clear();
for(auto& image_resources: m_image_resources) {
image_resources.render_done.destroy();

5
src/vk/Swapchain.h

@ -1,6 +1,7 @@
// Copyright 2022 Simon Boyé
#pragma once
#include <vk/Semaphore.h>
#include <vk/Context.h>
#include <core/utils.h>
@ -58,7 +59,7 @@ public:
VkImage image(size_t image_index);
VkImageView image_view();
VkImageView image_view(size_t image_index);
VkSemaphore ready_to_render();
Semaphore& ready_to_render();
Fence& render_done();
void initialize(const SwapchainSettings& settings);
@ -80,7 +81,7 @@ private:
};
struct FrameResources {
VkSemaphore ready_to_render = VK_NULL_HANDLE;
Semaphore ready_to_render;
Fence* render_done = nullptr;
};

Loading…
Cancel
Save