CP.21: Use std::lock() or std::scoped_lock to acquire multiple mutexes
CP.21:使用std::lock()或者std::scoped_lock獲取多個mutex
Reason(緣由)
To avoid deadlocks on multiple mutexes.git
避免在多個mutex上發生死鎖。
程序員
Example(實例)github
This is asking for deadlock:web
下面的代碼會引起死鎖:
微信
// thread 1
lock_guard<mutex> lck1(m1);
lock_guard<mutex> lck2(m2);
// thread 2
lock_guard<mutex> lck2(m2);
lock_guard<mutex> lck1(m1);
Instead, use lock():app
使用lock代替:ide
// thread 1
lock(m1, m2);
lock_guard<mutex> lck1(m1, adopt_lock);
lock_guard<mutex> lck2(m2, adopt_lock);
// thread 2
lock(m2, m1);
lock_guard<mutex> lck2(m2, adopt_lock);
lock_guard<mutex> lck1(m1, adopt_lock);
or (better, but C++17 only):學習
或者(能夠更好,但僅限於C++17)
ui
// thread 1
scoped_lock<mutex, mutex> lck1(m1, m2);
// thread 2
scoped_lock<mutex, mutex> lck2(m2, m1);
Here, the writers of thread1 and thread2 are still not agreeing on the order of the mutexes, but order no longer matters.spa
這裏,thread1和thread2的做者仍然沒有在獲取mutex的順序上取得一致,可是順序已經再也不重要。
Note(注意)
In real code, mutexes are rarely named to conveniently remind the programmer of an intended relation and intended order of acquisition. In real code, mutexes are not always conveniently acquired on consecutive lines.
在實際的代碼中,mutex的命名不多能向程序員提示但願的關係和但願的請求次序。在實際的代碼中,mute不會老是在相鄰代碼中執行獲取,那樣的話問題可能更容易被發現。
In C++17 it's possible to write plain
在C++17能夠簡單地這樣寫:
lock_guard lck1(m1, adopt_lock);
and have the mutex type deduced.
這樣就能夠實現mutex類型推斷。
Enforcement(實施建議)
Detect the acquisition of multiple mutexes. This is undecidable in general, but catching common simple examples (like the one above) is easy.
檢查多重mutex獲取操做。這一點一般是不可斷定的,可是捕捉通常的簡單例子(例如上面的例子)是容易作到的。
原文連接https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#cp21-use-stdlock-or-stdscoped_lock-to-acquire-multiple-mutexes
以爲本文有幫助?請分享給更多人。
關注微信公衆號【面向對象思考】輕鬆學習每一天!
面向對象開發,面向對象思考!
本文分享自微信公衆號 - 面向對象思考(OOThinkingDalian)。
若有侵權,請聯繫 support@oschina.cn 刪除。
本文參與「OSC源創計劃」,歡迎正在閱讀的你也加入,一塊兒分享。