read_write_lock.hpp

来自「CGAL is a collaborative effort of severa」· HPP 代码 · 共 1,112 行 · 第 1/3 页

HPP
1,112
字号
// Copyright (C)  2002-2003// David Moore//// Original scoped_lock implementation// Copyright (C) 2001// William E. Kempf//// Permission to use, copy, modify, distribute and sell this software// and its documentation for any purpose is hereby granted without fee,// provided that the above copyright notice appear in all copies and// that both that copyright notice and this permission notice appear// in supporting documentation.  David Moore makes no representations// about the suitability of this software for any purpose.// It is provided "as is" without express or implied warranty.#ifndef BOOST_READ_WRITE_LOCK_JDM031002_HPP#define BOOST_READ_WRITE_LOCK_JDM031002_HPP#include <boost/thread/detail/config.hpp>#include <boost/utility.hpp>#include <boost/thread/exceptions.hpp>#include <boost/thread/detail/lock.hpp>namespace boost {struct xtime;namespace read_write_lock_state {    enum read_write_lock_state_enum    {        unlocked=0,        read_locked=1,        write_locked=2    };} //namespace read_write_lock_statenamespace detail {namespace thread {template <typename Mutex>class read_write_lock_ops : private noncopyable{private:    read_write_lock_ops() { }    ~read_write_lock_ops() { }public:    typedef Mutex mutex_type;    static void write_lock(Mutex& m)    {        m.do_write_lock();    }    static void read_lock(Mutex& m)    {        m.do_read_lock();    }    static void write_unlock(Mutex& m)    {        m.do_write_unlock();    }    static void read_unlock(Mutex &m)    {        m.do_read_unlock();    }    static bool try_write_lock(Mutex &m)    {        return m.do_try_write_lock();    }    static bool try_read_lock(Mutex &m)    {        return m.do_try_read_lock();    }    static bool timed_write_lock(Mutex &m,const xtime &xt)    {        return m.do_timed_write_lock(xt);    }    static bool timed_read_lock(Mutex &m,const xtime &xt)    {        return m.do_timed_read_lock(xt);    }    static void demote(Mutex & m)    {        m.do_demote_to_read_lock();    }    static bool try_demote(Mutex & m)    {        return m.do_try_demote_to_read_lock();    }    static bool timed_demote(Mutex & m,const xtime &xt)    {        return m.do_timed_demote_to_read_lock(xt);    }    static void promote(Mutex & m)    {        m.do_promote_to_write_lock();    }    static bool try_promote(Mutex & m)    {        return m.do_try_promote_to_write_lock();    }    static bool timed_promote(Mutex & m,const xtime &xt)    {        return m.do_timed_promote_to_write_lock(xt);    }};template <typename ReadWriteMutex>class scoped_read_write_lock : private noncopyable{public:    typedef ReadWriteMutex mutex_type;    scoped_read_write_lock(        ReadWriteMutex& mx,        read_write_lock_state::read_write_lock_state_enum initial_state)        : m_mutex(mx), m_state(read_write_lock_state::unlocked)    {        if (initial_state == read_write_lock_state::read_locked)            read_lock();        else if (initial_state == read_write_lock_state::write_locked)            write_lock();    }    ~scoped_read_write_lock()    {        if (m_state != read_write_lock_state::unlocked)            unlock();    }    void read_lock()    {        if (m_state != read_write_lock_state::unlocked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::read_lock(m_mutex);        m_state = read_write_lock_state::read_locked;    }    void write_lock()    {        if (m_state != read_write_lock_state::unlocked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::write_lock(m_mutex);        m_state = read_write_lock_state::write_locked;    }    void unlock()    {        if (m_state == read_write_lock_state::unlocked) throw lock_error();        if (m_state == read_write_lock_state::read_locked)            read_write_lock_ops<ReadWriteMutex>::read_unlock(m_mutex);        else //(m_state == read_write_lock_state::write_locked)            read_write_lock_ops<ReadWriteMutex>::write_unlock(m_mutex);        m_state = read_write_lock_state::unlocked;    }    void demote(void)    {        if (m_state != read_write_lock_state::write_locked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::demote(m_mutex);        m_state = read_write_lock_state::read_locked;    }    void promote(void)    {        if (m_state != read_write_lock_state::read_locked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::promote(m_mutex);        m_state = read_write_lock_state::write_locked;    }    //If allow_unlock = true, set_lock always succeedes and    //the function result indicates whether an unlock was required.    //If allow_unlock = false, set_lock may fail;    //the function result indicates whether it succeeded.    bool set_lock(read_write_lock_state::read_write_lock_state_enum ls, bool allow_unlock = true)    {        bool result = !allow_unlock;        if (m_state != ls)        {            if (m_state == read_write_lock_state::unlocked)            {                if (ls == read_write_lock_state::read_locked)                    read_lock();                else //(ls == read_write_lock_state::write_locked)                    write_lock();            }            else //(m_state == read_write_lock_state::read_locked || m_state == read_write_lock_state::write_locked)            {                if (ls == read_write_lock_state::read_locked)                    demote();                else if (ls == read_write_lock_state::write_locked)                {                    if (allow_unlock)                    {                        result = true;                        unlock();                        write_lock();                    }                    else                        result = false;                }                else //(ls == read_write_lock_state::unlocked)                    unlock();            }        }        return result;    }      bool locked() const    {        return m_state != read_write_lock_state::unlocked;    }      bool read_locked() const    {        return m_state == read_write_lock_state::read_locked;    }      bool write_locked() const    {        return m_state != read_write_lock_state::write_locked;    }    operator const void*() const    {        return (m_state != read_write_lock_state::unlocked) ? this : 0;     }    read_write_lock_state::read_write_lock_state_enum state() const    {        return m_state;    }    private:    ReadWriteMutex& m_mutex;    read_write_lock_state::read_write_lock_state_enum m_state;};template <typename ReadWriteMutex>class scoped_read_lock : private noncopyable{public:    typedef ReadWriteMutex mutex_type;    explicit scoped_read_lock(        ReadWriteMutex& mx,        bool initially_locked = true)        : m_mutex(mx), m_state(read_write_lock_state::unlocked)    {        if (initially_locked)            lock();    }    ~scoped_read_lock()    {        if (m_state != read_write_lock_state::unlocked)            unlock();    }    void lock()    {        if (m_state != read_write_lock_state::unlocked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::read_lock(m_mutex);        m_state = read_write_lock_state::read_locked;    }    void unlock()    {        if (m_state != read_write_lock_state::read_locked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::read_unlock(m_mutex);        m_state = read_write_lock_state::unlocked;    }      bool locked() const    {        return m_state != read_write_lock_state::unlocked;    }    operator const void*() const    {        return (m_state != read_write_lock_state::unlocked) ? this : 0;     }    private:    ReadWriteMutex& m_mutex;    read_write_lock_state::read_write_lock_state_enum m_state;};template <typename ReadWriteMutex>class scoped_write_lock : private noncopyable{public:    typedef ReadWriteMutex mutex_type;    explicit scoped_write_lock(        ReadWriteMutex& mx,        bool initially_locked = true)        : m_mutex(mx), m_state(read_write_lock_state::unlocked)    {        if (initially_locked)            lock();    }    ~scoped_write_lock()    {        if (m_state != read_write_lock_state::unlocked)            unlock();    }    void lock()    {        if (m_state != read_write_lock_state::unlocked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::write_lock(m_mutex);        m_state = read_write_lock_state::write_locked;    }    void unlock()    {        if (m_state != read_write_lock_state::write_locked) throw lock_error();        read_write_lock_ops<ReadWriteMutex>::write_unlock(m_mutex);        m_state = read_write_lock_state::unlocked;    }      bool locked() const    {        return m_state != read_write_lock_state::unlocked;    }    operator const void*() const    {        return (m_state != read_write_lock_state::unlocked) ? this : 0;     }    private:    ReadWriteMutex& m_mutex;    read_write_lock_state::read_write_lock_state_enum m_state;};template <typename TryReadWriteMutex>class scoped_try_read_write_lock : private noncopyable{public:    typedef TryReadWriteMutex mutex_type;        scoped_try_read_write_lock(        TryReadWriteMutex& mx,        read_write_lock_state::read_write_lock_state_enum initial_state)        : m_mutex(mx), m_state(read_write_lock_state::unlocked)    {        if (initial_state == read_write_lock_state::read_locked)            read_lock();        else if (initial_state == read_write_lock_state::write_locked)            write_lock();    }

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?