Reputation: 772
This is related to a previous post:
Allocating a large memory block in C++
I would like a single C++ server running that generates a giant matrix M
. Then, on the same machine I would like to run other programs that can contact this server, and get the memory address for M
. M
is read only, and the server creates it once. I should be able to spawn a client ./test
and this programs should be able to make read only access to M
. The server should always be running, but I can run other programs like ./test
at anytime.
I don't know much about C++ or OS, what is the best way to do this? Should I use POSIX threads? The matrix is a primitive type (double
, float
etc), and all programs know its dimensions. The client programs require the entire matrix, so I don't want latency from mem copy from the server to the client, I just want to share that pointer directly. What are my best options?
Upvotes: 1
Views: 2306
Reputation: 5710
One mechanism of inter-process communication you could definitely use for sharing direct access to you matrix M
is shared memory. It means that the OS lets multiple processes access a shared segment in the memory, as if it was in their address space, by mapping it for each one requesting. A solution that answers all your requirements, and is also cross-platform is boost::interprocess. It is a thin portable layer that wraps all of the necessary OS calls. See a working example right here in the docs.
Essentially, your server process just needs to create an object of type boost::interprocess::shared_memory_object
, providing the constructor with a name for the shared segment. When calling its truncate()
method, the OS will look for a large enough segement in the address space of this server process. From this moment, any other process can create an object of the same type and provide the same name. Now it too has access to the exact same memory. No copies involved.
If for some reason you are unable to use the portable Boost libraries, or for other reason want to restrict the supported platform to Linux, use the POSIX API around the mmap()
function. Here's the Linux man page. Usage is basically not far from the Boost pipeline described above. you create the named segment with shm_open()
and truncate with ftruncate()
. From there onwards you receive the mapped pointer to this allocated space by calling mmap()
. In simpler cases where you'll only be sharing between parent and child processes, you can use this code example from this very website.
Of course, no matter what approach you take, when using a shared resource, make sure to synchronize read/writes properly so to avoid any race condition -- as you would have done in the scenario of multiple threads of the same process.
Upvotes: 2
Reputation: 2474
Of course other programs cannot access the matrix as long as it is in the "normal" process memory.
Without questioning the design approach: Yes, you have to use shared memory. Lookup functions like shmget(), shmat() etc. Then you don't need to pass the pointer to another program (which would not work, actually), you simply use the same file in ftok() everywhere to get access to the shared memory.
Upvotes: 0