共享内存区
来源:互联网 发布:华住酒店员工流失数据 编辑:程序博客网 时间:2024/06/05 17:12
Posix提供了无亲缘关系进程间共享内存区的两种方法:1.内存映射文件 由open函数打开,由mmap函数把得到的描述字映射到当前进程地址空间的一个文件。#include <sys/mman.h>void *mmap(void *addr, size_t len, int prot, int flags, int fd, off_t offset); addr可以指定为描述字fd应被映射到的进程内空间起始地址。通常被指定为NULL,由内核自己决定。len为映射的字节数。offset常设置为0,prot常见值为PROT_READ|PROT_WRITE。 prot常用参数表: prot description PROT_READ 数据可读 PROT_WRITE 数据可写 PROT_EXEC 数据可执行 PROT_NONE 数据不可访问 flags常用参数表: flags description MAP_SHARED 变动是共享的 MAP_PRIVATE 变动是私有的 MAP_FIXED 准确解释addr参数父子进程之间共享内存区的方法之一是,父进程在调用fork前先指定MAP_SHARED调用mmap()。int munmap(void *addr, size_t len);4.4BSD提供了匿名内存映射,避免了文件的创建和打开。其办法是把mmap的flags参数指定成MAP_SHARED|MAP_ANON,fd指定为-1。offset参数被忽略。这样的内存被初始化为0。使用方式类似这样: int *ptr = mmap(NULL, sizeof(int), PROT_READ|PROT_WRITE, MAP_SHARED|MAP_ANON, -1, 0);与需要打开文件的mmap相比,增加了MAP_ANON,fd = -1. offset值随意。2.共享内存区对象 由shm_open打开一个Posix名字,所返回描述字由mmap函数映射到当前进程地址空间。 int shm_open(const char *name, int oflag, mode_t mode); int shm_unlink(const char *name); oflag参数必须或者含有O_RDONLY,或者O_RDWR标志,也可以指定O_CREAT、O_EXCL或O_TRUNC。如果随O_RDWR指定O_TRUNC,而且所需的共享内存区对象已经存在,那么它将被截短成0长度。一般shm_open的oflag与mmanp的第三个参数读写权限相对应。 mode参数总是必须指定。处理mmap的时候,普通文件或共享内存区对象的大小都可以通过调用ftruncate修改。 #include <unistd.h> int ftruncate(int fd, off_t length);允许将普通文件和共享内存区对象的大小指定为比原来的大或小。//file_shm.c#include <semaphore.h>#include <stdio.h>#include <unistd.h>#include <stdlib.h>#include <sys/stat.h>#include <sys/types.h>#include <fcntl.h>#include <sys/mman.h>#define FILE_MODE (S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)struct shared{sem_t mutex;int count;}shared;int main(int argc, char **argv){int fd, i, nloop;struct shared *ptr;if(argc != 3){perror("usage: memshared <pathname> <#loops>");exit(0);}nloop = atoi(argv[2]);fd = open(argv[1], O_RDWR | O_CREAT, FILE_MODE);write(fd, &shared, sizeof(struct shared));// mmap returns void*ptr = mmap(NULL, sizeof(struct shared), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);close(fd);sem_init(&ptr->mutex, 1, 1);// 2nd param 1 means sem is shared among different processessetbuf(stdout, NULL);if(fork() == 0){for(i = 0; i < nloop; i++){sem_wait(&ptr->mutex);printf("child:%d\n", ptr->count++);sem_post(&ptr->mutex);}exit(0);}for(i = 0; i < nloop; i++){sem_wait(&ptr->mutex);printf("parent:%d\n", ptr->count++);sem_post(&ptr->mutex);}sem_destroy(&ptr->mutex);return 0;}// obj_shm.c#include <semaphore.h>#include <stdio.h>#include <unistd.h>#include <stdlib.h>#include <sys/stat.h>#include <sys/types.h>#include <fcntl.h>#include <sys/mman.h>#define FILE_MODE (S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)struct shared{sem_t mutex;int count;}shared;int main(int argc, char **argv){int fd, i, nloop;struct shared *ptr;if(argc != 2){perror("usage: memshared <#loops>");exit(0);}nloop = atoi(argv[1]);// mmap returns void*// BSD 4.4 provide a way of mmaping without opening a file, as followsptr = mmap(NULL, sizeof(struct shared), PROT_READ | PROT_WRITE, MAP_SHARED | MAP_ANON, -1, 0);sem_init(&ptr->mutex, 1, 1);// 2nd param 1 means sem is shared among different processessetbuf(stdout, NULL);if(fork() == 0){for(i = 0; i < nloop; i++){sem_wait(&ptr->mutex);printf("child:%d\n", ptr->count++);sem_post(&ptr->mutex);}exit(0);}for(i = 0; i < nloop; i++){sem_wait(&ptr->mutex);printf("parent:%d\n", ptr->count++);sem_post(&ptr->mutex);}sem_destroy(&ptr->mutex);return 0;}
0 0
- 共享内存区
- 共享内存区
- 共享内存区
- Posix共享内存区
- 共享内存区
- Posix共享内存区
- 【共享内存】共享内存
- zwcreatesection 共享内存区(Section)
- Linux共享内存区参数设置
- System V共享内存区
- Posix共享内存区基础知识
- System V 共享内存区
- 共享内存
- 共享内存
- 共享内存
- 共享内存
- 共享内存
- 共享内存
- 多态之父子争权
- The die is cast
- 几款开源的图形界面库(GUI Libraries)
- C++ Primer 5e chapter 10.2
- JAVA UDP聊天室
- 共享内存区
- 深入理解JavaScript系列(2):揭秘命名函数表达式
- 七个例子帮你更好地理解 CPU 缓存
- C语言 - 结构体
- 最大流:Dinic模板
- Linux系统负载
- 友谊赛 排序 水题
- 几款国产开源的Windows界面库
- Apache Spark 入门简介