I am creating an interprocess communication scheme using boost::interprocess
. I want my shared memory area to contain some std::vector
s and am doing this based on the example provided here.
To communicate, I plan to put a struct like the following in the shared memory (not even attempted to compile this yet btw):
// Define an STL compatible allocator of doubles that allocates from the managed_shared_memory.
// This allocator will allow placing stl containers in the segment
typedef allocator<doublereal, boost::interprocess::managed_shared_memory::segment_manager> ShmemAllocator_doublereal;
// Alias a vector that uses the previous STL-like allocator so that it
// allocates its values from the segment
typedef vector<doublereal, ShmemAllocator_doublereal> shmVector_doublereal;
// Define an STL compatible allocator for uint32_t in shared memory
typedef allocator<uint32_t, boost::interprocess::managed_shared_memory::segment_manager> ShmemAllocator_uint32_t;
// Shared memory vector for uint32_t type for lables
typedef vector<uint32_t, ShmemAllocator_uint32_t> shmVector_uint32_t;
struct shared_memory_buffer {
// Server initialized with one to start, client must wait for it to be released
shared_memory_buffer(int nnodes, boost::interprocess::managed_shared_memory segment): server(1), client(0){
// Initialize shared memory STL-compatible allocators
const ShmemAllocator_doublereal alloc_inst_d (segment.get_segment_manager());
const ShmemAllocator_uint32_t alloc_inst_u (segment.get_segment_manager());
// Construct the data vectors
motion_data = segment.construct<shmVector_doublereal>("motion_data_vector")(alloc_inst_d);
force_data = segment.construct<shmVector_doublereal>("force_data_vector")(alloc_inst_d);
labels = segment.construct<shmVector_uint32_t>("label_vector")(alloc_inst_u);
// position, velocity and acceleration in 6dof
motion_data.resize (nnodes * 6 * 3);
// force in 6dof
force_data.resize (nnodes * 6);
// n node labels
labels.resize (nnodes);
}
// convenience function to get the motion data vector from the shared
// memory segment
shmVector_doublereal<doublereal, ShmemAllocator_doublereal> * getMotionData (boost::interprocess::managed_shared_memory segment) {
return segment.find<shmVector_doublereal>("motion_data_vector").first;
}
// convenience function to get the force data vector from the shared
// memory segment
shmVector_doublereal<doublereal, ShmemAllocator_doublereal> * getMotionData (boost::interprocess::managed_shared_memory segment) {
return segment.find<shmVector_doublereal>("force_data_vector").first;
}
// convenience function to get the buffer from the shared
// memory segment
shmVector_doublereal<doublereal, shmMemAllocator> * getLabels (boost::interprocess::managed_shared_memory segment) {
return segment.find<shmVector_uint32_t>("label_vector").first;
}
// semaphores for read/write control
boost::interprocess::interprocess_semaphore server, client;
// buffer for motion data
shmVector_doublereal<doublereal, shmMemAllocator> *motion_data;
// buffer for force data
shmVector_doublereal<doublereal, shmMemAllocator> *force_data;
// buffer for label data
shmVector_uint32_t<uint32_t, shmMemAllocator> *labels;
//doublereal time;
};
My problem is, how can I know how much memory to allocate when creating the shared memory, e.g. with
managed_shared_memory segment(create_only, "MySharedMemory", 65536);
I therefore want to know/estimate how much memory in total must be allocated to hold the entire structure, which contains stl vectors, in the shared memory area.
At run time, before shared memory allocation I will always know how many elements will be in the vectors (see the struct constructor to give an idea of this), but not at compile time, which is one reason I'm using vectors. I could just allocate what I deem to be quite a lot, based on how I think people might use this, but no doubt some day someone will use too many nodes and will have difficulties.