學(xué)習(xí)啦 > 學(xué)習(xí)電腦 > 操作系統(tǒng) > 操作系統(tǒng)基礎(chǔ)知識 > Linux操作系統(tǒng)的信號量詳細(xì)解釋

Linux操作系統(tǒng)的信號量詳細(xì)解釋

時間: 佳洲1085 分享

Linux操作系統(tǒng)的信號量詳細(xì)解釋

  Linux操作系統(tǒng)信號量是進(jìn)程間通信的方法之一。下面由學(xué)習(xí)啦小編為大家整理了Linux操作系統(tǒng)的信號量詳細(xì)解釋的相關(guān)知識,希望對大家有幫助!

  Linux操作系統(tǒng)的信號量詳細(xì)解釋一、什么是信號量

  為了防止出現(xiàn)因多個程序同時訪問一個共享資源而引發(fā)的一系列問題,我們需要一種方法,它可以通過生成并使用令牌來授權(quán),在任一時刻只能有一個執(zhí)行線程訪問代碼的臨界區(qū)域。臨界區(qū)域是指執(zhí)行數(shù)據(jù)更新的代碼需要獨(dú)占式地執(zhí)行。而信號量就可以提供這樣的一種訪問機(jī)制,讓一個臨界區(qū)同一時間只有一個線程在訪問它,也就是說信號量是用來調(diào)協(xié)進(jìn)程對共享資源的訪問的。

  信號量是一個特殊的變量,程序?qū)ζ湓L問都是原子操作,且只允許對它進(jìn)行等待(即P(信號變量))和發(fā)送(即V(信號變量))信息操作。最簡單的信號量是只能取0和1的變量,這也是信號量最常見的一種形式,叫做二進(jìn)制信號量。而可以取多個正整數(shù)的信號量被稱為通用信號量。這里主要討論二進(jìn)制信號量。

  Linux操作系統(tǒng)的信號量詳細(xì)解釋二、信號量的工作原理

  由于信號量只能進(jìn)行兩種操作等待和發(fā)送信號,即P(sv)和V(sv),他們的行為是這樣的:

  P(sv):如果sv的值大于零,就給它減1;如果它的值為零,就掛起該進(jìn)程的執(zhí)行

  V(sv):如果有其他進(jìn)程因等待sv而被掛起,就讓它恢復(fù)運(yùn)行,如果沒有進(jìn)程因等待sv而掛起,就給它加1.

  舉個例子,就是兩個進(jìn)程共享信號量sv,一旦其中一個進(jìn)程執(zhí)行了P(sv)操作,它將得到信號量,并可以進(jìn)入臨界區(qū),使sv減1。而第二個進(jìn)程將被阻止進(jìn)入臨界區(qū),因?yàn)楫?dāng)它試圖執(zhí)行P(sv)時,sv為0,它會被掛起以等待第一個進(jìn)程離開臨界區(qū)域并執(zhí)行V(sv)釋放信號量,這時第二個進(jìn)程就可以恢復(fù)執(zhí)行。

  Linux操作系統(tǒng)的信號量詳細(xì)解釋三、Linux的信號量機(jī)制

  Linux提供了一組精心設(shè)計(jì)的信號量接口來對信號進(jìn)行操作,它們不只是針對二進(jìn)制信號量,下面將會對這些函數(shù)進(jìn)行介紹,但請注意,這些函數(shù)都是用來對成組的信號量值進(jìn)行操作的。它們聲明在頭文件sys/sem.h中。

  1、semget函數(shù)

  它的作用是創(chuàng)建一個新信號量或取得一個已有信號量,原型為:

  [cpp] view plain copy print?

  int semget(key_t key, int num_sems, int sem_flags);

  第一個參數(shù)key是整數(shù)值(唯一非零),不相關(guān)的進(jìn)程可以通過它訪問一個信號量,它代表程序可能要使用的某個資源,程序?qū)λ行盘柫康脑L問都是間接的,程序先通過調(diào)用semget函數(shù)并提供一個鍵,再由系統(tǒng)生成一個相應(yīng)的信號標(biāo)識符(semget函數(shù)的返回值),只有semget函數(shù)才直接使用信號量鍵,所有其他的信號量函數(shù)使用由semget函數(shù)返回的信號量標(biāo)識符。如果多個程序使用相同的key值,key將負(fù)責(zé)協(xié)調(diào)工作。

  第二個參數(shù)num_sems指定需要的信號量數(shù)目,它的值幾乎總是1。

  第三個參數(shù)sem_flags是一組標(biāo)志,當(dāng)想要當(dāng)信號量不存在時創(chuàng)建一個新的信號量,可以和值IPC_CREAT做按位或操作。設(shè)置了IPC_CREAT標(biāo)志后,即使給出的鍵是一個已有信號量的鍵,也不會產(chǎn)生錯誤。而IPC_CREAT | IPC_EXCL則可以創(chuàng)建一個新的,唯一的信號量,如果信號量已存在,返回一個錯誤。

  semget函數(shù)成功返回一個相應(yīng)信號標(biāo)識符(非零),失敗返回-1.

  2、semop函數(shù)

  它的作用是改變信號量的值,原型為:

  [cpp] view plain copy print?

  int semop(int sem_id, struct sembuf *sem_opa, size_t num_sem_ops);

  sem_id是由semget返回的信號量標(biāo)識符,sembuf結(jié)構(gòu)的定義如下:

  [cpp] view plain copy print?

  struct sembuf{

  short sem_num;//除非使用一組信號量,否則它為0

  short sem_op;//信號量在一次操作中需要改變的數(shù)據(jù),通常是兩個數(shù),一個是-1,即P(等待)操作,

  //一個是+1,即V(發(fā)送信號)操作。

  short sem_flg;//通常為SEM_UNDO,使操作系統(tǒng)跟蹤信號,

  //并在進(jìn)程沒有釋放該信號量而終止時,操作系統(tǒng)釋放信號量

  };

  3、semctl函數(shù)

  該函數(shù)用來直接控制信號量信息,它的原型為:

  [cpp] view plain copy print?

  int semctl(int sem_id, int sem_num, int command, ...);

  如果有第四個參數(shù),它通常是一個union semum結(jié)構(gòu),定義如下:

  [cpp] view plain copy print?

  union semun{

  int val;

  struct semid_ds *buf;

  unsigned short *arry;

  };

  前兩個參數(shù)與前面一個函數(shù)中的一樣,command通常是下面兩個值中的其中一個

  SETVAL:用來把信號量初始化為一個已知的值。p 這個值通過union semun中的val成員設(shè)置,其作用是在信號量第一次使用前對它進(jìn)行設(shè)置。

  IPC_RMID:用于刪除一個已經(jīng)無需繼續(xù)使用的信號量標(biāo)識符。

3637944