TmpFile: support IPC via shared memory mapping

For this to work, the memory must be mapped MAP_SHARED (otherwise
writes are not visible outside of the process) and the recipient
of a file descriptor must be able to create a TmpFile for it, which
then can be used to create a memory mapping.
This commit is contained in:
Patrick Ohly 2014-09-01 12:40:32 +02:00
parent 85b570e5db
commit b4b611002c
2 changed files with 22 additions and 1 deletions

View File

@ -103,6 +103,15 @@ void TmpFile::create(Type type)
}
}
void TmpFile::create(int fd)
{
if (m_fd >= 0 || m_mapptr || m_mapsize) {
throw TmpFileException("TmpFile::create(): busy");
}
m_fd = fd;
m_filename.clear();
m_type = FILE;
}
void TmpFile::map(void **mapptr, size_t *mapsize)
{
@ -117,7 +126,13 @@ void TmpFile::map(void **mapptr, size_t *mapsize)
if (fstat(m_fd, &sb) != 0) {
throw TmpFileException("TmpFile::map(): fstat()");
}
m_mapptr = mmap(NULL, sb.st_size, PROT_READ|PROT_WRITE, MAP_PRIVATE,
// TODO (?): make this configurable.
//
// At the moment, SyncEvolution either only reads from a file
// (and thus MAP_SHARED vs. MAP_PRIVATE doesn't matter, and
// PROT_WRITE doesn't hurt), or writes for some other process
// to read the data (hence needing MAP_SHARED).
m_mapptr = mmap(NULL, sb.st_size, PROT_READ|PROT_WRITE, MAP_SHARED,
m_fd, 0);
if (m_mapptr == MAP_FAILED) {
m_mapptr = 0;

View File

@ -64,6 +64,12 @@ class TmpFile
*/
void create(Type type = FILE);
/**
* Create a temporary file with an already existing
* file descriptor. New instance owns the FD.
*/
void create(int fd);
/**
* Map a view of file and optionally return pointer and/or size.
*