2011-09-10 92 views
0

我最近开始使用boost :: thread(WinXP,VS10,BoostPro),发现互斥锁可以被任何线程解锁,而不是只由拥有它的线程解锁。 此外,它接缝,基本lock_guard +互斥组合正在做一些内部计数多锁()和解锁(),但它不是一个大问题,我猜。Boost:可能从任何线程解锁互斥锁?

有人知道为什么它是这样设计的吗?这是故意的吗? (或者有什么毛病我的编译环境/库?)

示例应用程序:

#include <iostream> 
#include <boost/thread.hpp> 

using namespace std; 


class NamedThread 
{ 
public: 
    NamedThread(string name_, boost::mutex& mtx_) : 
     mtx(mtx_), name(name_) {} 

    void operator()() 
    { 
     for (int i = 0; i < 10; ++i) 
     { 
      boost::this_thread::sleep(boost::posix_time::milliseconds(1000)); 
      cout << name << endl; 

      //boost::lock_guard<boost::mutex> guard1(mtx); 
      //boost::lock_guard<boost::mutex> guard2(mtx); 

      boost::unique_lock<boost::mutex> guard1(mtx); 
      boost::unique_lock<boost::mutex> guard2(mtx); 
     } 


    } 

    string name; 
    boost::mutex& mtx; 
}; 

class UnlockerThread 
{ 
public: 
    UnlockerThread(string name_, boost::mutex& mtx_) : 
     mtx(mtx_), name(name_) {} 

    void operator()() 
    { 
     for (int i = 0; i < 100; ++i) 
     { 
      boost::this_thread::sleep(boost::posix_time::milliseconds(3000)); 
      cout << name << ": unlocking" << endl; 
      mtx.unlock(); // !!! IT WORKS !!! 
     } 
    } 

    string name; 
    boost::mutex& mtx; 
}; 


int main() 
{ 
    boost::mutex mtx; 

    NamedThread th2("Thread1", mtx); 
    boost::thread t2(th2); 

    UnlockerThread th3("UnlockerThread", mtx); 
    boost::thread t3(th3); 

    t2.join(); 

    char ch; 
    cin >> ch; 
    return 0; 
} 

感谢,

回答

2

Boost文档是很清楚,调用mutex.unlock的先决条件是“当前线程拥有这个”。这并不意味着违反该前提条件将导致异常/错误/崩溃(尽管对于调试版本来说它可能很好),但在这种情况下您不能依赖任何特定的行为。

win32实现似乎使用原子指令来实现大部分互斥体的逻辑 - 大概是因为在win32上对更复杂的互斥体类型(递归/定时)的有限支持。 Win32的本机关键部分只能用于简单的互斥锁(而Win32的本地互斥锁对于进程内互斥体来说太重量级了)。

+0

所以我想我的开发环境是好的。我完全知道boost文档中的内容,但我相信这种行为会导致在大型应用程序中发现非常严重且难以检测到的错误。文档声明本身不能防止编程错误。在我看来,至少应该在调试版本中声明一些声明,以及在这种情况下有关未定义行为的文档中的信息。再次感谢您的评论。 – Oedo808

+1

@ Oedo808除了您对Win32实现的评论之外。我相信1_55提升会使用Lamport的面包店(http://en.wikipedia.org/wiki/Lamport's_bakery_algorithm)。 –