Valkka  1.6.1
OpenSource Video Management
sharedmem.h
Go to the documentation of this file.
1 #ifndef sharedmem_HEADER_GUARD
2 #define sharedmem_HEADER_GUARD
3 /*
4  * sharedmem.h : Posix shared memory segment server/client management, shared memory ring buffer synchronized using posix semaphores.
5  *
6  * (c) Copyright 2017-2024 Sampsa Riikonen
7  *
8  * Authors: Sampsa Riikonen <sampsa.riikonen@iki.fi>
9  *
10  * This file is part of the Valkka library.
11  *
12  * Valkka is free software: you can redistribute it and/or modify
13  * it under the terms of the GNU Lesser General Public License as
14  * published by the Free Software Foundation, either version 3 of the
15  * License, or (at your option) any later version.
16  *
17  * This program is distributed in the hope that it will be useful,
18  * but WITHOUT ANY WARRANTY; without even the implied warranty of
19  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20  * GNU Lesser General Public License for more details.
21  *
22  * You should have received a copy of the GNU Lesser General Public License
23  * along with this program. If not, see <https://www.gnu.org/licenses/>
24  *
25  */
26 
37 #include "common.h"
38 #include <sys/shm.h>
39 #include <sys/mman.h>
40 #include <sys/stat.h> /* For mode constants */
41 #include <fcntl.h> /* For O_* constants */
42 #include <semaphore.h> // semaphores
43 #include "framefilter.h"
44 #include "Python.h"
45 
46 
47 // #define USE_SHMEM_CACHE 1 // Don't expose shmem segments directly as numpy arrays, but an intermediate copy instead
48 // #define SAFE_TEXT
49 
50 #ifdef SAFE_TEST
51 static std::mutex test_mutex;
52 #endif
53 
56 class EventFd { // <pyapi>
57 
58 public: // <pyapi>
59  EventFd(); // <pyapi>
60  ~EventFd(); // <pyapi>
61 
62 private:
63  int fd;
64 
65 public: // <pyapi>
66  int getFd(); // <pyapi>
67  void set(); // <pyapi>
68  void clear(); // <pyapi>
69 }; // <pyapi>
70 
71 
84 // https://stackoverflow.com/questions/115703/storing-c-template-function-definitions-in-a-cpp-file
86 
87 public:
95  SharedMemSegment(const char* name, std::size_t n_bytes, bool is_server=false);
97  virtual ~SharedMemSegment();
98 
99 protected:
100  virtual void serverInit() = 0;
101  virtual bool clientInit() = 0;
102  virtual void serverClose() = 0;
103  virtual void clientClose() = 0;
104 
105 public:
106  virtual std::size_t getSize() = 0;
107 
108  virtual void put(std::vector<uint8_t> &inp_payload, void *meta_) = 0;
109  virtual void put(uint8_t* buf_, void* meta_) = 0;
110 
111  virtual void copyMetaFrom(void *meta_) = 0;
112  virtual void copyMetaTo(void *meta_) = 0;
113 
114 protected:
115  std::string name;
116  std::string payload_name;
117  std::string meta_name;
118  bool is_server;
119  void *ptr,*ptr_;
121 
122 public:
123  uint8_t *payload;
124  // void *meta; ///< Metadata (define in child classes);
125  std::size_t n_bytes;
126 
127 public: // client
128  void init();
129  void close_();
130  bool getClientState();
131 };
132 
133 
139 
140 public:
141  SimpleSharedMemSegment(const char* name, std::size_t n_bytes, bool is_server=false);
142  virtual ~SimpleSharedMemSegment();
143 
144 protected:
145  virtual void serverInit();
146  virtual bool clientInit();
147  virtual void serverClose();
148  virtual void clientClose();
149 
150 public:
151  virtual std::size_t getSize();
152 
153  /* virtual method, since metadata depends on the shared mem segment type */
154  virtual void put(std::vector<uint8_t> &inp_payload, void* meta_);
155  virtual void put(uint8_t* buf_, void* meta_);
156  virtual void putAVRGBFrame(AVRGBFrame *f);
157 
158  virtual void copyMetaFrom(void *meta_);
159  virtual void copyMetaTo(void *meta_);
160 
161 public:
162  std::size_t *meta;
163 
164 public:
165  void put(std::vector<uint8_t> &inp_payload);
166 
167 };
168 
169 
174 struct RGB24Meta { // <pyapi>
175  std::size_t size;
176  int width; // <pyapi>
177  int height; // <pyapi>
178  SlotNumber slot; // <pyapi>
179  long int mstimestamp; // <pyapi>
180 }; // <pyapi>
181 
182 
189 
190 public:
191  RGB24SharedMemSegment(const char* name, int width, int height, bool is_server=false);
192  virtual ~RGB24SharedMemSegment();
193 
194 protected:
195  virtual void serverInit();
196  virtual bool clientInit();
197  virtual void serverClose();
198  virtual void clientClose();
199 
200 public:
201  virtual std::size_t getSize();
202 
203  virtual void put(std::vector<uint8_t> &inp_payload, void* meta_);
204  virtual void put(uint8_t* buf_, void* meta_);
205  virtual void putAVRGBFrame(AVRGBFrame *f);
206 
207  virtual void copyMetaFrom(void *meta_);
208  virtual void copyMetaTo(void *meta_);
209 
210 public:
211  RGB24Meta *meta;
212 
213 };
214 
215 
226 class SharedMemRingBufferBase { // <pyapi>
227 
228 public: // <pyapi>
240  SharedMemRingBufferBase(const char* name, int n_cells, std::size_t n_bytes, int mstimeout=0, bool is_server=false); // <pyapi>
242  virtual ~SharedMemRingBufferBase(); // <pyapi>
243 
244 protected: // at constructor init list
245  std::string name;
246  int n_cells, n_bytes;
247  int mstimeout;
248  bool is_server;
249 
250 protected: // posix semaphores and mmap'd files
251  sem_t *sema, *flagsema;
252  std::string sema_name;
253  std::string flagsema_name;
254  int index;
255  struct timespec ts;
256  int fd;
257 
258 public:
259  std::vector<SharedMemSegment*> shmems;
260  uint8_t** cache;
261 
262 protected: // internal methods - not for the api user
263  void setFlag();
264  bool flagIsSet();
265  void clearFlag();
266  int getFlagValue();
267  void zero();
268  void setEventFd();
269  void clearEventFd();
270 
271 
272 public:
273  int getValue();
274  bool getClientState();
275 
276 public: // server side routines - call these only from the server // <pyapi>
283  void serverPush(std::vector<uint8_t> &inp_payload, void* meta);
285  void serverUseFd(EventFd &event_fd); // <pyapi>
286 
287 
288 public: // client side routines - call only from the client side // <pyapi>
298  bool clientPull(int &index_out, void* meta); // <pyapi>
300  bool clientPullThread(int &index_out, void* meta); // <pyapi>
301  PyObject *getBufferListPy(); // <pyapi>
303  void clientUseFd(EventFd &event_fd); // <pyapi>
304 }; // <pyapi>
305 
306 
307 
308 class SharedMemRingBuffer : public SharedMemRingBufferBase { // <pyapi>
309 
310 public: // <pyapi>
311  SharedMemRingBuffer(const char* name, int n_cells, std::size_t n_bytes, int mstimeout=0, bool is_server=false); // <pyapi>
313  virtual ~SharedMemRingBuffer(); // <pyapi>
314 
315 public: // <pyapi>
316  void serverPush(std::vector<uint8_t> &inp_payload); // <pyapi>
318  bool serverPushPy(PyObject *po); // <pyapi>
319  bool clientPull(int &index_out, int &size_out); // <pyapi>
320 }; // <pyapi>
321 
322 
323 
329 
330 public: // <pyapi>
332  SharedMemRingBufferRGB(const char* name, int n_cells, int width, int height, int mstimeout=0, bool is_server=false); // <pyapi>
334  virtual ~SharedMemRingBufferRGB(); // <pyapi>
335 
336 protected:
337  int width, height;
338 
339 public:
340  void serverPushAVRGBFrame(AVRGBFrame *f);
341 
342 public: // <pyapi>
346  PyObject* clientPullPy(); // <pyapi>
347 
349  bool clientPull(int &index_out, int &size_out); // <pyapi>
350 
352  bool clientPullFrame(int &index_out, RGB24Meta &meta); // <pyapi>
354  bool clientPullFrameThread(int &index_out, RGB24Meta &meta); // <pyapi>
355  // ..not sure about passing RGB24Meta from python
356  // by reference. Not sure if swig handles the refcounting
357  // correctly.
358 
359  bool serverPushPyRGB(PyObject *po, SlotNumber slot, long int mstimestamp); // <pyapi>
360 
361  // in these versions, modify the python object in-place: TODO
362  //bool clientPullFramePy(int &index_out, PyObject *po) // <pyapi>
363  //bool clientPullFrameThreadPy(int &index_out, PyObject *po) // <pyapi>
364 }; // <pyapi>
365 
366 
367 
373 class ShmemFrameFilter : public FrameFilter { // <pyapi>
374 
375 public: // <pyapi>
386  ShmemFrameFilter(const char* name, int n_cells, std::size_t n_bytes, int mstimeout=0); // <pyapi>
387  //~ShmemFrameFilter(); // <pyapi>
388 
389 protected: // initialized at constructor
390  //int n_cells;
391  //std::size_t n_bytes;
392  //int mstimeout;
393  SharedMemRingBuffer shmembuf;
394 
395 protected:
396  virtual void go(Frame* frame);
397 
398 public: // <pyapi>
399  void useFd(EventFd &event_fd); // <pyapi>
400 }; // <pyapi>
401 
402 
408 class RGBShmemFrameFilter : public FrameFilter { // <pyapi>
409 
410 public: // <pyapi>
413  RGBShmemFrameFilter(const char* name, int n_cells, int width, int height, int mstimeout=0); // <pyapi>
414  //~RGBShmemFrameFilter(); // <pyapi>
415 
416 protected: // initialized at constructor
417  //int n_cells;
418  //int width;
419  //int height;
420  //int mstimeout;
421  SharedMemRingBufferRGB shmembuf;
422 
423 protected:
424  virtual void go(Frame* frame);
425 
426 public: // <pyapi>
427  void useFd(EventFd &event_fd); // <pyapi>
428 }; // <pyapi>
429 
430 
431 // macros
432 
433 #define server_init(CLASSNAME, TYPENAME)\
434 void CLASSNAME::serverInit() {\
435  int fd, fd_, r, r_;\
436  shm_unlink(payload_name.c_str());\
437  shm_unlink(meta_name.c_str());\
438  fd = shm_open(payload_name.c_str(),O_CREAT | O_EXCL | O_TRUNC | O_RDWR, 0600);\
439  fd_= shm_open(meta_name.c_str(), O_CREAT | O_EXCL | O_TRUNC | O_RDWR, 0600);\
440  if (fd == -1 or fd_==-1) {\
441  perror("valkka_core: sharedmem.cpp: SharedMemSegment::serverInit: shm_open failed");\
442  exit(2);\
443  }\
444  /* std::cout << "got shmem" << std::endl; */\
445  r = ftruncate(fd, n_bytes);\
446  /* r_= ftruncate(fd_,n_bytes); // BUG!*/\
447  r_= ftruncate(fd_, sizeof(TYPENAME));\
448  if (r != 0 or r_ !=0) {\
449  perror("valkka_core: sharedmem.cpp: SharedMemSegment::serverInit: ftruncate failed");\
450  exit(2);\
451  }\
452  ptr = mmap(0, n_bytes, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);\
453  ptr_= mmap(0, sizeof(TYPENAME), PROT_READ | PROT_WRITE, MAP_SHARED, fd_, 0);\
454  if (ptr == MAP_FAILED or ptr_ == MAP_FAILED) {\
455  perror("valkka_core: sharedmem.cpp: SharedMemSegment::serverInit: mmap failed");\
456  exit(2);\
457  }\
458  payload = (uint8_t*) ptr;\
459  meta = (TYPENAME*) ptr_;\
460  /*std::cout << "server meta reserved" << std::endl;*/\
461  close(fd);\
462  close(fd_);\
463  /*std::cout << "Server reserved " << sizeof(TYPENAME) << "bytes" << std::endl;*/\
464 };\
465 
466 
467 #define client_init(CLASSNAME, TYPENAME) \
468 bool CLASSNAME::clientInit() { \
469  int fd, fd_;\
470  fd = shm_open(payload_name.c_str(), O_RDONLY, 0400);\
471  fd_= shm_open(meta_name.c_str(), O_RDONLY, 0400);\
472  if (fd == -1 or fd_==-1) {\
473  /* perror("valkka_core: sharedmem.cpp: SharedMemSegment::clientInit: shm_open failed"); */\
474  /* exit(2); */\
475  return false;\
476  }\
477  /* std::cout << "got shmem" << std::endl; */\
478  ptr =mmap(0, n_bytes, PROT_READ, MAP_SHARED, fd, 0);\
479  ptr_ =mmap(0, sizeof(TYPENAME), PROT_READ, MAP_SHARED, fd_, 0);\
480  if (ptr == MAP_FAILED or ptr_ == MAP_FAILED) {\
481  std::cout << "valkka_core: sharedmem.cpp: SharedMemSegment::clientInit: mmap failed" << std::endl;\
482  /* perror("valkka_core: sharedmem.cpp: SharedMemSegment::clientInit: mmap failed"); */\
483  /* exit(2);*/\
484  return false;\
485  }\
486  payload = (uint8_t*) ptr;\
487  meta = (TYPENAME*) ptr_;\
488  /*std::cout << "client meta reserved" << std::endl;*/\
489  close(fd);\
490  close(fd_);\
491  /*std::cout << "Client reserved " << sizeof(TYPENAME) << "bytes" << std::endl;*/\
492  return true;\
493 };\
494 
495 
496 #define server_close(CLASSNAME, TYPENAME) \
497 void CLASSNAME::serverClose() { \
498  if (munmap(ptr, n_bytes)!=0 or munmap(ptr_, sizeof(TYPENAME)!=0)) { \
499  perror("valkka_core: sharedmem.cpp: CLASSNAME::serverClose: munmap failed"); \
500  exit(2); \
501  } \
502  if (shm_unlink(payload_name.c_str())!=0 or shm_unlink(meta_name.c_str())!=0) { \
503  perror("valkka_core: sharedmem.cpp: CLASSNAME::serverClose: shm_unlink failed"); \
504  /*exit(2);*/ \
505  } \
506 } \
507 
508 #define client_close(CLASSNAME, TYPENAME) \
509 void CLASSNAME::clientClose() { \
510 if (munmap(ptr, n_bytes)!=0 or munmap(ptr_, sizeof(TYPENAME)!=0)) { \
511  perror("valkka_core: sharedmem.cpp: CLASSNAME::clientClose: munmap failed"); \
512  exit(2); \
513  } \
514 } \
515 
516 
517 #define copy_meta_from(CLASSNAME, TYPENAME) \
518 void CLASSNAME::copyMetaFrom(void *meta_) { \
519  *meta = *((TYPENAME*)(meta_)); \
520 }\
521 
522 #define copy_meta_to(CLASSNAME, TYPENAME) \
523 void CLASSNAME::copyMetaTo(void *meta_) { \
524  *((TYPENAME*)(meta_)) = *meta; \
525 }\
526 
527 #endif
Decoded YUV frame in a non-planar format (thus "NP")
Definition: frame.h:437
A file descriptor for running select and poll with shmem ring buffers.
Definition: sharedmem.h:56
The mother class of all frame filters! FrameFilters are used to create "filter chains".
Definition: framefilter.h:44
Frame: An abstract queueable class.
Definition: frame.h:112
A Shmem segment describing an RGB24 frame.
Definition: sharedmem.h:188
virtual void serverInit()
Uses shmem_open with write rights. used by the constructor if is_server=true. Init with correct metad...
virtual void serverClose()
Erases the shmem segment. used by the constructor if is_server=true.
virtual bool clientInit()
Uses shmem_open with read-only rights. Init with correct metadata serialization.
virtual void copyMetaTo(void *meta_)
Dereference metadata pointer correctly and copy the contents from this memory segment's metadata.
virtual void putAVRGBFrame(AVRGBFrame *f)
Copy from AVFrame->data directly. Only metadata used: payload size.
Definition: sharedmem.cpp:220
virtual void put(std::vector< uint8_t > &inp_payload, void *meta_)
typecast void to std::size_t
Definition: sharedmem.cpp:200
virtual std::size_t getSize()
Client: return metadata = the size of the payload (not the maximum size). Uses SharedMemSegment::getM...
Definition: sharedmem.cpp:238
virtual void copyMetaFrom(void *meta_)
Dereference metadata pointer correctly and copy the contents into this memory segment's metadata.
Like ShmemFrameFilter.
Definition: sharedmem.h:408
virtual void go(Frame *frame)
Does the actual filtering/modification to the Frame. Define in subclass.
Definition: sharedmem.cpp:908
RGBShmemFrameFilter(const char *name, int n_cells, int width, int height, int mstimeout=0)
Default constructor.
Definition: sharedmem.cpp:899
Interprocess shared memory ring buffer synchronized with posix semaphores.
Definition: sharedmem.h:226
void clearEventFd()
Clear event file descriptor.
Definition: sharedmem.cpp:365
bool getClientState()
Are the shmem segments available for client?
Definition: sharedmem.cpp:438
sem_t * flagsema
Posix semaphore objects (semaphore counter, semaphore for the overflow flag)
Definition: sharedmem.h:251
int n_bytes
Parameters defining the shmem ring buffer (number, size)
Definition: sharedmem.h:246
uint8_t ** cache
One can expose a cache instead as numpy arrays - but this requires an additional copy step - enable w...
Definition: sharedmem.h:260
struct timespec ts
Timespec for semaphore timeouts.
Definition: sharedmem.h:255
bool clientPullThread(int &index_out, void *meta)
multithreading version: releases GIL
Definition: sharedmem.cpp:607
void clearFlag()
Client: call this after handling the ring-buffer overflow.
Definition: sharedmem.cpp:401
void setFlag()
Server: call this to indicate a ring-buffer overflow.
Definition: sharedmem.cpp:380
void zero()
Force reset. Semaphore value is set to 0.
Definition: sharedmem.cpp:420
int getFlagValue()
Used by SharedMemoryRingBuffer::flagIsSet()
Definition: sharedmem.cpp:412
virtual ~SharedMemRingBufferBase()
Default destructor.
Definition: sharedmem.cpp:289
int mstimeout
Semaphore timeout in milliseconds.
Definition: sharedmem.h:247
SharedMemRingBufferBase(const char *name, int n_cells, std::size_t n_bytes, int mstimeout=0, bool is_server=false)
Default constructor.
Definition: sharedmem.cpp:245
std::string flagsema_name
Name to identify the posix semaphore used for the overflow flag.
Definition: sharedmem.h:253
bool clientPull(int &index_out, void *meta)
Returns the index of SharedMemoryRingBuffer::shmems that was just written.
Definition: sharedmem.cpp:511
void setEventFd()
Set event file descriptor.
Definition: sharedmem.cpp:346
int fd
A file descriptor for poll and select.
Definition: sharedmem.h:256
std::vector< SharedMemSegment * > shmems
Shared memory segments - can be exposed as numpy arrays.
Definition: sharedmem.h:259
bool is_server
Are we on the server side or not?
Definition: sharedmem.h:248
void serverPush(std::vector< uint8_t > &inp_payload, void *meta)
Copies payload to ring buffer.
Definition: sharedmem.cpp:451
int getValue()
Returns the current index (next to be read) of the shmem buffer.
Definition: sharedmem.cpp:430
bool flagIsSet()
Client: call this to see if there has been a ring-buffer overflow.
Definition: sharedmem.cpp:391
std::string sema_name
Name to identify the posix semaphore counter.
Definition: sharedmem.h:252
void clientUseFd(EventFd &event_fd)
Activate the file descriptor api for usage with select and poll.
Definition: sharedmem.cpp:342
int index
The index of cell that has just been written. Remember: server and client see their own copies of thi...
Definition: sharedmem.h:254
void serverUseFd(EventFd &event_fd)
Activate the file descriptor api for usage with select and poll.
Definition: sharedmem.cpp:314
SharedMemRingBuffer for AVRGBFrame.
Definition: sharedmem.h:328
SharedMemRingBufferRGB(const char *name, int n_cells, int width, int height, int mstimeout=0, bool is_server=false)
Default ctor.
Definition: sharedmem.cpp:700
virtual ~SharedMemRingBufferRGB()
Default destructor.
Definition: sharedmem.cpp:719
bool clientPull(int &index_out, int &size_out)
Legacy support.
Definition: sharedmem.cpp:818
bool clientPullFrameThread(int &index_out, RGB24Meta &meta)
For multithreading (instead of multiprocessing) applications: releases python GIL.
Definition: sharedmem.cpp:836
PyObject * clientPullPy()
Returns a python tuple of metadata (index, width, height, slot, timestamp)
Definition: sharedmem.cpp:841
bool clientPullFrame(int &index_out, RGB24Meta &meta)
Pulls payload and extended metadata.
Definition: sharedmem.cpp:827
Definition: sharedmem.h:308
bool serverPushPy(PyObject *po)
Push a numpy array.
Definition: sharedmem.cpp:649
virtual ~SharedMemRingBuffer()
Default destructor.
Definition: sharedmem.cpp:635
Handles a shared memory segment with metadata (the segment size)
Definition: sharedmem.h:85
virtual void copyMetaTo(void *meta_)=0
Dereference metadata pointer correctly and copy the contents from this memory segment's metadata.
virtual void serverClose()=0
Erases the shmem segment. used by the constructor if is_server=true.
uint8_t * payload
Pointer to payload.
Definition: sharedmem.h:123
virtual void copyMetaFrom(void *meta_)=0
Dereference metadata pointer correctly and copy the contents into this memory segment's metadata.
std::string payload_name
Name to identify the posix memory mapped file.
Definition: sharedmem.h:116
bool client_state
Was the shmem acquisition succesfull?
Definition: sharedmem.h:120
virtual bool clientInit()=0
Client: Uses shmem_open with read-only rights. Init with correct metadata serialization.
virtual void put(std::vector< uint8_t > &inp_payload, void *meta_)=0
Server: copy byte chunk into payload accompanied with metadata. Corrent typecast in child class metho...
virtual std::size_t getSize()=0
Client: return size of payload.
virtual void serverInit()=0
Server: Uses shmem_open with write rights. used by the constructor if is_server=true....
std::string meta_name
Name to identify the posix memory mapped file for the metadata.
Definition: sharedmem.h:117
std::string name
Name to identify the posix objects.
Definition: sharedmem.h:115
bool getClientState()
Was the shmem acquisition succesfull?
Definition: sharedmem.cpp:115
virtual ~SharedMemSegment()
Default destructor.
Definition: sharedmem.cpp:110
void close_()
Must be called before destruction. Releases correct amount of metadata bytes (depending on the subcla...
Definition: sharedmem.cpp:98
std::size_t n_bytes
Maximum size of the payload (this much is reserved)
Definition: sharedmem.h:125
void init()
Must be called after construction. Reserves shmem payload and correct metadata (depending on the subc...
Definition: sharedmem.cpp:82
void * ptr_
Raw pointers to shared memory.
Definition: sharedmem.h:119
SharedMemSegment(const char *name, std::size_t n_bytes, bool is_server=false)
Default constructor.
Definition: sharedmem.cpp:76
bool is_server
Client or server process?
Definition: sharedmem.h:118
This FrameFilter writes frames into a SharedMemRingBuffer.
Definition: sharedmem.h:373
ShmemFrameFilter(const char *name, int n_cells, std::size_t n_bytes, int mstimeout=0)
Default constructor.
Definition: sharedmem.cpp:878
virtual void go(Frame *frame)
Does the actual filtering/modification to the Frame. Define in subclass.
Definition: sharedmem.cpp:886
Shared mem segment with simple metadata : just the payload length.
Definition: sharedmem.h:138
virtual void copyMetaTo(void *meta_)
Dereference metadata pointer correctly and copy the contents from this memory segment's metadata.
virtual void copyMetaFrom(void *meta_)
Dereference metadata pointer correctly and copy the contents into this memory segment's metadata.
virtual void serverClose()
Erases the shmem segment. used by the constructor if is_server=true.
virtual void putAVRGBFrame(AVRGBFrame *f)
Copy from AVFrame->data directly. Only metadata used: payload size.
Definition: sharedmem.cpp:171
virtual void put(std::vector< uint8_t > &inp_payload, void *meta_)
typecast void to std::size_t
Definition: sharedmem.cpp:150
virtual void serverInit()
Uses shmem_open with write rights. used by the constructor if is_server=true. Init with correct metad...
virtual bool clientInit()
Uses shmem_open with read-only rights. Init with correct metadata serialization.
virtual std::size_t getSize()
Client: return metadata = the size of the payload (not the maximum size). Uses SharedMemSegment::getM...
Definition: sharedmem.cpp:145
List of common header files.
Definition of FrameFilter and derived classes for various purposes.
A seriazable metadata object.
Definition: sharedmem.h:174
std::size_t size
Actual size copied // <pyapi>
Definition: sharedmem.h:175