进程以及进程通信(IPC)类型
这里用我有限的知识来解释同时参考了一些其他博主的子类,希望能给与一部分入门的朋友一个清晰的理解,有问题之处还请指出
首先简单谈一下什么是进程?
答:进程是装入内存运行的程序段,是许多的系统对象拥有权的集合,换句大家经常引用的话说进程是资源分配的基本单位。
举例来说,我们的浏览器程序存放在C盘的某个位置,这时它只是硬盘上的程序。每次我们打开一个浏览器的时候,这个程序就会被装入内存中去,进行一系列初始化(进程控制块PCB的初始化,包括进程计数器,进程状态,CPU命令,寄存器等等)。此时我们看到了浏览器打开并显示网页,此时这就是一个运行中的进程,我们可以打开任务管理器看到许许多多运行的进程。
为什么说进程拥有许多系统对象?
答:刚才说了,进程是装入内存的程序段,那进程的运行势必涉及到内存的分配(包括堆栈,文本区,数据区等,这里是参考了C语言程序的内存分配),而进程所占用的内存中就可能会有文件句柄,DLL模块(在可执行程序运行时才载入内存的代码),上下文等。
这里,我们顺便说一下线程,大家记住线程是CPU运行调度的基本单位,线程必须被包含在进程中,一个进程可以有很多线程(至少有一个),这些线程共享进程的许多资源(如栈,寄存器)。(关于进程与线程的优缺点,多线程的东西会在之后的博客里写)。
什么是进程通信?为什么要通信?
答:进程通信(IPC),即Inter-ProcessCommunication,字面上理解就是进程之间的通信。
层模型)传输到另一台机器的socket,最后服务器获取到该信息,实现进程间通信。一句话说,A主机的浏览器通过socket与另一台B主机的进程进行通信交流。
进程属于内核的基本功能,所以不同的操作系统在实现进程通信有一定的区别,不过想通之处也还是很多的。
其实,可能有很多同学和朋友和我一开始理解的一样,认为IPC只有消息传递和共享内存两种(没错,操作系统书上就是这么写的),可后来我发现消息传递具体是什么,有什么特点,我都说不太清~所以稍微研究了下
我们可以这样理解:
IPC只是按形式上可以分为消息传递,共享内存,同步。
(下面是用linux的IPC举例)
消息传递就包括,管道,FIFO命名管道,消息队列
共享内存,包括匿名与具名的,
同步,包括互斥量,读写锁,信号量等。
我们可以把每一种IPC都拿出来单独作比较。
首先先大致说一下共享内存,管道的概念:
其原理就是将一份物理内存映射到不同进程各自的虚拟地址空间,使每一个进程都可以读取这份数据,来实现通信,因为是直接通过内存操作,所以是一种非常高效的通信方式。
管道(Pipe)是一种具有两个端点的通信通道:有一端句柄的进程可以和有另一端句柄的进程通信。管道可以是单向-一端是只读的,另一端点是只写的;也可以是双向的一—管道的两端点既可读也可写。
下面简单介绍一下Windows与Linux的进程通信以及比较:(这里主要参考了 coolmeme 的博客)
Windows:
1. 文件映射:
文件映射(Memory-Mapped Files)能使进程把文件内容当作进程地址区间一块内存那样来对待。因此,进程不必使用文件I/O操作(正常来说需要用输入输出流来读写文件ioStream),只需简单的指针操作就可读取和修改文件的内容。
Win32API允许多个进程访问同一文件映射对象,各个进程在它自己的地址空间里接收内存的指针。通过使用这些指针,不同进程就可以读或修改文件的内容,实现了对文件中数据的共享。
注意:文件映射是在多个进程间共享数据的非常有效方法,有较好的安全性。但文件映射只能用于本地机器的进程之间,不能用于网络中,而开发者还必须控制进程间的同步。
2. 共享内存:
Win32API中共享内存(SharedMemory)实际就是文件映射的一种特殊情况。进程在创建文件映射对象时用0xFFFFFFFF来代替文件句柄(HANDLE),就表示了对应的文件映射对象是从操作系统页面文件访问内存,其它进程打开该文件映射对象就可以访问该内存块。
3. 匿名管道:
匿名管道(Anonymous Pipe)是在父进程和子进程之间,或同一父进程的两个子进程之间传输数据的无名字的单向管道。通常由父进程创建管道,然后由要通信的子进程继承通道的读端点句柄或写端点句柄,然后实现通信。父进程还可以建立两个或更多个继承匿名管道读和写句柄的子进程。这些子进程可以使用管道直接通信,不需要通过父进程。
4. 命名管道:
FIFO,先进先出的通信方式。
命名管道(Named Pipe)是服务器进程和一个或多个客户进程之间通信的单向或双向管道。不同于匿名管道的是命名管道可以在不相关的进程之间和不同计算机之间使用,服务器建立命名管道时给它指定一个名字,任何进程都可以通过该名字打开管道的另一端,根据给定的权限和服务器进程通信。
5. 动态链接库
DLL解释:与动态链接库连接的可执行文件只包含它需要的函数的引用表,而不是所有的函数代码,只有在程序执行时, 那些需要的函数代码才被拷贝到内存中,这样就使可执行文件比较小, 节省磁盘空间,操作系统使用虚拟内存,使得一份DLL驻留在内存中被多个程序使用,节省内存;
Win32动态连接库(DLL)中的全局数据可以被调用DLL的所有进程共享,这就又给进程间通信开辟了一条新的途径,当然访问时要注意同步问题。
6. 远程调用RPC
Win32 API提供的远程过程调用(RPC)使应用程序可以使用远程调用函数,这使在网络上用RPC进行进程通信就像函数调用那样简单。RPC既可以在单机不同进程间使用也可以在网络中使用。
7. Socket
刚才我们举例子简单说明了socket(套接字)的作用,我们要知道目前socket是一种非常流行的网络通信手段。
WindowsSockets规范是以U.C.Berkeley大学BSD
UNIX中流行的Socket接口为范例定义的一套Windows下的网络编程接口。除了Berkeley
Socket原有的库函数以外,还扩展了一组针对Windows的函数,使程序员可以充分利用Windows的消息机制进行编程。
8. 剪贴板
Windows剪贴板应该算是一种比较简单开销小的IPC,内置在windows并使用系统的内部资源RAM,或者虚拟内存类临时保存剪切和复制的信息,系统预留的一块全局共享内存,用来暂存在各进程间进行交换的数据:提供数据的进程创建一个全局内存块,并将要传送的数据移到或复制到该内存块;接受数据的进程(也可以是提供数据的进程本身)获取此内存块的句柄,并完成对该内存块数据的读取。这里有一点疑问,我认为剪贴板并不是把所有的信息复制到那个内存,而是把路径等信息存入再进行拷贝(这里希望有大神给解释一下。。。)。
9. WM_COPYDATA消息
当一个应用向另一个应用传送数据时,发送方只需使用调用SendMessage函数,参数是目的窗口的句柄、传递数据的起始地址、WM_COPYDATA消息。接收方只需像处理其它消息那样处理WM_COPY
DATA消息,这样收发双方就实现了数据共享。WM_COPYDATA消息无疑是一种经济实惠的一中方法
Linux:
1. 管道:
与上述windows的管道类似,也分为匿名与有名字的管道。管道可用于具有亲缘关系进程间(父子,兄弟进程)的通信,有名管道克服了管道没有名字的限制,允许不同无亲缘关系的进程通信。
2. 信号(signal):
信号是比较复杂的通信方式,用于通知接受进程有某种事件发生,除了用于进程间通信外,进程还可以发送信号给进程本身;linux除了支持Unix早期信号语义函数sigal外,还支持语义符合Posix.1标准的信号函数sigaction
3. 报文(Message)队列(消息队列):
消息队列是消息的链接表,包括Posix消息队列system V消息队列。有足够权限的进程可以向队列中添加消息,被赋予读权限的进程则可以读走队列中的消息,注意消息队列是创建文件方式建立,所以即使添加消息的进程结束,保存在消息队列的消息也不会消失。
消息队列克服了信号承载信息量少,管道只能承载无格式字节流以及缓冲区大小受限等缺点。
4. 共享内存:
上面描述了基本原理,往往与其它通信机制,如信号量结合使用,来达到进程间的同步及互斥。
5. 信号量(semaphore):
主要作为进程间以及同一进程不同线程之间的同步手段。(线程间通信业经常使用信号量)
信号量是一个特殊的变量,只能对其进行初始化,PV以及删除操作(这里涉及到同步与锁的一些内容,可以查一下)。
6. 套接字(Socket):
上面描述过,可用于不同机器之间的进程间通信。
对几种IPC的简单比较:
1. 管道,速度较慢,缓冲区大小受限,只能承载无格式的字节流。只能用于有亲缘关系的进程。
2. FIFO管道,任何进程间都可以通信,包括不同机器上的管道,速度较慢。
3. 消息队列:因为位于内核中,所以容量受限,第一次读取时要注意上次添加的消息是否读取。
4. 信号量:不能传递复杂的消息,只用于同步信息。
5. 共享内存:能很容易的控制变量,速度快,要注意读写安全性,避免死锁等。
上面的每一种通信机制都有很大的研究价值,如果大家想详细了解,还需要进一步去研究。
进程以及进程通信(IPC)类型的更多相关文章
- python进程、进程池(二)代码部分
第一种创建进程的方式: from multiprocessing import Process def f(name): print(name,"在子进程") if __name_ ...
- day 28 :进程相关,进程池,锁,队列,生产者消费者模式
---恢复内容开始--- 前情提要: 一:进程Process 1:模块介绍 from multiprocessing import Process from multiprocessing impo ...
- 【Chromium中文文档】跨进程通信 (IPC)
跨进程通信 (IPC) 转载请注明出处:https://ahangchen.gitbooks.io/chromium_doc_zh/content/zh//General_Architecture/I ...
- 《Python》进程之间的通信(IPC)、进程之间的数据共享、进程池
一.进程间通信---队列和管道(multiprocess.Queue.multiprocess.Pipe) 进程间通信:IPC(inter-Process Communication) 1.队列 概念 ...
- Python之网路编程之-互斥锁与进程间的通信(IPC)及生产者消费者模型
一.互斥锁 进程之间数据隔离,但是共享一套文件系统,因而可以通过文件来实现进程直接的通信,但问题是必须自己加锁处理. 注意:加锁的目的是为了保证多个进程修改同一块数据时,同一时间只能有一个修改,即串行 ...
- c# IPC实现本机进程之间的通信
IPC可以实现本地进程之间通信.这种用法不是太常见,常见的替代方案是使用wcf,remoting,web service,socket(tcp/pipe/...)等其他分布式部署方案来替代进程之间的通 ...
- linux进程篇 (三) 进程间的通信3 IPC通信
3 IPC通信 用户空间 进程A <----无法通信----> 进程B -----------------|--------------------------------------|- ...
- Python 35 进程间的通信(IPC机制)、生产者消费者模型
一:进程间的通信(IPC):先进先出 管道:队列=管道+锁 from multiprocessing import Queue q=Queue(4) q.put(['first',],block=T ...
- Linux 线程与进程,以及通信
http://blog.chinaunix.net/uid-25324849-id-3110075.html 部分转自:http://blog.chinaunix.net/uid-20620288-i ...
随机推荐
- IT 达人
1. 手机与电脑多屏互动 [教程]华为多屏互动功能与PC win7的连接 要求手机和电脑必须在同一局域网内,且手机必须支持多屏互动功能. 操作步骤如下: PC 端: services.msc,启动下面 ...
- [OpenGL]OpenGL坐标系和坐标变换
OpenGL通过摄像机的模拟.要实现一个三维计算机图形重大转变,这是几何变换(模型转换-查看转型(两者统称为几何变换)).投影.作物转型.口变换等.同一时候,OpenGL还实现了矩阵堆栈等.理解掌握了 ...
- 《Silk》(皇家律师)—— 英美海洋法系
Abortion Act:堕胎法: 1. 表达习惯 we employ him, not the other way round, Officially,-,官方的说法是,Unofficially,- ...
- poj 2763 Housewife Wind(树链拆分)
id=2763" target="_blank" style="">题目链接:poj 2763 Housewife Wind 题目大意:给定一棵 ...
- ./configure,make,make install的作用(configure一般用来生成 Makefile,相当于qmake)
这些都是典型的使用GNU的AUTOCONF和AUTOMAKE产生的程序的安装步骤. ./configure是用来检测你的安装平台的目标特征的.比如它会检测你是不是有CC或GCC,并不是需要CC或GCC ...
- CCPlace,CCFlip*,CCToggleVisibility,CCMoveTo*,CCJumpTo*,CCScale*,CCRotate*,CCSkew*,fade,CCCardinalSp*
1 CCAction动作 CCAction作为一个基类.事实上质是一个接口(即抽象类),由它派生的实现类(如运动和转动等)才是我们实际使用的动作.CCAction 的绝大多数实现类都派生自CCF ...
- 好用的Markdown 编辑器及工具
Markdown 是 2004 年由 John Gruberis 设计和开发的纯文本格式的语法,所以通过同一个名字它可以使用工具来转换成 HTML.readme 文件,在线论坛编写消息和快速创建富文本 ...
- ThreadPool类(线程池)
原文:ThreadPool类(线程池) CLR线程池并不会在CLR初始化时立即建立线程,而是在应用程序要创建线程来运行任务时,线程池才初始化一个线程.线程池初始化时是没有线程的,线程池里的线程的初始化 ...
- .net core 允许跨域
在Startup的ConfigureServices()中添加services.AddCors()在Startup的Configure()中添加app.UseCors(); 保证其在app.UseMv ...
- IdentityServer学习目录
IdentityServer IdentityServer的基本概念与特性 IdentityServer流程图与相关术语 最简单的IdentityServer实现 最简单的IdentityServer ...