2012-03-30 92 views
0

我創建將在幾個進程和線程數,所以我創建了一個函數來實現鎖定和同步是鎖定和同步使用互斥

HANDLE WaitOnMutex(char* mt) 
{ 
    HANDLE ghMutex=NULL; 
    DWORD lastError=-1; 
    do 
    { 
     ghMutex = CreateMutex(NULL,TRUE,mt); 
     lastError= GetLastError(); 
     if(lastError!=ERROR_SUCCESS) 
     { 
      CloseHandle(ghMutex); 
      Sleep(2000); 
     } 
    } 
    while(lastError!=ERROR_SUCCESS); 
    return ghMutex; 
} 

運行相同功能的程序,我使用它像以下

HANDLE mtx=WaitOnMutex("Global\\DBG_MY_APP"); 
    //Do the work that needs sync 
    CloseHandle(mtx) 

這是鎖定此功能的正確方法嗎?或者我需要使用不同的方法..

注:我使用「全球」,因爲我的應用程序的某些部分是WINSERVICE,我需要會話隔離過程

的代碼是工作在鎖之間測試環境,但我不確定我是否以正確的方式進行

+0

您正在使用錯誤的方式。有關更多信息,請參閱此文檔。 [互斥msdn](http://msdn.microsoft.com/en-us/library/windows/desktop/ms686927%28v=vs.85%29.aspx) – rbelli 2012-03-30 17:23:38

+0

@rbelli可以告訴我什麼是我的方式錯誤? – CnativeFreak 2012-03-30 17:25:11

+1

如果我完全理解你在做什麼,你只是創建或打開互斥鎖。你沒有得到互斥體。爲此,正如我在示例中看到的,您需要調用WaitForSingleObjects函數進行檢查並獲取互斥鎖,然後調用ReleaseMutex函數釋放它。 – rbelli 2012-03-30 17:31:21

回答

4

您編碼的內容是繁忙的等待,在大多數情況下,這並不理想。不僅如此,而且你已經用重量級互斥創建並釋放了調用。

要使用已命名的互斥鎖進行跨進程同步,每個進程只應調用CreateMutex一次。然後保持互斥手柄周圍,並使用WaitForSingleObject等待它,並ReleaseMutex釋放鎖。然後,您可以在下次需要訪問受保護的資源時再次使用WaitForSingleObject將其鎖定,等等。

當你的過程完成了「永久」互斥體(例如因爲過程正在退出),那麼你可以撥打CloseHandle

+0

不錯,但首先我不認爲它忙於等待「睡眠(2000)」; 但我想你是正確的重量級互斥創建。 現在我的問題是函數CreateMutex中斷?如果是這樣,那麼我的所有工作是錯誤的,如果不是那麼我的工作是壞的表現.. – CnativeFreak 2012-03-30 17:36:17

+1

不可否認,2秒的等待不是「忙」,但它仍然是一個輪詢循環,這需要調度程序喚醒線程只是爲了檢查它是否可以獲取互斥鎖,然後再回到睡眠狀態。 – 2012-03-31 07:47:22

+1

由於計劃問題,'CreateMutex'不能「失敗」,除非創建互斥體的其他線程/進程更改訪問權限,以便您的線程/進程沒有必要的權限。如果這沒有發生,那麼你的線程創建互斥鎖,並且你得到鎖(因爲你指定了「初始所有者」標誌爲true),或者另一個線程創建了互斥鎖,並且你得到了句柄和一個'ERROR_ALREADY_EXISTS'錯誤代碼,但不是鎖。 – 2012-03-31 07:52:52

2

我想這將是一種工作,爲「工作」一個足夠寬鬆的定義。這不是我如何做這項工作。

我想我會做的事情更是這樣的:

某處一次性初始化代碼:期間

WaitForSingleObject(mutex, INFINITE); 

// write to log 

ReleaseMutex(handle); 

然後:

HANDLE mutex = CreateMutex(name); // yes, there are more parameters here. 

然後寫入日誌一次性關機代碼:

CloseHandle(mutex); 

如果你使用的是C++而不是C,你通常需要通過RAII來處理,所以你可以創建一個日誌對象,它在ctor中調用CreateMutex,並調用CloseHandle。然後你會有一個寫函數,它在ctor中執行WaitForSingleObject,在其日誌中寫入operator(),並在其dtor中執行ReleaseMutex。這使得大部分代碼相對簡單,並且只需很少的工作就可以保持異常安全。

+0

糟糕 - 看起來像安東尼打敗了我。 – 2012-03-30 17:35:10

+0

我的新問題:函數CreateMutex中斷?如果是這樣,那麼我所有的工作是錯誤的,如果不是那麼我的工作是壞的表現.. – CnativeFreak 2012-03-30 17:40:18

+0

我想這取決於你的意思是可中斷的一點點,但對你的代碼它的行爲像原子。 – 2012-03-30 17:42:13