进程间通信Inter-Process Communication,IPC
1)匿名管道
int pipe(int fd[2]); 产生一个管道,两端各自用一个文件描述符表示,其中读端的文件描述符保存在fd[0]中,写端的文件描述符保存在fd[1]中。
只能用于父子进程间通信。在两个进程中只保留个描述符,一个保留写,另一个保留读,反之亦然。
2)命名管道named pipe (mkfifo)
int mkfifo(const char *pathname, mode\_t mode); //按指定的权限去创建管道文件
打开是不应使用O\_CREAT;
打开操作会等待同时存在读写双方时才继续;
可以用于任意进程间单向通信。
3)匿名本地网络
socketpair(AF\_LOCAL, SOCK\_STREAN, 0, int fd[2]); //产生一对相互连接的网络套接字,可以用于两进程间相互通信
用于fork的父子进程中通信,每个进程中只保留个套接字就好,读写都用它。
4)专业的进程间通信方式:共享内存、消息队列、信号量
共享内存:
int shmget(key\_t key, size\_t size, int shmflg); //创建或获取一块共享内存对象,返回对象id,同一个可以返回同一个共享内存id, 当key是IPC\_PRIVATE的时候例外,总是创建一片新的共享内存。shmflag可以是PIC\_CREAT IPC\_EXCL的适当组合。失败返回-1.key 类似于文件路径。
void *shmat(int shmid, const void *shmaddr, int shmflg); //把共享内存对象挂接到本进程内存中,返回挂接后的地址,失败返回-1
int shmdt(const void *shmaddr); //解除共享内存对象的挂接,shmaddr是shmat的返回值
int shmctl(int shmid, int cmd, struct shmid\_ds *buf); //对共享内存的操作
shmctl(id, IPC\_RMID, NULL) //删除共享内存
ipcs 命令查看进程间通信对象状态,ipcrm删除进程间通信对象
消息队列:
int msgget(key\_t key, int msgflg); //创建或取得消息队列对象,返回对象的id,同一个key返回相同id
int msgsnd(int msqid, const void *msgp, size\_t msgsz, int msgflg); //打包发送一个消息数据到队列中,返回发送的字节数
ssize\_t msgrcv(int msqid, void *msgp, size\_t msgsz, long msgtyp, int msgflg); //从消息队列中接收指定类型的消息,返回收到的字节数
int msgctl(int msqid, int cmd, struct msqid\_ds *buf); //对一个消息队列进行设置
消息队列里头的消息由类型和数据组成,发送和接收的时候指定的长度都是指的数据的长度(不包括类型占用的4字节)。
信号量集
int semget(key\_t key, int nsems, int semflg); //创建获取的一个信号量集对象,返回对象id,semflg 可以是0/IPC\_CREAT/IPC\_EXCL跟权限组合
int semop(int semid, struct sembuf *sops, size\_t nsops);//对信号量集中sops指定的信号量操作
struct sembuf{
......
unsigned short sem\_num; 一般是0,表示第一信号量
short sem\_op; 计数器操作,一般是1或-1,表示计算器加1或减1
short sem\_flg; 0或IPC\_NOWAIT或SEM\_UNDO组合,其中SEM\_UNDO表示进程结束时系统自动复原该信号量
};
int semctl(int semid, int semnum, int cmd, ...); //IPC\_RMID
semctl(semid, 0, IPC\_RMID, NULL) //删除信号量集
semctl(semid, idx, SETVAL, N) //设置编号为dix的信号量值为N
信号量就是一个计数器,一般用来控制访问同一资源的进程数量,控制多个进程的同步。计数器的减1操作在不够减时会等待直到够减为止(信号可能会打断它),semtimedop可以指定超时时间。

标签: 进程, int, 共享内存, IPC, key, 间通信, 信号量, 方式

相关文章推荐

添加新评论,含*的栏目为必填