zpp
Zephyr C++20 Framework
heap.hpp
Go to the documentation of this file.
1 //
2 // Copyright (c) 2021 Erwin Rol <erwin@erwinrol.com>
3 //
4 // SPDX-License-Identifier: Apache-2.0
5 //
6 
7 #ifndef ZPP_INCLUDE_ZPP_HEAP_HPP
8 #define ZPP_INCLUDE_ZPP_HEAP_HPP
9 
10 #include <zephyr/kernel.h>
11 #include <zephyr/sys/__assert.h>
12 
13 #include <chrono>
14 #include <array>
15 #include <cstdint>
16 
17 namespace zpp {
18 
22 template <class T_Heap>
23 class base_heap {
24 public:
25  using native_type = struct k_heap;
28 protected:
32  constexpr base_heap() noexcept { }
33 public:
41  [[nodiscard]] void*
42  allocate(size_t bytes) noexcept
43  {
44  return k_heap_alloc(native_handle(), bytes, K_FOREVER);
45  }
46 
55  [[nodiscard]] void*
56  allocate(size_t bytes, size_t align) noexcept
57  {
58  return k_heap_aligned_alloc(native_handle(), align, bytes, K_FOREVER);
59  }
60 
68  [[nodiscard]] void*
69  try_allocate(size_t bytes) noexcept
70  {
71  return k_heap_alloc(native_handle(), bytes, K_NO_WAIT);
72  }
73 
82  [[nodiscard]] void*
83  try_allocate(size_t bytes, size_t align) noexcept
84  {
85  return k_heap_aligned_alloc(native_handle(), align, bytes, K_NO_WAIT);
86  }
87 
96  template<class T_Rep, class T_Period>
97  [[nodiscard]] void*
98  try_allocate_for(size_t bytes, const std::chrono::duration<T_Rep, T_Period>& timeout) noexcept
99  {
100  return k_heap_alloc(native_handle(), bytes, to_timeout(timeout));
101  }
102 
112  template<class T_Rep, class T_Period>
113  [[nodiscard]] void*
114  try_allocate_for(size_t bytes, size_t align, const std::chrono::duration<T_Rep, T_Period>& timeout) noexcept
115  {
116  return k_heap_aligned_alloc(native_handle(), align, bytes, to_timeout(timeout));
117  }
118 
124  void deallocate(void* mem) noexcept
125  {
126  k_heap_free(native_handle(), mem);
127  }
128 
134  auto native_handle() noexcept -> native_pointer
135  {
136  return static_cast<T_Heap*>(this)->native_handle();
137  }
138 
144  auto native_handle() const noexcept -> native_const_pointer
145  {
146  return static_cast<const T_Heap*>(this)->native_handle();
147  }
148 public:
149  base_heap(const base_heap&) = delete;
150  base_heap(base_heap&&) = delete;
151  base_heap& operator=(const base_heap&) = delete;
153 };
154 
158 template <size_t T_Size>
159 class heap : public base_heap<heap<T_Size>> {
160 public:
161  using typename base_heap<heap<T_Size>>::native_type;
164 public:
168  heap() noexcept {
169  k_heap_init(&m_heap, m_mem.data(), m_mem.size());
170  }
171 
177  static constexpr size_t size() noexcept {
178  return T_Size;
179  }
180 
186  constexpr auto native_handle() noexcept -> native_pointer
187  {
188  return &m_heap;
189  }
190 
196  constexpr auto native_handle() const noexcept -> native_const_pointer
197  {
198  return &m_heap;
199  }
200 private:
201  native_type m_heap{};
202  std::array<uint8_t, T_Size> m_mem;
203 public:
204  heap(const heap&) = delete;
205  heap(heap&&) = delete;
206  heap& operator=(const heap&) = delete;
207  heap& operator=(heap&&) = delete;
208 };
209 
215 class heap_ref : public base_heap<heap_ref> {
216 public:
225  constexpr explicit heap_ref(native_pointer h) noexcept
226  : m_heap(h)
227  {
228  __ASSERT_NO_MSG(m_heap != nullptr);
229  }
230 
239  template<class T_Heap>
240  constexpr explicit heap_ref(T_Heap& h) noexcept
241  : m_heap(h.native_handle())
242  {
243  __ASSERT_NO_MSG(m_heap != nullptr);
244  }
245 
256  constexpr heap_ref& operator=(native_pointer h) noexcept
257  {
258  m_heap = h;
259  __ASSERT_NO_MSG(m_heap != nullptr);
260  return *this;
261  }
262 
273  template<class T_Heap>
274  constexpr heap_ref& operator=(T_Heap& rhs) noexcept
275  {
276  m_heap = rhs.native_handle();
277  __ASSERT_NO_MSG(m_heap != nullptr);
278  return *this;
279  }
280 
286  constexpr auto native_handle() noexcept -> native_pointer
287  {
288  return m_heap;
289  }
290 
296  constexpr auto native_handle() const noexcept -> native_const_pointer
297  {
298  return m_heap;
299  }
300 private:
301  native_pointer m_heap{nullptr};
302 public:
303  heap_ref() = delete;
304 };
305 
306 } // namespace zpp
307 
308 #endif // ZPP_INCLUDE_ZPP_HEAP_HPP
Heap memory allocater CRTP base class.
Definition: heap.hpp:23
native_type * native_pointer
Definition: heap.hpp:26
struct k_heap native_type
Definition: heap.hpp:25
void * allocate(size_t bytes) noexcept
Allocate memory from this heap wainting forever.
Definition: heap.hpp:42
base_heap(const base_heap &)=delete
auto native_handle() noexcept -> native_pointer
get the native zephyr heap handle.
Definition: heap.hpp:134
void * try_allocate(size_t bytes, size_t align) noexcept
Allocate memory from this heap without waiting.
Definition: heap.hpp:83
void * allocate(size_t bytes, size_t align) noexcept
Allocate memory from this heap waiting forever.
Definition: heap.hpp:56
void * try_allocate_for(size_t bytes, size_t align, const std::chrono::duration< T_Rep, T_Period > &timeout) noexcept
Allocate memory from this heap waiting with a timeout.
Definition: heap.hpp:114
void * try_allocate(size_t bytes) noexcept
Allocate memory from this heap without waiting.
Definition: heap.hpp:69
base_heap(base_heap &&)=delete
constexpr base_heap() noexcept
default protected constructor so only derived objects can be created
Definition: heap.hpp:32
void deallocate(void *mem) noexcept
Deallocate memory previously allocated.
Definition: heap.hpp:124
native_type const * native_const_pointer
Definition: heap.hpp:27
void * try_allocate_for(size_t bytes, const std::chrono::duration< T_Rep, T_Period > &timeout) noexcept
Allocate memory from this heap waiting with a timeout.
Definition: heap.hpp:98
base_heap & operator=(const base_heap &)=delete
base_heap & operator=(base_heap &&)=delete
auto native_handle() const noexcept -> native_const_pointer
get the native zephyr heap handle.
Definition: heap.hpp:144
heap reference class
Definition: heap.hpp:215
heap_ref()=delete
constexpr heap_ref & operator=(native_pointer h) noexcept
assign new native heap object
Definition: heap.hpp:256
constexpr heap_ref & operator=(T_Heap &rhs) noexcept
assign new heap object
Definition: heap.hpp:274
constexpr auto native_handle() noexcept -> native_pointer
get the native zephyr heap handle.
Definition: heap.hpp:286
constexpr heap_ref(native_pointer h) noexcept
reference native heap object
Definition: heap.hpp:225
constexpr auto native_handle() const noexcept -> native_const_pointer
get the native zephyr heap handle.
Definition: heap.hpp:296
constexpr heap_ref(T_Heap &h) noexcept
reference heap object
Definition: heap.hpp:240
heap class
Definition: heap.hpp:159
static constexpr size_t size() noexcept
Return the total size of this heap.
Definition: heap.hpp:177
heap & operator=(heap &&)=delete
heap & operator=(const heap &)=delete
constexpr auto native_handle() noexcept -> native_pointer
get the native zephyr heap handle.
Definition: heap.hpp:186
heap() noexcept
The default constructor.
Definition: heap.hpp:168
constexpr auto native_handle() const noexcept -> native_const_pointer
get the native zephyr heap handle.
Definition: heap.hpp:196
heap(const heap &)=delete
heap(heap &&)=delete
constexpr k_timeout_t to_timeout(const std::chrono::duration< T_Rep, T_Period > &d) noexcept
convert a duration to tick
Definition: clock.hpp:88