操作系统入门 – 进程的通信方式
1.什么是进程通信
1.1 定义
进程通信就是在不同进程之间交换信息。在之前文章中可以了解到,进程之间相互独立,一般不可能互相访问。因此进程之间若需要通信,则需要一个所有进程都认可的共享空间,而这个空间就是内存区以及系统空间。总的来说,进程通信就是一组编程接口,可以让开发人员协调不同进程,使之能在一个操作系统里同时运行,并相互传递、交换信息。
1.2 进程通信的意义
有些复杂的程序需要多个进程协同完成某些具体任务,因此进程之间就需要互相通信实现数据的交换和访问。整个系统执行任务的最小粒度就是进程,这样可以提升系统性能以及安全性。此外在之前讲解进程也提过,多进程应用比多线程引用更加壮硕。
2.进程通信方式
在该节将会讲解进程之间的通信方式。
2.1 管道通信
2.1.1 管道通信的概念
管道通信中所谓管道就是一个用于连接读进程和写进程的数据缓冲区。写进程通过将数据以字节流的方式向管道中发送,而接收端使用读进程读取管道中的数据即可实现信息交换。为了协调双方的通信,管道需要提供 同步、互斥 和 确定对方存在 的协调能力,其目的是为了让进程同步。
2.1.2 管道通信的性质
在管道中数据读取是一次性的,即数据被读取后将会被删除,以释放管道空间。同时在某一时刻管道内的数据只能单向传输,即某一时刻只能读或只能写。目前,管道通信类似于生产者-消费者模型,即当管道内写入一定数据时,即可读出。而单向传输决定了进程之间的性质,只有亲缘关系的进程才会使用管道通信。
2.2 消息队列
2.2.1 消息队列概念
消息队列在发送数据时会按照一个个的消息体进行发送,每个消息体都规定了大小,收发双方约定好一种消息类型。相比于字节流的无格式方式,消息队列允许不同进程以消息队列的形式发送给 任意 进程,而进程之间的数据交换也是格式化的消息。若通信进程之间不存在可以直接访问的共享空间,则必须利用 操作系统 提供的消息传递方法实现通信,进程通过系统提供的发送消息和接收消息两个原语进行数据交换。
2.2.2 消息队列通信的性质
- 直接通信方式:发送进程直接把数据发送至接收进程,并把数据挂到接收进程的消息队列中,接收进程从自己的消息队列中获得消息
- 间接通信方式:发送进程把消息发送到实体中间件,接收进程再从中间件中获取。
2.3 共享内存
2.3.1 共享内存概念
在使用消息队列时如果数据量较大则数据的收发会产生一定的延迟,因此使用共享内存可以解决收发速度较慢的问题。
进程在运行时需要有自己的虚拟空间,而这些虚拟空间将会映射到不同的物理内存中。共享内存通过申请一块虚拟地址空间,让不同进程的虚拟地址空间映射到同一物理空间,即可实现数据的共享。
2.4 信号量
多进程使用共享内存,但若果所有进程读或写则会导致数据混乱,因此需要有一个约束,这就是之间进程同步与互斥中讲到的信号量。目的是为了防止读写冲突。信号量定义了两种操作,p操作和v操作,p操作为申请资源,会将数值减去M,表示这部分被他使用了,其他进程暂时不能用。v操作是归还资源操作,告知归还了资源可以用这部分。
2.5 套接字
与网络连接类似,基于socket连接的进程需要有一个专门负责监听的进程(服务进程)若进程之间想通信则调用监听进程,并开始TCP或UDP连接。当数据交换完成后结束通信,下次数据交换时则继续建立新的连接。