25#ifndef JOIN_CORE_MEMORY_HPP
26#define JOIN_CORE_MEMORY_HPP
33#include <system_error>
52 template <
typename Backend,
size_t Count,
size_t... Sizes>
56 template <
typename Backend,
template <
typename,
typename>
class SyncPolicy>
59 template <
typename,
typename>
62 template <
typename,
typename>
65 template <
typename,
typename>
76 inline int mbind (
void* ptr,
size_t size,
int numa)
noexcept
78 if (ptr ==
nullptr || numa < 0 || numa > (
static_cast<int> (
sizeof (
unsigned long) * 8) - 1))
84 unsigned long mask = (1UL << numa);
85 if (::mbind (ptr, size, MPOL_BIND, &mask,
sizeof (mask) * 8, MPOL_MF_STRICT) == -1)
87 lastError = std::error_code (errno, std::generic_category ());
101 inline int mlock (
void* ptr,
size_t size)
noexcept
111 lastError = std::error_code (errno, std::generic_category ());
124 template <
size_t Count,
size_t... Sizes>
143 long sc = sysconf (_SC_PAGESIZE);
144 uint64_t pageSize = (sc > 0) ?
static_cast<uint64_t
> (sc) : _defaultPageSize;
145 _size = (size + pageSize - 1) & ~(pageSize - 1);
168 : _size (other._size)
172 other._ptr =
nullptr;
188 other._ptr =
nullptr;
207 return _ptr !=
nullptr;
217 const void*
get (uint64_t offset = 0)
const
221 throw std::runtime_error (
"memory not mapped");
226 throw std::out_of_range (
"offset out of bounds");
229 return static_cast<const char*
> (_ptr) + offset;
239 void*
get (uint64_t offset = 0)
243 throw std::runtime_error (
"memory not mapped");
248 throw std::out_of_range (
"offset out of bounds");
251 return static_cast<char*
> (_ptr) + offset;
260 int mbind (
int numa)
const noexcept
262 return join::mbind (_ptr, _size, numa);
282 _ptr = ::mmap (
nullptr, _size, PROT_READ | PROT_WRITE,
283 MAP_PRIVATE | MAP_ANONYMOUS | MAP_POPULATE | MAP_HUGETLB, -1, 0);
284 if ((_ptr == MAP_FAILED) && ((errno == ENOMEM) || (errno == EINVAL)))
288 ::mmap (
nullptr, _size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS | MAP_POPULATE, -1, 0);
291 if (_ptr == MAP_FAILED)
293 throw std::system_error (errno, std::generic_category (),
"mmap failed");
300 void cleanup () noexcept
302 if ((_ptr !=
nullptr) && (_ptr != MAP_FAILED))
304 ::munlock (_ptr, _size);
305 ::munmap (_ptr, _size);
313 static constexpr uint64_t _defaultPageSize = 4096;
319 void* _ptr =
nullptr;
328 template <
size_t Count,
size_t... Sizes>
341 explicit ShmMem (uint64_t size,
const std::string& name)
344 long sc = sysconf (_SC_PAGESIZE);
345 uint64_t pageSize = (sc > 0) ?
static_cast<uint64_t
> (sc) : _defaultPageSize;
346 _size = (size + pageSize - 1) & ~(pageSize - 1);
348 if (_size >
static_cast<uint64_t
> (std::numeric_limits<off_t>::max ()))
350 throw std::overflow_error (
"size will overflow");
374 : _size (other._size)
375 , _name (std::move (other._name))
380 other._ptr =
nullptr;
394 _name = std::move (other._name);
399 other._ptr =
nullptr;
419 return _ptr !=
nullptr;
429 const void*
get (uint64_t offset = 0)
const
433 throw std::runtime_error (
"memory not mapped");
438 throw std::out_of_range (
"offset out of bounds");
441 return static_cast<const char*
> (_ptr) + offset;
451 void*
get (uint64_t offset = 0)
455 throw std::runtime_error (
"memory not mapped");
460 throw std::out_of_range (
"offset out of bounds");
463 return static_cast<char*
> (_ptr) + offset;
472 int mbind (
int numa)
const noexcept
474 return join::mbind (_ptr, _size, numa);
492 static int unlink (
const std::string& name)
noexcept
494 if (::shm_unlink (name.c_str ()) == -1)
500 lastError = std::error_code (errno, std::generic_category ());
516 _fd = ::shm_open (_name.c_str (), O_CREAT | O_RDWR | O_EXCL | O_CLOEXEC, 0644);
517 if ((_fd == -1) && (errno == EEXIST))
520 _fd = ::shm_open (_name.c_str (), O_RDWR | O_CLOEXEC, 0644);
525 throw std::system_error (errno, std::generic_category (),
"shm_open failed");
532 if (fstat (_fd, &st) == -1)
536 throw std::system_error (err, std::generic_category (),
"fstat failed");
539 if (
static_cast<uint64_t
> (st.st_size) != _size)
542 throw std::runtime_error (
"shared memory size mismatch");
547 if (::ftruncate (_fd, _size) == -1)
551 throw std::system_error (err, std::generic_category (),
"ftruncate failed");
555 _ptr = ::mmap (
nullptr, _size, PROT_READ | PROT_WRITE, MAP_SHARED | MAP_HUGETLB, _fd, 0);
556 if ((_ptr == MAP_FAILED) && ((errno == ENOMEM) || (errno == EINVAL)))
559 _ptr = ::mmap (
nullptr, _size, PROT_READ | PROT_WRITE, MAP_SHARED, _fd, 0);
562 if (_ptr == MAP_FAILED)
566 throw std::system_error (err, std::generic_category (),
"mmap failed");
573 void cleanup () noexcept
575 if ((_ptr !=
nullptr) && (_ptr != MAP_FAILED))
577 ::munlock (_ptr, _size);
578 ::munmap (_ptr, _size);
593 static constexpr uint64_t _defaultPageSize = 4096;
602 void* _ptr =
nullptr;
memory arena owning backend and managing one or more pools.
Definition memory.hpp:53
local anonymous memory provider.
Definition memory.hpp:122
int mlock() const noexcept
lock memory in RAM.
Definition memory.hpp:270
const void * get(uint64_t offset=0) const
get a const pointer to the memory at a given offset.
Definition memory.hpp:217
LocalMem & operator=(const LocalMem &other)=delete
copy assignment operator.
void * get(uint64_t offset=0)
get a pointer to the memory at a given offset.
Definition memory.hpp:239
LocalMem(const LocalMem &other)=delete
copy constructor.
LocalMem() noexcept=default
default constructor.
LocalMem(LocalMem &&other) noexcept
move constructor.
Definition memory.hpp:167
bool mapped() const noexcept
check if the memory is mapped.
Definition memory.hpp:205
~LocalMem() noexcept
releases the mapped memory.
Definition memory.hpp:196
posix shared memory provider.
Definition memory.hpp:326
bool mapped() const noexcept
check if the shared memory is mapped.
Definition memory.hpp:417
void * get(uint64_t offset=0)
get a pointer to the shared memory at a given offset.
Definition memory.hpp:451
ShmMem(const ShmMem &other)=delete
copy constructor.
ShmMem & operator=(const ShmMem &other)=delete
copy assignment operator.
static int unlink(const std::string &name) noexcept
destroy synchronization primitives and unlink the shared memory segment.
Definition memory.hpp:492
int mlock() const noexcept
lock memory in RAM.
Definition memory.hpp:482
ShmMem(ShmMem &&other) noexcept
move constructor.
Definition memory.hpp:373
~ShmMem() noexcept
unmaps the memory and closes the file descriptor.
Definition memory.hpp:408
ShmMem(uint64_t size, const std::string &name)
creates or opens a named shared memory segment.
Definition memory.hpp:341
const void * get(uint64_t offset=0) const
get a const pointer to the shared memory at a given offset.
Definition memory.hpp:429
Definition acceptor.hpp:32
int mlock(void *ptr, size_t size) noexcept
lock memory in RAM.
Definition memory.hpp:101
std::error_code make_error_code(join::Errc code) noexcept
Create an std::error_code object.
Definition error.cpp:195
const std::string _name
Definition shared_futex_test.cpp:45
multiple producer multiple consumer ring buffer.
Definition queue.hpp:857
multiple producer single consumer ring buffer.
Definition queue.hpp:664
single producer single consumer ring buffer.
Definition queue.hpp:483
queue forward declarations.
Definition queue.hpp:1051
#define JOIN_UNLIKELY(x)
Definition utils.hpp:46