aboutsummaryrefslogtreecommitdiffstats
path: root/include/api-test
diff options
context:
space:
mode:
Diffstat (limited to 'include/api-test')
-rw-r--r--include/api-test/freelist.hpp115
-rw-r--r--include/api-test/handle.hpp14
-rw-r--r--include/api-test/vk-device-types.hpp59
-rw-r--r--include/api-test/vk-device.hpp16
4 files changed, 136 insertions, 68 deletions
diff --git a/include/api-test/freelist.hpp b/include/api-test/freelist.hpp
index 3cdd55d..e9df734 100644
--- a/include/api-test/freelist.hpp
+++ b/include/api-test/freelist.hpp
@@ -3,61 +3,118 @@
#include <vector>
#include <cassert>
+#include "handle.hpp"
+
static constexpr uint32_t default_element_count = 1024U;
template<typename T, const size_t initial_size = default_element_count>
class freelist {
public:
- freelist()
- : free(initial_size),
- items(initial_size) {
- std::iota(free.rbegin(), free.rend(), 0);
+
+ freelist() {
+ auto next_free = 0U;
+ elements.reserve(initial_size);
+ for (auto id { 0U }; id < initial_size; id++) {
+ elements.push_back(
+ {
+ .next_free = static_cast<uint32_t>(++next_free % initial_size),
+ }
+ );
+ }
+
+ elements.back().next_free = -1U;
}
- uint32_t add(const T& item) {
- const auto id = free.back();
- free.pop_back();
+ handle<T> add(const T& item) {
+ auto id = elements[0U].next_free;
+
+ if (id != -1U) {
+ auto& element = elements[id];
- items[id] = std::move(item);
+ elements[0U].next_free = element.next_free;
+ element.item = std::move(item);
- return id;
+ return { id, ++element.generation };
+ }
+
+ // grow
}
- void remove(uint32_t item_id) {
- free.push_back(item_id);
+ void remove(handle<T> handle) {
+ assert(handle.generation == elements[handle.id].generation);
+ elements[handle.id].next_free = elements[0U].next_free;
+ elements[0U].next_free = handle.id;
}
- T& operator[](uint32_t index) {
- assert(index >= 0);
- return items[index];
+ T& operator[](handle<T> handle) {
+ assert(handle.generation == elements[handle.id].generation);
+ return elements[handle.id].item;
}
- const T& operator[](uint32_t index) const {
- return items[index];
+ const T& operator[](handle<T> handle) const {
+ assert(handle.generation == elements[handle.id].generation);
+ return elements[handle.id].item;
}
- uint32_t find(const T& seeked_item) {
- for (auto index { 0U }; index < items.size(); index++) {
- const auto& item = items[index];
- if (memcmp(&item, &seeked_item, sizeof(T)) == 0) {
- return index;
- }
+ static constexpr uint32_t invalid_id = -1;
+
+private:
+ struct element {
+ union {
+ T item;
+ uint32_t next_free = -1;
+ };
+ uint32_t generation = 0U;
+ };
+
+ std::vector<element> elements;
+};
+
+template<const size_t initial_size = default_element_count>
+class idlist {
+ public:
+
+ idlist() {
+ auto next_free = 1U;
+ elements.reserve(initial_size);
+ for (auto id { 0U }; id < initial_size; id++) {
+ elements.push_back(
+ {
+ .next_free = static_cast<uint32_t>(++next_free % initial_size),
+ }
+ );
}
- return invalid_id;
+ elements.back().next_free = -1U;
}
- auto begin() const {
- return items.begin();
+ handle<void> add() {
+ auto id = elements[0U].next_free;
+
+ if (id != -1U) {
+ auto& element = elements[id];
+ elements[0U].next_free = element.next_free;
+ element.next_free = -1;
+
+ return { id, ++element.generation };
+ }
+
+ // grow
}
- auto end() const {
- return items.end();
+ void remove(handle<void> handle) {
+ assert(handle.generation == elements[handle.id].generation);
+ elements[handle.id].next_free = elements[0U].next_free;
+ elements[0U].next_free = handle.id;
}
static constexpr uint32_t invalid_id = -1;
private:
- std::vector<T> items;
- std::vector<uint32_t> free;
+ struct element {
+ uint32_t next_free = -1;
+ uint32_t generation = 0U;
+ };
+
+ std::vector<element> elements;
};
diff --git a/include/api-test/handle.hpp b/include/api-test/handle.hpp
index a81480a..72c46a2 100644
--- a/include/api-test/handle.hpp
+++ b/include/api-test/handle.hpp
@@ -2,9 +2,19 @@
#include <cstdint>
-template<typename T>
+// template<typename T>
+// struct handle {
+// uint32_t id = handle::invalid_id;
+//
+// [[nodiscard]] inline bool is_valid() const { return id != handle::invalid_id; }
+//
+// static constexpr uint32_t invalid_id = -1U;
+// };
+
+template<typename U>
struct handle {
- uint32_t id = handle::invalid_id;
+ uint32_t id = invalid_id;
+ uint32_t generation = 0U;
[[nodiscard]] inline bool is_valid() const { return id != handle::invalid_id; }
diff --git a/include/api-test/vk-device-types.hpp b/include/api-test/vk-device-types.hpp
index 86eb22b..3085e29 100644
--- a/include/api-test/vk-device-types.hpp
+++ b/include/api-test/vk-device-types.hpp
@@ -22,33 +22,42 @@ struct texture_desc {
};
struct device_texture {
- device_texture() = default;
- device_texture(const texture_desc& desc);
+ void init(const texture_desc& desc);
- void create_views();
+ void release();
- VkImage vk_image;
- VkImageView whole_view;
+ void create_views();
+
+ [[nodiscard]] uint32_t get_storage_index() const {
+ return storage_index.id;
+ }
+
+ [[nodiscard]] uint32_t get_sampled_index() const {
+ return sampled_index.id;
+ }
+
+ VkImage vk_image = nullptr;
+ VkImageView whole_view = nullptr;
VkImageView mips_views[texture_desc::max_mips] = { nullptr };
- VkImageLayout layout = VK_IMAGE_LAYOUT_UNDEFINED;
- VkPipelineStageFlags2 stage = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT;
- VkAccessFlags2 access = VK_ACCESS_2_NONE;
- VkFormat format;
- VkImageAspectFlags aspects;
+ VkImageLayout layout = VK_IMAGE_LAYOUT_UNDEFINED;
+ VkPipelineStageFlags2 stage = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT;
+ VkAccessFlags2 access = VK_ACCESS_2_NONE;
+ VkFormat format = VK_FORMAT_UNDEFINED;
+ VkImageAspectFlags aspects = VK_IMAGE_ASPECT_NONE_KHR;
- uint32_t width = 1U;
- uint32_t height = 1U;
- uint32_t depth = 1U;
- uint32_t mips = 1U;
+ uint32_t width = 1U;
+ uint32_t height = 1U;
+ uint32_t depth = 1U;
+ uint32_t mips = 1U;
- uint32_t storage_index = -1;
- uint32_t sampled_index = -1;
+ private:
+ handle<void> storage_index;
+ handle<void> sampled_index;
- VmaAllocation alloc;
+ VmaAllocation alloc = nullptr;
-private:
- static freelist<device_texture*> storage_indices;
- static freelist<device_texture*> sampled_indices;
+ static idlist<> storage_indices;
+ static idlist<> sampled_indices;
};
struct buffer_desc {
@@ -66,7 +75,6 @@ struct device_buffer {
size_t size;
};
-
struct pipeline_desc {
std::span<uint8_t> cs_code;
std::span<uint8_t> vs_code;
@@ -81,15 +89,14 @@ struct device_pipeline {
VkPipelineBindPoint bind_point;
};
-
struct semaphore_desc {
VkSemaphoreType type;
uint64_t initial_value = 0U;
};
struct device_semaphore {
- VkSemaphore vk_semaphore = nullptr;
- uint64_t value;
+ VkSemaphore vk_semaphore = nullptr;
+ uint64_t value;
};
@@ -102,7 +109,7 @@ struct surface_desc {
VkImageUsageFlags usages;
uint32_t image_count = surface_desc::default_image_count;
- static constexpr uint32_t max_image_count = 3U;
+ static constexpr uint32_t max_image_count = 3U;
static constexpr uint32_t default_image_count = 3U;
};
@@ -115,6 +122,6 @@ struct device_surface {
uint32_t image_index;
uint32_t image_count;
- void acquire_image_index(handle<device_semaphore> signal_handle);
+ void acquire_image_index(handle<device_semaphore> signal_handle);
handle<device_texture> get_backbuffer_image() const;
};
diff --git a/include/api-test/vk-device.hpp b/include/api-test/vk-device.hpp
index 9e42b38..ca5457a 100644
--- a/include/api-test/vk-device.hpp
+++ b/include/api-test/vk-device.hpp
@@ -7,7 +7,6 @@
#include "command-buffer.hpp"
#include "freelist.hpp"
-#include "handle.hpp"
#include "vk-bindless.hpp"
#include "vk-device-types.hpp"
@@ -40,19 +39,14 @@ class vkdevice {
handle<device_semaphore> create_semaphore(const semaphore_desc& desc);
- void destroy_texture(const device_texture& texture);
void destroy_texture(handle<device_texture> handle);
- void destroy_buffer(const device_buffer& buffer);
void destroy_buffer(handle<device_buffer> handle);
- void destroy_pipeline(const device_pipeline& pipeline);
void destroy_pipeline(handle<device_pipeline> handle);
- void destroy_semaphore(const device_semaphore& semaphore);
void destroy_semaphore(handle<device_semaphore> handle);
- void destroy_surface(const device_surface& surface);
void destroy_surface(handle<device_surface> handle);
template<typename cmd_buf_type>
@@ -61,23 +55,23 @@ class vkdevice {
}
[[nodiscard]] inline device_texture& get_texture(handle<device_texture> handle) {
- return textures[handle.id];
+ return textures[handle];
}
[[nodiscard]] inline const device_buffer& get_buffer(handle<device_buffer> handle) const {
- return buffers[handle.id];
+ return buffers[handle];
}
[[nodiscard]] inline const device_pipeline& get_pipeline(handle<device_pipeline> handle) const {
- return pipelines[handle.id];
+ return pipelines[handle];
}
[[nodiscard]] inline device_surface& get_surface(handle<device_surface> handle) {
- return surfaces[handle.id];
+ return surfaces[handle];
}
[[nodiscard]] inline device_semaphore& get_semaphore(handle<device_semaphore> handle) {
- return semaphores[handle.id];
+ return semaphores[handle];
}
[[nodiscard]] inline const bindless_model& get_bindingmodel() const {