0

I'm working with mmap() function. I Confiused about something in mmap flags.

MAP_SHARED with fd → Usage To allocated virtual memory which uses Hard Drive (HDD) and physical memory (RAM) will not be used. I allocated 2 GB using this flag with fd and my RAM remained unused (what I expected).

MAP_PRIVATE|MAP_ANONYMOUS with (fd = -1) → Usage To allocated main memory, which is RAM. I allocated 2 GB using this flag and I filled it with something then I checked my RAM usage and yes, 2 GB in use ...

Now my point, first method (MAP_SHARED) uses virtual memory (HDD) and second method (MAP_PRIVATE|MAP_ANONYMOUS) uses main memory (RAM) so 100% the second method MUST be different in performance since RAM is too much faster than HDD ... am I right ? If I'm right, so why mmap function is called as a 'virtual memory allocation' function !!!??? By flag MAP_PRIVATE|MAP_ANONYMOUS allocates main memory (RAM) too !!!!!!!

If MAP_PRIVATE|MAP_ANONYMOUS does not guarantee to provide 'main memory (RAM)', what should I do to allocated memory from main memory (RAM) ?!

What I got from mmap, mmap checks if a private flag (MAP_PRIVATE|MAP_ANONYMOUS) is provided, checks for unused RAM space and provides memory from RAM (main memory), if there is available space on RAM and if there isn't, it uses virtual memory (HDD). Right !?

Update

I decide to put 2 tests. one with MAP_SHARED and one with MAP_PRIVATE|MAP_ANONYMOUS

test 1 Memory allocation based on a file (MAP_SHARED)

#include <stdio.h>
#include <sys/mman.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include <fcntl.h>
#include <time.h>

int
main() {
    double time_spent = 0.0;
    int fd = open("/home/alireza/Documents/mem", O_CREAT|O_RDWR);
    ftruncate(fd, (4294967296));
    char * memory = mmap(NULL, (4294967296), PROT_WRITE|PROT_READ, MAP_SHARED, fd, 0);
    if(memory == MAP_FAILED) {
        printf("(%d)", errno);
        exit(0);
    }
    write(0, "started ...\n", sizeof("started ...\n")-1);
    clock_t begin = clock();
    for (long i = 0; i < (4294967296); i++) {
        memory[i] = 'c';
    }
    clock_t end = clock();
    write(0, "done\n", sizeof("done\n")-1);
    time_spent += (double)(end - begin) / CLOCKS_PER_SEC;
    printf("time (%f)\n", time_spent);
    exit(0);
}

Result (9 seconds (since it uses virtual memory (HDD)) !!!)

started ...
done
time (9.087634)

test 2 Memory allocation using RAM (MAP_PRIVATE|MAP_ANONYMOUS)

#include <stdio.h>
#include <sys/mman.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include <fcntl.h>
#include <time.h>

int
main() {
    double time_spent = 0.0;
    char * memory = mmap(NULL, (4294967296), PROT_WRITE|PROT_READ, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
    if(memory == MAP_FAILED) {
        printf("(%d)", errno);
        exit(0);
    }
    write(0, "started ...\n", sizeof("started ...\n")-1);
    clock_t begin = clock();
    for (long i = 0; i < (4294967296); i++) {
        memory[i] = 'c';
    }
    clock_t end = clock();
    write(0, "done\n", sizeof("done\n")-1);
    time_spent += (double)(end - begin) / CLOCKS_PER_SEC;
    printf("time (%f)\n", time_spent);
    exit(0);
}

Result (1 second)

started ...
done
time (1.405220)

So mmap is not just virtual memory allocation (HDD). It's main memory allocation too, and it decides it based on the flag ! So using MAP_PRIVATE|MAP_ANONYMOUS flag to use real memory (RAM) is completely different from using SHARED flag !

HelloMachine
  • 355
  • 2
  • 8
  • 2
    This sounds like a question about the terminology. It may help to understand that one of the use case for `mmap` is to map the same file in multiple processes to share that memory space to allow inter process communication. If you just want to allocate memory normally, you can use `new`, `std::make_unique`, `std::allocator` and other portable solutions instead of `mmap` unless you are doing something very specific. – François Andrieux Jun 29 '21 at 17:14
  • 1
    Here shared doesn't mean the location of the memory, instead it means processes can share it with each other. – NathanOliver Jun 29 '21 at 17:15
  • 1
    It would be a neat trick which "uses Hard Drive" but "memory (RAM) will not be used". That's not how `MAP_SHARED` works. Which specific part of `mmap`'s documentation led you to draw thijs conclusion? Can you quote that documentation, verbatim? – Sam Varshavchik Jun 29 '21 at 17:16
  • Sorry, I changed 'shared' memory to 'virtual' memory. I mean 'virtual' memory not 'shared' because a main memory (RAM) could be shared too. – HelloMachine Jun 29 '21 at 17:22
  • 1
    All of the memory userland processes can access is 'virtual'. Do you mean "mapped from a file"? Because the `MAP_ANONYMOUS` flag is explicitly telling `mmap` "I don't want this mapped from a particular file; I just want it to be treated as if it was". I would also point out that `MAP_PRIVATE` and `MAP_ANONYMOUS` are orthogonal. It's perfectly valid to specify `MAP_SHARED|MAP_ANONYMOUS` to get an anonymous shared mapping. – Miles Budnek Jun 29 '21 at 17:32
  • Very Related: [Understanding Virtual Address, Virtual Memory and Paging](https://stackoverflow.com/questions/22290347/understanding-virtual-address-virtual-memory-and-paging) – Mooing Duck Jun 29 '21 at 17:45
  • @Mooing Duck No since I'm talking about `mmap`. what `mmap` do. – HelloMachine Jun 29 '21 at 17:50
  • @HelloMachine: `mmap` allocates virtual memory, that may be backed by a file, or it may be other shared virtual memory, or it may be unshared virtual memory. – Mooing Duck Jun 29 '21 at 18:01
  • @Mooing Duck: so why when we using `MAP_PRIVATE|MAP_ANONYMOUS`, it allocates memory from RAM !!? So it's not always 'virtual memory' – HelloMachine Jun 29 '21 at 18:33
  • 1
    virtual memory does not mean disk. It can be RAM, disk, or not allocated. Its just the address space of the process. – stark Jun 29 '21 at 18:38
  • 1
    mmap doesn't actually allocate any RAM until you use it. If you mmap 4 GB and use only 4 KB, then that much RAM will be actually allocated. The OS can seamlessly use a swap file for pages that don't fit in RAM. Also in file-backed mode the OS still allocates RAM, for caching purposes. So the boundary between file-backed and not is really blurred. And it's all exactly the same process in the kernel, it's virtual memory. – rustyx Jun 29 '21 at 18:42
  • @stark but in every place I read about virtual memory, they said 'HDD' ... – HelloMachine Jun 29 '21 at 18:43
  • 1
    Then you are reading the wrong places. – stark Jun 29 '21 at 18:43
  • @rustyx I know about page size and each 4 Kb must be filled to count as used space ... So you're telling me that OS decides to use a file-backed mode or real RAM.... a question ! How MySQL has 'MEMORY' database type ? 'MEMORY' means real RAM usage. So there must be a way to use actual memory (RAM (not just for caching)) instead of file-backed memory .... no ? – HelloMachine Jun 29 '21 at 18:50
  • I think you've got some misconceptions here. mmap'ing a file doesn't mean that RAM will not be used - it means that whatever RAM is used will be *backed* by the file on the disk. The RAM will be filled with the file contents before you read it, and any modifications will be written back to the file when you are done (if not before). – Nate Eldredge Jun 29 '21 at 20:57
  • @NateEldredge correct, but why using `MAP_SHARED` flag with fd takes 9 seconds (copy 4 billion characters) and using `MAP_PRIVATE|MAP_ANONYMOUS` flag without fd takes 1 second (copy 4 billion characters) ?!!! – HelloMachine Jun 30 '21 at 05:27
  • Where are you copying to or from? – Nate Eldredge Jun 30 '21 at 05:53
  • @NateEldredge you can see the examples in my question. I used `mmap` with `MAP_SHARED` and a file (`fd`) and I copied 4 billion characters into the allocated space. It took 9 seconds. Then I used `mmap` with `MAP_PRIVATE|MAP_ANONYMOUS` without `fd` and I copied the same (4 billion characters into the allocated space), It took only 1 second. So using `MAP_PRIVATE|MAP_ANONYMOUS` is not about FILE any more ! since using `MAP_PRIVATE|MAP_ANONYMOUS` flag is about directly RAM usage. – HelloMachine Jun 30 '21 at 05:56
  • `MAP_ANONYMOUS` mappings are backed by swap. – ninjalj Jun 30 '21 at 09:19

0 Answers0