1. 程式人生 > >2.3 進程間通信

2.3 進程間通信

它的 height todo 臨界區 另一個 一段 cal 簡單的 有一個

2.3.1 競爭條件

  舉個栗子:有兩個進程同時對同一內存或磁盤上的文件進行讀寫,那麽假設進程A先讀了一段,此時內核調度讓進程B進行寫,那麽下一次A讀的就不是原來的數據了。類似這樣的情況,兩個或多個進程同時讀寫某些共享數據,而最後的結果取決於進程運行的精確時序,稱為競爭條件。

2.3.2 臨界區

  我們要找出某種途徑來阻止多個進程同時讀寫數據,即以某種手段來確保當一個進程在使用共享數據時,其他進程不能做相同的操作,所以我們需要的是互斥(mutual exclusion)。運用抽象的思想:我們把對內存進行訪問的程序片段稱為臨界區(critical region)。所以一個好的方案要滿足一下的條件:

  1.任何兩個進程不能同時進入臨界區  2.不能對cpu速度和數量做任何的假設。

  3.臨界區外進行的進程不能阻塞其他進程 4.不能使進程無限期等待進入臨界區。

  如下圖:

技術分享圖片

2.3.3 忙等待的互斥

  有幾種實現互斥的方案,如下:

  1.屏蔽中斷  

  當進程進入臨界區時,讓內核不進行上下文的切換,讓cpu單獨為這個進程服務,當然這是最簡單的想法也是最不現實的。

  2.鎖(lock)變量  

  進程有一個共享鎖變量,初始值為0,表示進程可以進入臨界區,然後修改值為1,其他進程想要進入臨界區時先訪問這個鎖變量,如果值為1則切換其他線程。雖然比上一個方法解決了運行多個進程的功能,然而也有缺陷:假設進程A此刻讀鎖變量為0,不巧的是來不及修改鎖變量,切換到另一個進程B,進程B也發現了鎖變量為0,它即認為可以進入臨界區。此時就會導致兩個進程同時讀寫。

  3.嚴格輪換法

  這個方法只適用於兩個進程。假設有一個變量turn(稱為自旋鎖spin lock),它的值用來記錄何時輪到某個進程執行。當turn=0時A進程進入臨界區,=1時B進程進入臨界區。雖然這個方法避免了兩個進程同時進入臨界區,可是當A進程需要很多的cpu時間,那麽這就會一直阻塞B進程的執行,所以違反了規則3:臨界區外的運行的進程不得阻塞其他進程。如下圖: 技術分享圖片

  4.Peterson 解法

  避免了嚴格輪換,如下圖:

技術分享圖片

//TODO

2.3 進程間通信