通信与实际用例应用(消息队列和进程撰写的ATM机与消息队列的五子棋对站)
int semget(key_t key, int nsems, int semflg);
功能:创建信号量或获取信号量
nsems:信号量的数量
semflg:
IPC_CREAT|IPC_EXEC| int semop(int semid, struct sembuf *sops, unsigned nsops);
功能:对信号量增加或减少
struct sembuf {
unsigned short sem_num;信号量的编号
short sem_op; 对信号量的操作
short sem_flg;
IPC_NOWAIT:不阻塞
} int semctl(int semid, int semnum, int cmd, ...);
功能:对信号量控制或释放
semnum:信号量的编号
cmd:
IPC_SET 设置信号量的属性
IPC_STAT 获取信号量的属性
IPC_RMID 删除信号量
IPC_INFO 获取信号的信号
GETVAL
SETVAL
https://files.cnblogs.com/files/mingyoujizao/msg_gobang1.0.zip
进程间通信的方式:
简单的进程间通信:
命令行:父进程通过exec函数创建子进程时可以附加一些数据。
环境变量:父进程通过exec函数创建子进程顺便传递一张环境变量表。
信号:父子进程之间可以根据进程号相互发送信号,进程简单通信。
文件:一个进程向文件中写入数据,另一个进程从文件中读取出来。
命令行、环境变量只能单身传递,信号太过于简单,文件通信不能实时。
XSI通信方式:X/open 计算机制造商组织。
共享内存、消息队列、信号量
网络进程间通信方式:
网络通信就是不同机器的进程间通信方式。
传统的进程间通信方式:管道
二、管道
1、管道是一种古老的通信的方式(基本上不再使用)
2、早期的管道是一种半双工,现在大多数是全双工。
3、有名管道(这种管道是以文件方式存在的)。
int mkfifo(const char *pathname, mode_t mode);
管道通信的编程模式:
进程A 进程B
创建管道mkfifo
打开管道open 打开管道
写/读数据read/write 读/写数据
关闭管道close 关闭管道
4、无名管道:由内核帮助创建,只返回管道的文件描述符,看不到管道文件,但这种管道只能用在fork创建的父子进程之间。
int pipe(int pipefd[2]);
pipefd[0] 用来读数据
pipefd[1] 用来写数据
练习:使用无名管道,让父子进程通信。
三、XSI IPC进程间通信
1、XSI通信是靠内核的IPC对象进程通信。
2、每一个IPC对象都有一个IPC标识(类似文件描述符),IPC标识它是一个非的整数。
3、IPC对象必须要先创建,创建后才能进程获取、设置、操作、删除。
4、创建IPC对象必须要提供一个键值(key_t),键值是创建、获取IPC对象的依据。
5、产生键值的方法:
固定的字面值:1980014
使用函数计算:键值=ftok(项目路径,项目id)
使用宏让操作系统随机分配:IPC_PRIVTE
必须把获取到IPC对象标识符记录下来,告诉其它进程
6、XSI可以创建的IPC对象有:
共享内存,消息队列,信号量
四、共享内存
1、由内存维护一个共享的内存区域,其它进程把自己的虚拟地址映射到这块内存,然后多个进程之间就可以共享这块内存了。
2、这种进程间通信的好处是不需要信息复制,是进程间通信最快的一种方式。
3、但这种通信方式会面临同步的问题,需要与其它通信方式配合,最合适的就是信号。
共享内存的编程模式:
1、进程之间要约定一个键值
进程A 进程B
创建共享内存
加载共享内存 加载共享内存
卸载共享内存 卸载共享内存
销毁共享内存
int shmget(key_t key, size_t size, int shmflg);
功能:创建共享内存
size:共享的大小,尽量是4096的位数
shmflg:IPC_CREAT|IPC_EXCL
返回值:IPC对象标识符(类似文件描述符)
void *shmat(int shmid, const void *shmaddr, int shmflg);
功能:加载共享内存(进程的虚拟地址与共享的内存映射)
shmid:shmget的返回值
shmaddr:进程提供的虚拟地址,如果为NULL,操作系统会自动选择一块地址映射。
shmflg:
SHM_RDONLY:限制内存的权限为只读
SHM_REMAP:映射已经存的共享内存。
SHM_RND:当shmaddr为空时自动分配
SHMLBA:shmaddr的值不能为空,否则出错
返回值:映射后的虚拟内存地址
int shmdt(const void *shmaddr);
功能:卸载共享内存(进程的虚拟地址与共享的内存取消映射关系)
int shmctl(int shmid, int cmd, struct shmid_ds *buf);
功能:控制/销毁共享内存
cmd:
IPC_STAT:获取共享内存的属性
IPC_SET:设置共享内存的属性
IPC_RMID:删除共享内存
buf:
记录共享内存属性的对象
五、消息队列
1、消息队列是一个由系统内核负责存储和管理、并通过IPC对象标识符获取的数据链表。
int msgget(key_t key, int msgflg);
功能:创建或获取消息队列
msgflg:
创建:IPC_CREAT|IPC_EXEC
获取: int msgsnd(int msqid, const void *msgp, size_t msgsz, int msgflg);
功能:向消息队列发送消息
msqid:msgget的返回人值
msgp:消息(消息类型+消息内容)的首地址
msgsz:消息内存的长度(不包括消息类型) ssize_t msgrcv(int msqid, void *msgp, size_t msgsz, long msgtyp,int msgflg);
功能:从消息队列接收消息
msgp:存储消息的缓冲区
msgsz:要接收的消息长度
msgtyp:消息的的类型(它包含消息的前4个字节)
msgflg:
MSG_NOERROR:当消息的实际长比msgsz比要接长的话,则按照msgsz长度截取再发送,否则产生错误。
MSG_NOWAIT:如果要接收的消息不存在,直接返回。
否则阻塞等待。
MSG_EXCEPT:从消息队列中接收第一个不msgtyp类型的第一个消息。 int msgctl(int msqid, int cmd, struct msqid_ds *buf);
功能:控制/销毁消息队列
cmd:
IPC_STAT:获取消息队的属性
IPC_SET:设置消息队列的属性
IPC_RMID:删除消息队列
信号量(信号灯),可以当作进程与进程之间共享的全局变量,一般用来为共享的资源计数。
信号量的使用方法:
1、进程A,创建信号量,并设置初始化(设置资源的数)
2、进程B,获取信号量,查看信号量(查询剩余资源的数量),减少信号量(使用资源),增加信号量(资源使用完毕归还还)。
3、当一进程尝试减少信号量,如果不能减(资源使用完毕),则进程可以进入等待状态,当信号量能够被减时(其它进程把资源还回来了),进程会被唤醒。
通信与实际用例应用(消息队列和进程撰写的ATM机与消息队列的五子棋对站)的更多相关文章
- Linux进程间通信--进程,信号,管道,消息队列,信号量,共享内存
Linux进程间通信--进程,信号,管道,消息队列,信号量,共享内存 参考:<linux编程从入门到精通>,<Linux C程序设计大全>,<unix环境高级编程> ...
- 鸿蒙内核源码分析(消息队列篇) | 进程间如何异步传递大数据 | 百篇博客分析OpenHarmony源码 | v33.02
百篇博客系列篇.本篇为: v33.xx 鸿蒙内核源码分析(消息队列篇) | 进程间如何异步传递大数据 | 51.c.h .o 进程通讯相关篇为: v26.xx 鸿蒙内核源码分析(自旋锁篇) | 自旋锁 ...
- 初试kafka消息队列中间件二(采用java代码收发消息)
初试kafka消息队列中间件二(采用java代码收发消息) 上一篇 初试kafka消息队列中间件一 今天的案例主要是将采用命令行收发信息改成使用java代码实现,根据上一篇的接着写: 先启动Zooke ...
- Windows消息理解(系统消息队列,进程消息队列,非队列消息)
// ====================Windows消息分类==========================在Windows中,消息分为以下三类:标准消息——除WM_COMMAND之外,所 ...
- 通过队列实现进程间的通信(使用阻塞方式调用func函数)
#_author:来童星#date:2019/12/17#通过队列实现进程间的通信from multiprocessing import Poolimport osimport timedef fun ...
- 消息队列(七)--- RocketMQ延时发送和消息重试(半原创)
本文图片和部分总结来自于参考资料,半原创,侵删 问题 Rocketmq 重试是否有超时问题,假如超时了如何解决,是重新发送消息呢?还是一直等待 假如某个 msg 进入了重试队列(%RETRY_XXX% ...
- Python并发编程03 /僵孤进程,孤儿进程、进程互斥锁,进程队列、进程之间的通信
Python并发编程03 /僵孤进程,孤儿进程.进程互斥锁,进程队列.进程之间的通信 目录 Python并发编程03 /僵孤进程,孤儿进程.进程互斥锁,进程队列.进程之间的通信 1. 僵尸进程/孤儿进 ...
- 多任务-python实现-使用队列完成进程间的通信(2.1.8)
@ 目录 1.为什么要使用队列 2.python代码实现 1.为什么要使用队列 进程之间是互相独立的,而线程能够共享全局变量 所以如果进程间想要交换数据的话 只有通过进程间的通信,比如socket.太 ...
- Windows进程间通讯(IPC)----消息队列
消息队列 windows系统是通过消息驱动的,每移动一下鼠标,点击一下屏幕都会产生一个消息.这些消息会先被放在windows的一个系统消息队列(先进先出)中,windows系统会为每一个GUI线程创建 ...
随机推荐
- (转)mysql -prompt选项
mysql -prompt选项 原文:http://www.cnblogs.com/abclife/p/5632826.html 使用-pormpt修改提示符.可以在登录时或者在登录后使用prompt ...
- tomcat监控工具probe
probe官网:http://www.lambdaprobe.org/ 但是已经链接至github了:https://github.com/psi-probe/psi-probe 下载psi-prob ...
- js中in关键字的用法
1. 在For...In 声明用于对数组或者对象的属性进行循环/迭代操作. 例子:var a = new Array; for(x in a){ console.log(x); } 2. 判断对象是否 ...
- 搭建nginx代理,为前端页面跨域调用接口
前端同学因开发需要,本地搭建的服务需要调用其它域名的接口,在帮助正确配置后,已能正常使用. 这里写一篇博客,记录一下. 前端页面地址为127.0.0.1:9813/a.html 接口地址http:// ...
- [转]WxEmojiView
本文转自:https://github.com/icindy/WxEmojiView 来源信息 author: Di (微信小程序开发工程师) organization: WeAppDev(微信小程序 ...
- PHP项目学习——控件
主要是在项目学习中总结的一些东西 动态效果 flashbar滚动条,增加动态效果,直接嵌入html中 <!--flash滚动条--> <object classid="cl ...
- String.IsNullOrEmpty 与 String.IsNullOrWhiteSpace
String.IsNullOrEmpty 指示指定的字符串是否为 null 或者 空字符串: 返回值:如果参数为 null 或者 空字符串("" .String.Empty),结果 ...
- golang rpc 简单范例
RPC(Remote Procedure Call Protocol)--远程过程调用协议,它是一种通过网络从远程计算机程序上请求服务,而不需要了解底层网络技术的协议. 它的工作流程如下图: go ...
- HDU 2045 RPG难题
http://acm.hdu.edu.cn/showproblem.php?pid=2045 这道题也是用倒推: 先假设前n-2个块都已经涂好,涂第n-1块时有以下两种情况: 1.n-1和1相同,则n ...
- 使用Mac自带svn搭建服务器,并使用idea进行连接
一.检查Mac自带SVN版本号 二.创建代码仓库 $ mkdir -p /Users/Shared/svn/repository $ svnadmin create /Users/Shared/svn ...