内存文件系统

ramdisk

Linux内核2.0/2.2就已经支持,为了能够使用Ramdisk,我们在编译内核时须将block device中的Ramdisk支持选上,它下面还有两个选项,一个是设定Ramdisk的大小,默认是4096k;

首先查看一下可用的RamDisk,使用ls /dev/ram*
首先创建一个目录,比如test,运行mkdir /mnt/test;
然后对/dev/ram0 格式化创建文件系统,运行mke2fs /dev/ram0;
最后挂载 /dev/ram0,运行mount /dev/ram /mnt/test,就可以象对普通硬盘一样对它进行操作了。

如果umount再加载,只要不重启linux,那文件依然会保存在/dev/ramX中

ramfs

Ramfs顾名思义是内存文件系统,它处于虚拟文件系统(VFS)层,而不像ramdisk那样基于虚拟在内存中的其他文件系统(ex2fs)。因而,它无需格式化,可以创建多个,只要内存足够,在创建时可以指定其最大能使用的内存大小。

# mount -t ramfs none /testRAM

# mount -t ramfs none /testRAM -o maxsize=2000

umount后再加载数据消失

tmpfs

Tmpfs是一个虚拟内存文件系统,它不同于传统的用块设备形式来实现的Ramdisk,也不同于针对物理内存的Ramfs。Tmpfs可以使用物理内存,也可以使用交换分区

在编译内核时须将

File systems -->> pseudo filesystems -->>  Virtual memory file system support支持选上。
mkdir -p /mnt/tmpfs
mount tmpfs /mnt/tmpfs -t tmpfs
同样可以在加载时指定tmpfs文件系统大小的最大限制:
mount tmpfs /mnt/tmpfs -t tmpfs -o size=32m

size=32m,内存的消耗值不是32m,要看真实使用

umount后再加载数据消失。

共享内存

(1) * System V shared memory(shmget/shmat/shmdt) *

(2) * POSIX shared memory(shm_open/shm_unlink) *

  1. 用于SYSV共享内存,还有匿名内存映射;这部分由内核管理,用户不可见;

2.用于POSIX共享内存,由用户负责mount,而且一般mount到/dev/shm;依赖于CONFIG_TMPFS;

System V与POSIX共享内存都是通过tmpfs实现,但是受的限制却不相同。也就是说/proc/sys/kernel/shmmax只会影响SYS V共享内存,/dev/shm只会影响Posix共享内存

Posix共享内存区对象的大小可在任何时刻通过ftruncate修改,而System V 共享内存区对象的大小是在调用shmget创建时固定下来的。

Posix共享内存区是先调用shm_open然后再调用mmap,System V 共享内存区是先调用shmget再调用shmat。

mmap

mmap, 它把文件内容映射到一段内存上(准确说是虚拟内存上), 通过对这段内存的读取和修改, 实现对文件的读取和修改,mmap()系统调用使得进程之间可以通过映射一个普通的文件实现共享内存

  void *mmap(void *addr, size_t length, int prot, int flags,
                  int fd, off_t offset);
data = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);

mmap函数成功返回指向内存区域的指针
addr,某个特定的地址作为起始地址,当被设置为NULL,系统会在地址空间选择一块合适的内存区域。

const char *memname = "/mymem";
//创建在/dev/shm下面, 必须“/”开始
    const size_t region_size = sysconf(_SC_PAGE_SIZE);
    int fd = shm_open(memname, O_CREAT|O_TRUNC|O_RDWR, 0666);
    if (fd == -1)
        error_out("shm_open");
    r = ftruncate(fd, region_size);
    if (r != 0)
        error_out("ftruncate");
    void *ptr = mmap(0, region_size, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0);
    if (ptr == MAP_FAILED)
        error_out("MMAP");
    close(fd);

Android 下的property

其中data的创建采用内存映射函数mmap,用dev/properties的原因是因为dev为tmpfs

static int init_workspace(workspace *w, size_t size)
{
    void *data;
    int fd;

        /* dev is a tmpfs that we can use to carve a shared workspace
         * out of, so let's do that...
         */
    fd = open("/dev/__properties__", O_RDWR | O_CREAT, 0600);
    if (fd < 0)
        return -1;

    if (ftruncate(fd, size) < 0)
        goto out;

    data = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); ------内存映射,属性为MAP_SHARED
    if(data == MAP_FAILED)
        goto out;

    close(fd);

    fd = open("/dev/__properties__", O_RDONLY);
    if (fd < 0)
        return -1;

    unlink("/dev/__properties__");

    w->data = data;----workspace的地址空间指向内存映射的区域
    w->size = size;
    w->fd = fd;
    return 0;

out:
    close(fd);
    return -1;
}

你可能感兴趣的:(Linux)