以下爲看視頻筆記..........
1. 例子說明互斥量
我們來看一個生活中的例子:現在大多銀行ATM機都有一個特製的鐵門。需要使用ATM的用戶都需要在門前排隊,進入鐵門]使用ATM機的用戶進入後會在裏面將鐵門鎖住,以保障自身安全,這個時候,在門外排隊的用戶無法使用.ATM機;
當之前鎖住ATM鐵門的用戶辦理完業務,打開門以後,其他在外排隊的用戶纔可以進入鐵門使用ATM,這位進入鐵門的用戶也會和前一個用戶一樣,將門鎖住,保障自身的安全。
例子中ATM機就相當於系統中的共享資源,需要使用ATM的用戶相當於系統中的線程,而鐵門,就起到了互斥量的作用。
2. 互斥量工作機制
互斥量 (互斥鎖)是用於線程間互斥訪問的IPC對象,它是一種特殊的 二值性信號量。當某個線程訪問系統中的共享資源時,通過引入互斥量機制,可以保證其他線程無法取得對此共享資源的訪問權。
互斥量只有兩種狀態: LOCKED和UNLOCKED, 分別代表加鎖和開鎖的兩種情況。當有線程持有它時,互斥量處於閉鎖狀態,由這個線程獲得它的所有權。相反,當這個線程釋放它時,將對互斥量進行開鎖,失去對它的所有權。當一個線程持有互斥量時,其他線程將不能夠對它進行開鎖或持有它。持有該互斥量的線程也能夠再次獲得這個“鎖”(遞歸持有)而不被掛起
3. 互斥量控制塊
在RT—Thread中,互斥量控制塊是操作系統用於管理互斥量的一個數據結構。
struct rt_mutex
{
struct rt_ipc_object parent;
rt_uint16_t value; //只有兩種狀態,上鎖和解鎖
rt_uint8_t original_priority; //保存上一次線程擁有互斥量的優先級
rt_uint8_t hold; //保存某個線程擁有這個互斥量的次數
struct rt_thread *owner; //owner指向當前擁有這個互斥量的線程控制塊
}
定義靜態互斥量: struct rt_mutex static_mutex
定義動態互斥量:rt_mutex_t dynamic_mutex //rt_mutex_t 是struct rt_mutex的指針。
4.互斥量的操作
初始化與脫離,這組API是針對靜態互斥量的,
rt_err_t rt_mutex_init(rt_mutex_t,const char *name,rt_uint8_t flag) //對靜態互斥量初始化,就是把互斥量加入到系統的對象管理器中,其中flag可爲RT_IPC_FLAG_FIFO,RT_IPC_FLAG_PRIO,即決定線程獲取互斥量的方式.
rt_err_t rt_mutex_detach(rt_mutex_t mutex) //從系統對象管理器中移除
創建與刪除,這組API是針對動態互斥量的,
rt_mutex_t rt_mutex_create(const char *name,rt_uint8_t flag)
rt_err_t rt_mutex_delete(rt_mutex_t mutex)
獲取互斥量,也稱爲互斥量的加鎖操作;當線程申請互斥量時,互斥量已經被使用,則線程等待時間time,等待時間超過time返回-RT_TIMEOUT,可用 RT_WAITING_FOREVER永久等待,其值爲=-1
rt_err_t rt_mutex_take(rt_mutex_t rt_int32_t time)
釋放互斥量
rt_err_t rt_mutex_release(rt_mutex_t mutex)//只有先獲取互斥量後才能釋放,
注意互斥量屬於線程,rt_mutex_take()和rt_mutex_release()都只能在線程中使用,不能在中斷中調用。
信號量可以在中斷中釋放信號量的
5. 實例
在mutex_sample.c中
6. 信號量VS互斥量
1、信號量可以由任何線程(以及中斷)釋放,它用於同步的時候就像交通燈,線程只有在獲得許可的時候纔可以運行,強調的是運行步驟;
斥量只能由持有它的線程釋放,即只有“鎖上”它的那個線程纔有“鑰匙”打開它。它用於互斥的時候就像--把鑰匙,只有獲得鑰匙的線程纔可以運行,強調的是許可和權限。
2、使用信號量可能導致線程優先級反轉,而互斥量可通過優先級繼承的方法解決優先級反轉問題