C++ Scoped Lock with RAII

Resource Acquisition Is Initialization (RAII)[1] is a programming idiom used in several object-oriented languages like C++, D, Ada and Vala. The technique was invented by Bjarne Stroustrup[2] to deal with resource allocation and deallocation in C++. In this language, the only code that can be guaranteed to be executed after an exception is thrown are the destructors of objects residing on the stack. Resource management therefore needs to be tied to the lifespan of suitable objects in order to gain automatic allocation and reclamation. Resources are acquired during initialization, when there is no chance of them being used before they are available, and released with the destruction of the same objects, which is guaranteed to take place even in case of errors.

RAII is vital in writing exception-safe C++ code: to release resources before permitting exceptions to propagate (in order to avoid resource leaks) one can write appropriate destructors once rather than dispersing and duplicating cleanup logic between exception handling blocks that may or may not be executed.

The solution is from stackoverflow. Here is the code:

// stub mutex_t: implement this for your operating system
struct mutex_t { 
    void Acquire() {} 
    void Release() {} 
};

struct LockGuard {
     LockGuard(mutex_t& mutex) : _ref(mutex) { 
         _ref.Acquire();  // TODO operating system specific
     };
     ~LockGuard() { 
          _ref.Release(); // TODO operating system specific
     }
   private:
     LockGuard(const LockGuard&); // or use c++0x ` = delete`
     mutex_t& _ref;
};

int main() {
    mutex_t mtx;
    {
        LockGuard lock(mtx);
        // LockGuard copy(lock); // ERROR: constructor private
        // lock = LockGuard(mtx);// ERROR: no default assignment operator
    }
}

When used with pthread, the sample mutex_t can be:


struct mutex_t {
    public:
        mutex_t(pthread_mutex_t &lock) : m_mutex(lock) {}

        void Acquire() { pthread_mutex_lock(&m_mutex);   }
        void Release() { pthread_mutex_unlock(&m_mutex); }
    private:
        pthread_mutex_t& m_mutex;
};
Advertisements

About minghuasweblog

a long time coder
This entry was posted in All, C/C++ and tagged , , . Bookmark the permalink.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s