Gaia-ECS v1.0.0
A simple and powerful entity component system
Loading...
Searching...
No Matches
ser_buffer_binary.h
1#pragma once
2#include "gaia/config/config.h"
3
4#include <type_traits>
5
6#include "gaia/cnt/darray.h"
7#include "gaia/cnt/darray_ext.h"
8
9namespace gaia {
10 namespace ser {
11 enum class serialization_type_id : uint8_t;
12
13 namespace detail {
15 static constexpr uint32_t SerializationBufferCapacityIncreaseSize = 128U;
16
17 template <typename DataContainer>
19 class ser_buffer_binary_impl {
20 protected:
21 // Increase the capacity by multiples of CapacityIncreaseSize
22 static constexpr uint32_t CapacityIncreaseSize = SerializationBufferCapacityIncreaseSize;
23
25 DataContainer m_data;
27 uint32_t m_dataPos = 0;
28
29 public:
30 void reset() {
31 m_dataPos = 0;
32 m_data.clear();
33 }
34
36 GAIA_NODISCARD uint32_t bytes() const {
37 return (uint32_t)m_data.size();
38 }
39
41 GAIA_NODISCARD bool empty() const {
42 return m_data.empty();
43 }
44
46 GAIA_NODISCARD const auto* data() const {
47 return m_data.data();
48 }
49
52 void reserve(uint32_t size) {
53 const auto nextSize = m_dataPos + size;
54 if (nextSize <= bytes())
55 return;
56
57 // Make sure there is enough capacity to hold our data
58 const auto newSize = bytes() + size;
59 const auto newCapacity = ((newSize / CapacityIncreaseSize) * CapacityIncreaseSize) + CapacityIncreaseSize;
60 m_data.reserve(newCapacity);
61 }
62
65 void resize(uint32_t size) {
66 m_data.resize(size);
67 }
68
71 void seek(uint32_t pos) {
72 m_dataPos = pos;
73 }
74
77 void skip(uint32_t size) {
78 m_dataPos += size;
79 }
80
82 GAIA_NODISCARD uint32_t tell() const {
83 return m_dataPos;
84 }
85
88 template <typename T>
89 void save(T&& value) {
90 reserve((uint32_t)sizeof(T));
91
92 const auto cnt = m_dataPos + (uint32_t)sizeof(T);
93 if (cnt > m_data.size())
94 m_data.resize(cnt);
95 mem::unaligned_ref<T> mem((void*)&m_data[m_dataPos]);
96 mem = GAIA_FWD(value);
97
98 m_dataPos += (uint32_t)sizeof(T);
99 }
100
105 void save_raw(const void* pSrc, uint32_t size, [[maybe_unused]] ser::serialization_type_id id) {
106 if (size == 0)
107 return;
108
109 reserve(size);
110
111 // Copy "size" bytes of raw data starting at pSrc
112 const auto cnt = m_dataPos + size;
113 if (cnt > m_data.size())
114 m_data.resize(cnt);
115 memcpy((void*)&m_data[m_dataPos], pSrc, size);
116
117 m_dataPos += size;
118 }
119
122 template <typename T>
123 void load(T& value) {
124 GAIA_ASSERT(m_dataPos + (uint32_t)sizeof(T) <= bytes());
125
126 const auto& cdata = std::as_const(m_data);
127 value = mem::unaligned_ref<T>((void*)&cdata[m_dataPos]);
128
129 m_dataPos += (uint32_t)sizeof(T);
130 }
131
136 void load_raw(void* pDst, uint32_t size, [[maybe_unused]] ser::serialization_type_id id) {
137 if (size == 0)
138 return;
139
140 GAIA_ASSERT(m_dataPos + size <= bytes());
141
142 const auto& cdata = std::as_const(m_data);
143 memmove(pDst, (const void*)&cdata[m_dataPos], size);
144
145 m_dataPos += size;
146 }
147 };
149 } // namespace detail
150
154 using ser_buffer_binary_storage_dyn = gaia::cnt::darray<uint8_t>;
155
159 class ser_buffer_binary: public detail::ser_buffer_binary_impl<ser_buffer_binary_storage> {};
161 class ser_buffer_binary_dyn: public detail::ser_buffer_binary_impl<ser_buffer_binary_storage_dyn> {};
162 } // namespace ser
163} // namespace gaia
Array with variable size of elements of type.
Definition darray_impl.h:27
Same API as ser_buffer_binary, but backed by fully dynamic storage.
Definition ser_buffer_binary.h:161
Minimal in-memory binary serializer. It stores raw bytes only (no schema, versioning,...
Definition ser_buffer_binary.h:159
GAIA_NODISCARD uint32_t bytes(const T &data)
Calculates how many bytes data would need when serialized via ser::save. Useful when a destination st...
Definition ser_ct.h:88
void load(Reader &reader, T &data)
Read data using Reader at compile-time.
Definition ser_ct.h:112
void save(Writer &writer, const T &data)
Write data using Writer at compile-time.
Definition ser_ct.h:101