六大进程通信机制总结( 四 )


六大进程通信机制总结

文章插图
 
如果 P2 的 “代码4” 要基于 P1 的 “代码1” 和 “代码2” 的运行结果才能执行,那么我们就必须保证 “代码4” 一定是在 “代码2” 之后才会执行 。
使用信号量和 PV 操作实现进程的同步也非常方便,三步走:
  • 定义一个同步信号量,并初始化为当前可用资源的数量
  • 在优先级较高的操作的后面执行 V 操作,释放资源
  • 在优先级较低的操作的前面执行 P 操作,申请占用资源

六大进程通信机制总结

文章插图
 
配合下面这张图直观理解下:
六大进程通信机制总结

文章插图
 
6. 信号注意!信号和信号量是完全不同的两个概念!
信号是进程通信机制中唯一的异步通信机制,它可以在任何时候发送信号给某个进程 。通过发送指定信号来通知进程某个异步事件的发送,以迫使进程执行信号处理程序 。信号处理完毕后,被中断进程将恢复执行 。用户、内核和进程都能生成和发送信号 。
信号事件的来源主要有硬件来源和软件来源 。所谓硬件来源就是说我们可以通过键盘输入某些组合键给进程发送信号,比如常见的组合键 Ctrl+C 产生 SIGINT 信号,表示终止该进程;而软件来源就是通过 kill 系列的命令给进程发送信号,比如 kill -9 1111,表示给 PID 为 1111 的进程发送 SIGKILL 信号,让其立即结束 。我们来查看一下 Linux 中有哪些信号:
六大进程通信机制总结

文章插图
 
7. Socket至此,上面介绍的 5 种方法都是用于同一台主机上的进程之间进行通信的,如果想要跨网络与不同主机上的进程进行通信,那该怎么做呢?这就是 Socket 通信做的事情了(当然,Socket 也能完成同主机上的进程通信) 。
六大进程通信机制总结

文章插图
 
Socket 起源于 Unix,原意是插座,在计算机通信领域,Socket 被翻译为套接字,它是计算机之间进行通信的一种约定或一种方式 。通过 Socket 这种约定,一台计算机可以接收其他计算机的数据,也可以向其他计算机发送数据 。
从计算机网络层面来说,Socket 套接字是网络通信的基石,是支持 TCP/IP 协议的网络通信的基本操作单元 。它是网络通信过程中端点的抽象表示,包含进行网络通信必须的五种信息:连接使用的协议,本地主机的 IP 地址,本地进程的协议端口,远地主机的 IP 地址,远地进程的协议端口
Socket 的本质其实是一个编程接口(API),是应用层与 TCP/IP 协议族通信的中间软件抽象层,它对 TCP/IP 进行了封装 。它把复杂的 TCP/IP 协议族隐藏在 Socket 接口后面 。对用户来说,只要通过一组简单的 API 就可以实现网络的连接 。
六大进程通信机制总结

文章插图
 
8. 总结简单总结一下上面六种 Linux 内核提供的进程通信机制:
1)首先,最简单的方式就是管道,管道的本质是存放在内存中的特殊的文件 。也就是说,内核在内存中开辟了一个缓冲区,这个缓冲区与管道文件相关联,对管道文件的操作,被内核转换成对这块缓冲区的操作 。管道分为匿名管道和有名管道,匿名管道只能在父子进程之间进行通信,而有名管道没有限制 。
2)虽然管道使用简单,但是效率比较低,不适合进程间频繁地交换数据,并且管道只能传输无格式的字节流 。为此消息队列应用而生 。消息队列的本质就是存放在内存中的消息的链表,而消息本质上是用户自定义的数据结构 。如果进程从消息队列中读取了某个消息,这个消息就会被从消息队列中删除 。
3)消息队列的速度比较慢,因为每次数据的写入和读取都需要经过用户态与内核态之间数据的拷贝过程,共享内存可以解决这个问题 。所谓共享内存就是:两个不同进程的逻辑地址通过页表映射到物理空间的同一区域,它们所共同指向的这块区域就是共享内存 。如果某个进程向共享内存写入数据,所做的改动将立即影响到可以访问同一段共享内存的任何其他进程 。
对于共享内存机制来说,仅在建立共享内存区域时需要系统调用,一旦建立共享内存,所有的访问都可作为常规内存访问,无需借助内核 。这样,数据就不需要在进程之间来回拷贝,所以这是最快的一种进程通信方式 。


推荐阅读