管道(有名无名),信号,信号量,消息队列,共享内存。
所谓进程间通信,就是指一个进程和另一个进程有联系,不仅仅指传递消息,还包括其他操作,有简单也有复杂。不过他们使用的方法是基本相同的。信号和信号量是两种不同的方式,他们都可以用来实现同步和互斥,但前者是使用信号处理器来进行的,后者是使用pv操作来实现的。消息队列是一种比较高级的进程间通信的方法,可以使用其来传递消息。
一个消息队列可以被多个进程所共享,如果一个进程消息太多,一个消息队列放不下,也可以用多个消息队列。共享消息队列的进程所发送的消息除了消息本身外,还有一个标志,这个标志该消息将由哪个进程或者哪类进程接收。每一个共享消息队列的进程针对这个队列也有自己的标志,可以用来声明自己的身份。
两者的主要区别是mutex可以用于进程之间的互斥,critical section适用于线程间的互斥。
四,考察进程的调度 短作业优先代表最短剩余时间优先 可剥夺式处理机&不可剥夺式处理机
首先来分析死锁,死锁是指两个或两个以上的进程在运行的过程中,由于争夺资源而产生的一种互相等待的状态。若无外力作用,它们都将无法推进下去,此时称系统陷入了死锁状态或者说进程产生了死锁。
产生死锁的四个必要条件如下:
这四个条件是死锁的必要条件,只要系统发生死锁,这些条件必然成立,而只要上述条件之一不满足,就不会发生死锁。
死锁的解除与预防方法如下:
首先,对于资源的分配要予以合理的规划,防止进程在处于等待状态之下占用资源,在系统运行过程中,对于进程对系统发出的每一个可以满足的资源请求进行动态检查,并根据检查结果决定是否分配资源,若分配资源后可能发生死锁,则不予分配。
根据以上四条必要条件,只要破坏其中一条,就可以避免产生死锁,因此有如下三种预防措施:
这里注意一点,互斥条件无法被破坏!
避免死锁算法最有代表性的是Dijkstra E.W 于1968年提出的银行家算法,该算法需要检查申请者对资源的最大需求量,如果系统现存的各类资源可以满足申请者的请求,就满足申请者的请求。这样申请者就可以很快完成其计算,然后释放它占用的资源,从而保证系统中所有进程都能完成,进而避免死锁的发生。
fork()函数可以复制一个子进程,子进程复制了父进程的绝大部分,栈,缓冲区等。系统为子进程创建一个新的页表项,其中进程ID与父进程的进程id不同,父进程的返回值是子进程的进程id,子进程的返回值为0;虽然父子进程共享代码空暗间,但是在涉及代码写数据时子进程有着自己的数据空间。在子进程进行修改时,系统会为子进程申请新的页面。
就绪(Ready):程序获得了运行所需要的所有资源,只要获得处理机便可以执行,此时程序处于就绪状态。
运行(Running):当进程获得处理机,程序正在处理机上执行,,此时进程的状态处于执行状态。
阻塞(Blocked):在处理机上运行的程序,由于等待某个事件发生而无法执行时,便放弃处理机而处于阻塞状态。引起进程组的事件有很多种,例如,等待I/O完成,申请缓冲区不能满足,等待信号等。
若系统中有五台绘图仪,有多个进程需要使用两台,规定每个进程一次仅允许申请一台,则至多允许()个进程参与竞争,而不会发生死锁?
哲学家就餐问题:资源(餐叉)按照某种规则编号为1-5,每个工作单元(哲学家)总是先拿起左右两边编号较低的餐叉,再拿编号较高的餐叉,用完餐叉后,他总是先放下编号较高的,再放下编号较低的。在这种情况下,当四位哲学家同时拿起他们手边编号较低的餐叉时,只有编号最高的餐叉留在桌子上,从而第五位哲学家就不能使用任何一只餐叉了。
(整理自程序员面试宝典)