
Peter Dimov wrote:
Eric Niebler wrote:
How about:
if( ScopedLock l = try_lock( m ) ) { }
You know that I very much favor declarations in conditions, but this is a whole new design, one that uses moveable locks. Something like:
class Mutex { public:
AutoLock lock(); AutoLock try_lock(); AutoLock timed_lock( xtime ); };
One might argue that a lock is naturally moveable...
This does need to be addressed someday, but...
but I think that we should constrain ourselves to (fixing) the current noncopyable scoped_lock idiom.
I agree that movable locks should wait. However, what about something like this, which doesn't require movable locks (concept only--there are probably errors): //----- locker classes -----/ template <typename Mutex> class unlocked { public: unlocked(Mutex& m) : m_(m) {} template <typename Lock> operator () (Lock& l) const {} }; template <typename Mutex> class locked { public: locked(Mutex& m) : m_(m) {} template <typename Lock> operator () (Lock& l) const {l.lock();} }; template <typename Mutex> class try_locked { public: try_locked(Mutex& m) : m_m(m) {} template <typename Lock> operator () (Lock& l) const {l.try_lock();} Mutex m_; private: bool locked_; }; template <typename Mutex> class timed_locked { public: timed_locked(Mutex& m, const xtime& t) : m_m(m), t_(t) {} template <typename Lock> operator () (Lock& l) const {l.timed_lock(t);} Mutex m_; private: bool t_; }; //----- lock classes -----/ class lock { public: template <class Locker> try_lock(const Locker& locker) : m_(locker.m_) {locker(*this);} } class try_lock { public: template <class Locker> try_lock(const Locker& locker) : m_(locker.m_) {locker(*this);} } class timed_lock { public: template <class Locker> try_lock(const Locker& locker) : m_(locker.m_) {locker(*this);} } //----- example -----/ mutex m; lock l1 = unlocked(m); lock l2 = locked(m); try_lock l3 = unlocked(m); try_lock l4 = locked(m); if (try_lock l5 = try_locked(m)) {/*...*/} timed_lock l6 = unlocked(m); timed_lock l7 = locked(m); if (timed_lock l8 = try_locked(m)) {/*...*/} if (timed_lock l9 = timed_locked(m, get_xtime()) {/*...*/} To select whether a lock should be locked or not at runtime, you could add constructors to the locker classes that take a bool or enum and redefine their operator() to lock if the constructor parameter indicated that it should. Mike