#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <stdio.h>
int main(void){
// 创建一个ipc的key
key_t k = ftok(".",8);
// 通过key创建或获取共享内存ID 返回共享内存ID 失败返回-1
/*
* shmget 创建或获取共享内存ID
* key: ftok函数返回的key
* size 要开辟内存空间的字节数,按页取整
* shmflg 标志位置
* 0 - 获取 不存在即失败(是否存在根据key来判断)
* IPC_CERAT - 创建 不存在即创建,已存在即获取(是否存在根据key来判断)
* IPC_EXCL - 排它 不存在即创建,已存在即失败(是否存在根据key来判断)
* */
// 表示创建权限为0664内存不获取旧的内存
int mid = shmget(k, sizeof(int ),IPC_CREAT | IPC_EXCL | 0664);
if (mid == -1){
perror("shmget");
return -1;
}
// 加载共享内存 返回共享内存的起始地址 失败返回 (void*)-1
/*
* shmat 加载共享内存
* shmid 共享内存的ID
* shmaddr 共享内存的下虚拟内存起始地址,NULL则由系统自动选择
* shmflg 加载标志
* 0 以读写的方式共享
* SHM_RDONLY 以只读的方式共享
* */
shmat();
// 解除内存映射关系
/*
* shmdt 解除内存映射关系
* shmaddr 需要解除映射的内存首地址
*
* 成功 返回0 失败返回-1
* */
shmdt();
// 控制共享内存
/*
* shmctl 控制共享内存
* shmid 要操作的共享内存ID
* cmd 要做的操作
* IPC_RMID 销毁共享内存
* buf NULL
* 成功返回0 失败返回-1
* 备注:调用销毁时,并非立即销毁,需要加载计数为0时才真正销毁;并且其他进程无法创建与这块共享内存的映射,之前已经创建的不受影响
* */
shmctl();
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <sys/shm.h>
#include <unistd.h>
int main(void){
// 创建key
key_t k = ftok(".",8);
if (k == 0xffffffff){
perror("ftok");
return -1;
}
// 通过key创建共享空间,获取共享空间的ID
printf("%d:创建共享空间\n",getpid());
int mid = shmget(k, 4096,IPC_CREAT | IPC_EXCL | 0664);
if (mid == -1){
perror("shmget");
return -1;
}
// 将共享空间的ID映射到虚拟内存表(加载空间)
printf("%d:加载空间\n",getpid());
void* shmatAddr = shmat(mid,NULL,0);
if (shmatAddr == (void*)-1){
perror("shmat");
return -1;
}
// 在共享内存中写入数据
printf("%d:写入数据\n",getpid());
if(sprintf(shmatAddr,"KEY=%x;PID=%d;shmatAddr=%p",k,getpid(),shmatAddr) == -1){
perror("sprintf");
return -1;
}
// 卸载共享空间
printf("%d:卸载共享空间\n",getpid());
if (shmdt(shmatAddr) == -1){
perror("shmat");
return -1;
}
getchar();
// 销毁共享空间
printf("%d:销毁共享空间\n",getpid());
if(shmctl(mid,IPC_RMID,NULL)==-1){
perror("销毁共享空间");
return -1;
}
return 0;
}
#include <stdlib.h>
#include <stdio.h>
#include <sys/shm.h>
#include <unistd.h>
int main(void){
// 创建key
key_t k = ftok(".",8);
if (k == 0xffffffff){
perror("ftok");
return -1;
}
// 通过key获取空间,获取共享空间的ID
printf("%d:获取共享空间\n",getpid());
int mid = shmget(k, 0,0);
if (mid == -1){
perror("shmget");
return -1;
}
// 将共享空间的ID映射到虚拟内存表(加载空间)
printf("%d:加载空间\n",getpid());
void* shmatAddr = shmat(mid,NULL,0);
if (shmatAddr == (void*)-1){
perror("shmat");
return -1;
}
// 读取共享空间中的数据v
printf("%d:读取数据\n",getpid());
printf("%s\n",(char*)shmatAddr);
// 卸载共享空间
printf("%d:卸载共享空间\n",getpid());
if (shmdt(shmatAddr) == -1){
perror("shmat");
return -1;
}
return 0;
}