Is boost shared_ptr <XXX> thread safe?

user25749 picture user25749 · Mar 28, 2009 · Viewed 23.4k times · Source

I have a question about boost::shared_ptr<T>.

There are lots of thread.

using namespace boost;

class CResource
{
  // xxxxxx
}

class CResourceBase
{
public:
   void SetResource(shared_ptr<CResource> res)
   {
     m_Res = res;
   }

   shared_ptr<CResource> GetResource()
   {
      return m_Res;
   }
private:
   shared_ptr<CResource> m_Res;
}

CResourceBase base;

//----------------------------------------------
// Thread_A:
    while (true)
    {
       //...
       shared_ptr<CResource> nowResource = base.GetResource();
       nowResource.doSomeThing();
       //...
    }

// Thread_B:
    shared_ptr<CResource> nowResource;
    base.SetResource(nowResource);
    //...

Q1

If Thread_A do not care the nowResource is the newest, will this part of code have problem?

I mean when Thread_B do not SetResource() completely, Thread_A get a wrong smart point by GetResource()?

Q2

What does thread-safe mean?

If I do not care about whether the resource is newest, will the shared_ptr<CResource> nowResource crash the program when the nowResource is released or will the problem destroy the shared_ptr<CResource>?

Answer

Michael Burr picture Michael Burr · Mar 28, 2009

boost::shared_ptr<> offers a certain level of thread safety. The reference count is manipulated in a thread safe manner (unless you configure boost to disable threading support).

So you can copy a shared_ptr around and the ref_count is maintained correctly. What you cannot do safely in multiple threads is modify the actual shared_ptr object instance itself from multiple threads (such as calling reset() on it from multiple threads). So your usage is not safe - you're modifying the actual shared_ptr instance in multiple threads - you'll need to have your own protection.

In my code, shared_ptr's are generally locals or parameters passed by value, so there's no issue. Getting them from one thread to another I generally use a thread-safe queue.

Of course none of this addresses the thread safety of accessing the object pointed to by the shared_ptr - that's also up to you.