Я играл с буферами копирования при записи в Linux, и следующий пример, похоже, работает так, как задумано:
#include <stdio.h>
#include <stdlib.h>
#include <sys/mman.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
#define SIZE 4096
#define SHM_NAME "foobar"
int main(void)
{
int fd = shm_open(SHM_NAME, O_RDWR | O_CREAT, 0666);
int r = ftruncate(fd, SIZE);
char *buf1 = mmap(NULL, SIZE, PROT_READ | PROT_WRITE,
MAP_SHARED, fd, 0);
strcpy(buf1, "Original buffer");
char *buf2 = mmap(NULL, SIZE, PROT_READ | PROT_WRITE,
MAP_PRIVATE, fd, 0);
// At this point buf2 is aliased to buf1
// Now modifying buf2 should trigger copy-on-write)...
strcpy(buf2, "Modified buffer");
// buf1 and buf2 are now two separate buffers
strcpy(buf1, "Modified original buffer");
// clean up
r = munmap(buf2, SIZE);
printf("munmap(buf2): %i\n", r);
r = munmap(buf1, SIZE);
printf("munmap(buf1): %i\n", r);
r = shm_unlink(SHM_NAME);
printf("shm_unlink: %i\n", r);
return EXIT_SUCCESS;
}
Однако в OS X (10.10) второй вызов mmap
возвращает MAP_FAILED
с errno
= 22 (EINVAL
). справочная страница OS X для mmap
a> кажется, что это должно работать (в описании флага MAP_PRIVATE
даже упоминается копирование при записи), и я экспериментировал с различными флагами для вызовов mmap
, но, похоже, ничего не работает. Есть идеи ?
OS X
использованиеMAP_PRIVATE
не обрабатывает файловые дескрипторы одинаково. - person l'L'l   schedule 14.03.2015offset
вmmap
в этом примере? - person Paul R   schedule 14.03.2015MAP_PRIVATE
, который изначально имеет псевдоним для буфераMAP_SHARED
, а затем переназначается с помощью копирования при записи. Поэтому я думаю, чтоoffset
должен быть равен 0 для обоих, но я готов попробовать что угодно. ;-) - person Paul R   schedule 14.03.2015open
; Кажется, что использованиеshm_open
и выполнение псевдонима сMAP_SHARED
иMAP_PRIVATE
каким-то образом портит дескриптор файла. Судя по внешнему виду, это может быть ошибка. - person l'L'l   schedule 14.03.2015open
с обычным файлом вместоshm_open
, и теперь все работает! Большое спасибо за вашу помощь - не стесняйтесь написать это как ответ, если хотите, и я проголосую/приму его, в противном случае я сделаю это сам позже для всех, у кого может возникнуть такая же проблема в будущем. . - person Paul R   schedule 14.03.2015