Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is this lock usage thread safe?

I know that is wrong to use lock(this) or any shared object.

I wonder if this usage is OK?

public class A
{
  private readonly object locker = new object();
  private List<int> myList;
  public A()
  {
    myList = new List<int>()
  }

  private void MethodeA()
  {
    lock(locker)
    {
      myList.Add(10);
    }
  }

  public void MethodeB()
  {
    CallToMethodInOtherClass(myList);
  }
}

public class OtherClass
{
  private readonly object locker = new object();
  public CallToMethodInOtherClass(List<int> list)
  {
   lock(locker)
   {
     int i = list.Count;
   }
  }
}

Is this thread safe? In OtherClass we lock with a private object so if the class A lock with its private lock can the list still change in the the lock block in OtherClass?

like image 576
Maya Avatar asked Jan 19 '12 10:01

Maya


3 Answers

No, it's not thread safe. Add and Count may be executed at the "same" time. You have two different lock objects.

Always lock your own lock object when passing the list:

  public void MethodeB()
  {
    lock(locker)
    {
      CallToMethodInOtherClass(myList);
    }
  }
like image 188
Stefan Steinegger Avatar answered Sep 22 '22 01:09

Stefan Steinegger


No this is not thread safe. To make it thread safe you can use lock on static objects because they are shared between threads, this may cause deadlocks in the code but it can be handle by maintaining proper order for locking. There is a performance cost associated with lock so use it wisely.

Hope this helps

like image 41
Amar Palsapure Avatar answered Sep 22 '22 01:09

Amar Palsapure


No, this is not thread-safe. A.MethodeA and OtherClass.CallToMethodInOtherClass are locking on different objects, so they're not mutually exclusive. If you need to protect the access to the list, don't pass it to external code, keep it private.

like image 37
Thomas Levesque Avatar answered Sep 20 '22 01:09

Thomas Levesque