mmap help

Discussion in 'Mac Programming' started by laprej, Nov 25, 2014.

  1. laprej macrumors regular

    Joined:
    Oct 14, 2005
    Location:
    Troy, NY
    #1
    The intent of this code is to create a posix shared memory segment, open it in RW mode using mmap(), then open the same segment in private mode so I get the copy-on-write functionality.

    Can anyone see what I'm doing wrong in this code? It compiles and runs fine under Linux but after outputting "debug 1" I get
    (It's mostly just error-checking code below

    Code:
    #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 <errno.h>
    
    #define SIZE 4*4096
    
    #define HANDLE "/tmpmem2"
    
    int main(void) {
        int err = EXIT_SUCCESS;
        
        int fd = shm_open(HANDLE, O_RDWR | O_CREAT, 0777);
        
        if (fd == -1) {
            perror(NULL);
            err = -1;
            goto end;
        }
        
        printf("Page size is %ld\n", sysconf(_SC_PAGESIZE));
        
        int r = ftruncate(fd, SIZE);
        if (r == -1) {
            printf("errno is %d\n", errno);
            perror(NULL);
            err = -1;
            goto unlink;
        }
        
        printf("fd: %i, r: %i\n", fd, r);
        char *buf = mmap(0, SIZE, PROT_READ | PROT_WRITE,
                        MAP_SHARED, fd, 0);
        if (buf == MAP_FAILED) {
            printf("errno is %d\n", errno);
            perror(NULL);
            err = -1;
            goto unlink;
        }
        printf("buf is %p\n", buf);
        
        printf("debug 0\n");
        buf[SIZE - 2] = 41;
        buf[SIZE - 1] = 42;
        printf("debug 1\n");
        
        char *buf2 = mmap(0, SIZE, PROT_READ | PROT_WRITE,
                          MAP_PRIVATE, fd, 0);
        if (buf2 == MAP_FAILED) {
            printf("errno is %d\n", errno);
            perror(NULL);
            err = -1;
            goto munmap1;
        }
        
        printf("buf2: %p\n", buf2);
        buf2[SIZE - 1] = 43;
        buf[SIZE - 2] = 40;
        printf("buf[-2]: %i, buf[-1]: %i, buf2[-2]: %i, buf2[-1]: %i\n",
               buf[SIZE - 2],
               buf[SIZE - 1],
               buf2[SIZE - 2],
               buf2[SIZE - 1]);
        
    munmap2:
        munmap(buf2, SIZE);
        
    munmap1:
        munmap(buf, SIZE);
        
    unlink:
        shm_unlink(HANDLE);
        
    end:
        return err;
    }
    
     
  2. willieva macrumors 6502

    Joined:
    Mar 12, 2010
    #2
    This code compiles and runs fine on centos7 gcc 4.8.2

    Page size is 4096
    fd: 3, r: 0
    buf is 0x7f605a6f9000
    debug 0
    debug 1
    buf2: 0x7f605a6f5000
    buf[-2]: 40, buf[-1]: 42, buf2[-2]: 41, buf2[-1]: 43
     
  3. laprej thread starter macrumors regular

    Joined:
    Oct 14, 2005
    Location:
    Troy, NY
    #3
    Sorry, I meant to say it runs fine under Linux but fails to run correctly on Mac...
     
  4. laprej thread starter macrumors regular

    Joined:
    Oct 14, 2005
    Location:
    Troy, NY
    #4
    For what it's worth, I found a work-around. In place of shm_open(), I used mkstemp(). Should be more or less the desired functionality.
     

Share This Page