Thread: Boost Syncronization and Single writer Multiple readers

  1. #1
    Registered User kroiz's Avatar
    Join Date
    Jun 2007
    Posts
    116

    Boost Syncronization and Single writer Multiple readers

    I came across a solution to the "Single writer Multiple readers Problem" implemented with Boost here.

    Code:
    typedef boost::shared_mutex ReadWriteMutex; 
     typedef boost::shared_lock<boost::shared_mutex> ReadLock; 
     typedef boost::unique_lock<boost::shared_mutex> WriteLock; 
     
    class MtClass 
     { 
     public: 
      MtClass() 
       : m_value() 
      { 
      } 
      ~MtClass(){} 
     
     void setValue(int value) 
      { 
       WriteLock w_lock(rw_mutex); 
       m_value = value; 
      } 
     
     int getValue(void) const 
      { 
       ReadLock r_lock(rw_mutex); 
       return m_value; 
      } 
     
    private: 
      int m_value; 
      mutable ReadWriteMutex rw_mutex;  
    I read the Boost manual about Synchronization and some old (2002) article on Dr. Dobb, but I can not figure how this really works.
    I do know the classics solution to the "Single writer multiple readers" and I guess this is equivalent.
    I will be thankful if you could make me get it...

  2. #2
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    What part don't you get? Any number of threads can enter getValue() at the same time, but if any thread calls setValue(), no thread may be in getValue() or setValue() at the same time.
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  3. #3
    Registered User kroiz's Avatar
    Join Date
    Jun 2007
    Posts
    116
    I guess the main thing I don't get, is how this is done with only one mutex.

  4. #4
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    It isn't. shared_mutex isn't just one normal mutex, it's a special class that supports shared ownership. If you want to know how it is implemented internally, you should check the source. There will be at least a mutex and several atomic counts in there.
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

  5. #5
    Registered User kroiz's Avatar
    Join Date
    Jun 2007
    Posts
    116
    Ok, I think I understand now, but if I understand correctly this solution can lead to writer starvation, right?
    I have seen solutions to the "single writer multiple reader problem" that used a semaphore initialized to the number threads.
    can this be done with Boost?

  6. #6
    Cat without Hat CornedBee's Avatar
    Join Date
    Apr 2003
    Posts
    8,895
    Quote Originally Posted by kroiz View Post
    Ok, I think I understand now, but if I understand correctly this solution can lead to writer starvation, right?
    Depends on the strategy that the mutex employs. My memory is a bit hazy on this, but I remember three general strategies:
    1) Fair. As long as only readers want to enter, they can do so immediately. If a writer comes, it must wait until all readers have left. New readers cannot enter while a writer is waiting.
    2) Writer preference. Like #1, but arriving writers skip all waiting readers, i.e. if one writer arrives, then three readers, then another writer, the second writer will enter once the first writer has left, skipping the three readers.
    3) Reader preference. Writers have to wait until all readers are gone. Readers can enter even if a writer is waiting.

    These strategies all have their pros and cons. The first is probably the most generic. The third can easily lead to writer starvation if there's always readers arriving.

    I have seen solutions to the "single writer multiple reader problem" that used a semaphore initialized to the number threads.
    can this be done with Boost?
    The "standard solution" from this paper is strategy #3.
    The "fair solution" is strategy #1.

    I'm afraid Boost's shared_mutex doesn't document what strategy it follows.
    From reading the implementation, though, it's clear that it implements strategy #1. The exact means differ between the POSIX and the Win32 implementation. The implementation is more complex than the simple one presented in the paper, because shared_mutex allows for upgradeable shared locks.
    As such, the POSIX solution employs one mutex and three condition variables, while the Win32 solution employs three semaphores.
    All the buzzt!
    CornedBee

    "There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
    - Flon's Law

Popular pages Recent additions subscribe to a feed

Tags for this Thread