lock used in thread and by event

U

uupi_duu

Hello,

I have a application with two threads. I have also a resoure that is
synchronized by lock.

When testing locks before this App I noticed that if one threaded
application for test purposes

invokes code like below it does not start waiting.

lock(this)

{

..... some code

lock(this)

{

.... some code

} // Execution goes through both locks.

}


Okey for my two threaded Application. In main thread there is a
method that uses lock to protect a data structure. Code is like below:

class MyClass {

public void My Method(object item)
{
lock(_myList)
{
_myList.Remove(item);
}
}

.....

}

In same class there is also a eventhandler to remove items from List
and it's fired from another thread. Code is like below.

class MyClass {
public void OnRemoveItemFromList(object sender, ItemEventArgs e)
{

lock (_myList)
{
_myList.Remove(session)
}

}

......

}


From another thread List item is remove by Event like below:

class SecondThread {
.....

RemoveItemFromListEvent(this, new ItemEventArgs (this));

.....

}



What I have noticed that lock(_myList) does not stop and start waiting
if one of the threads have aquired it.
lock(_myList) goes allways through. So, can anyone explain that is
Event call same as a call executed in thread that owns lock(_myList)
or how this goes?

Can anyone clarify this to me?
Any documentation considering this issue?

Thanks!
 
J

Jon Skeet [C# MVP]

What I have noticed that lock(_myList) does not stop and start waiting
if one of the threads have aquired it.

It will do if it's a different thread.
lock(_myList) goes allways through. So, can anyone explain that is
Event call same as a call executed in thread that owns lock(_myList)
or how this goes?

Can anyone clarify this to me?
Any documentation considering this issue?

Could you post a short but complete program which demonstrates the
problem?

See http://www.pobox.com/~skeet/csharp/complete.html for details of
what I mean by that.
 
U

uupi_duu

Hello, I can't post the program but code was in previous posting.
But what I would like to know is that is event call executed in caller
thread's context or
in the context of that thread were the event handler code is? To
clearify: is event call
same as a method call and executed in context of the thread which has
the actual event handler?

So, is my example of two different threads using event and same lock-
variable in first thread
same thing that what happends when one thead calls lock(this) too
times sequentially (and it does
not start waitiing in second lock call).

Cheers!
 
J

Jon Skeet [C# MVP]

Hello, I can't post the program but code was in previous posting.

Well *some* code was in the previous posting - but nothing to show
what threads are doing what, etc.
But what I would like to know is that is event call executed in caller
thread's context or in the context of that thread were the event
handler code is?

The caller. There's no such thing as "the thread where the event
handler code is".
To clearify: is event call
same as a method call and executed in context of the thread which has
the actual event handler?
Yes.

So, is my example of two different threads using event and same lock-
variable in first thread same thing that what happends when one thead
calls lock(this) too times sequentially (and it does
not start waitiing in second lock call).

It depends on what you mean by "two different threads using event". It
would be *much* easier to talk about this if you could write a short
but complete example. It doesn't need to be your real code - just code
we can talk about.

Jon
 
U

uupi_duu

No, this is the issue: first thread is using a method X that uses
lock(X).
Second thread is fireing an event that executes first threads method
that
also uses lock(X).

So is this situation same like e.g. one and only thread is calling
lock(X)
two times and it does not block?

To clearify again ;) is Event call from one thread to another threads
method that uses lock(X) {...} like Java's ReentrantLock?

Cheers!
 
J

Jon Skeet [C# MVP]

No, this is the issue: first thread is using a method X that uses
lock(X).
Second thread is fireing an event that executes first threads method
that also uses lock(X).

There's no such thing as "first thread's method" though.
So is this situation same like e.g. one and only thread is calling
lock(X) two times and it does not block?

I don't know - I'd have to see the code.
To clearify again ;) is Event call from one thread to another threads
method that uses lock(X) {...} like Java's ReentrantLock?

An event call doesn't change threads (unless you explicitly call
Invoke or something like that). But to reiterate, there's no such
thing as "another thread's method". Methods don't belong to threads.

And yes, locks are re-entrant.

Jon
 
U

uupi_duu

There's no such thing as "first thread's method" though.
Yes there are. Don't make this too hard...

We can also use Abstraction when posting to news.

If I say first thread's method that means there is a class that is a
thread,
and there is an instance of that class. It has a method Y which uses
lock(x).
This class has also a eventhandler Z which is a method and has also
lock(x).
x is a synchronization variable.

So, in same principle to second thread. A class which implements
thread interface, has
an instance and we can call it a second thread. It has an C# Event to
be used to
fire a method in "first class". This method is called eventhandler.

So, some action now! "First method is executing method y and comes to
line
where lock(x) is executed. At the same time "second thread" fires an
event which calls
first thread's (synonym can be now class in this case ) eventhandler
(method z) which also executes
it's lock(x) line.

So the question is again, will any of these threads (first one and
second one) block to line lock(x)?

I know that if second thread (class) call directly without Event first
threads (class) method then
lock(x) will block in eventhandler z (we assume now that eventhandler
Z can be called directly like method).

If you know what is Java's ReentrantLock you should understand this
question :)

Cheers with Guiness!!
 
J

Jon Skeet [C# MVP]

Yes there are. Don't make this too hard...

No, there really isn't. The sooner you express yourself clearly in
accepted terminology, the sooner we'll solve your problem.
We can also use Abstraction when posting to news.

If I say first thread's method that means there is a class that is a
thread,

But again, that breaks down. A class isn't a thread. Multiple threads
can run the same method in the same object at the same time.

In other words: it's not clear what you mean when you write "a class
that is a thread" or "a thread's method".

It *would* be clear if you'd produce a short but complete program,
however.

So, some action now! "First method is executing method y and comes to
line where lock(x) is executed. At the same time "second thread" fires an
event which calls first thread's (synonym can be now class in this case ) eventhandler
(method z) which also executes it's lock(x) line.

If it's *genuinely* a second thread and the locks are *genuinely* to
the same reference,
then the second thread will block.
I know that if second thread (class) call directly without Event first
threads (class) method then
lock(x) will block in eventhandler z (we assume now that eventhandler
Z can be called directly like method).

Sorry, but you've lost me again. It would be *much* simpler to write
this in code rather than in text which uses terminology in a non-
standard way.
If you know what is Java's ReentrantLock you should understand this
question :)

I've already said that locks in C# (and .NET in general) are re-
entrant. Java's ReentrantLock has (as per the API documentation) "the
same basic behavior and semantics as the implicit monitor lock
accessed using synchronized methods" - and Java's synchronization is
very similar to .NET's.

In other words, within one thread you can indeed do:

lock (foo)
{
lock (foo) // No blocking here
{
...
}
}

But if you really, really have a second thread trying to acquire a
lock while another thread holds that lock, the second thread *will*
block until the holding thread releases the lock.

Jon
 
U

uupi_duu

Okey, thanks being "cool" :)

I made a simple sample app. There are two classes and they are both
running in threads.
First class has a method which use lock(this) and then it put itself
to sleep.
Another thread use a Event which launces handler in first class and
handler has also
a lock(this) synchronization. When first thread is in sleep second one
can't execute method
it fired using Event. Or this is what I discovered when debugging
code. So, Events and their handlers
are synchronized.


using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;

namespace TestLock
{
class Parent
{
public Parent()
{
}

public void JustACall()
{
lock (this)
{
Thread.Sleep(5000);
Console.WriteLine("JustACall");
}
}

public void CalledByEvent()
{
lock (this)
{
Console.WriteLine("CalledByEvent");
}
}
}

public delegate void DoHandler();

class Child
{
public event DoHandler _eventHandler;

private Parent _parent;

public Child(Parent parent)
{
_parent = parent;
_eventHandler += new DoHandler(_parent.CalledByEvent);
}

public void CallMe()
{
_eventHandler();
}
}

class Program
{
static void Main(string[] args)
{
Parent parent = new Parent();
Thread t = new Thread(new ThreadStart(parent.JustACall));
t.Start();
Child child = new Child(parent);
Thread t2 = new Thread(new ThreadStart(child.CallMe));
t2.Start();

Console.ReadKey();
}
}
}

Cheers!
 
J

Jon Skeet [C# MVP]

Okey, thanks being "cool" :)

I made a simple sample app.

Excellent, thank you.
There are two classes and they are both running in threads.
First class has a method which use lock(this) and then it put itself
to sleep.
Okay.

Another thread use a Event which launces handler in first class and
handler has also a lock(this) synchronization. When first thread is in
sleep second one can't execute method it fired using Event.

While the first thread owns the lock, the second thread can't aquire
it, yes.
(It will get into the CalledByEvent method, but not be able to acquire
the lock.)
Or this is what I discovered when debugging
code. So, Events and their handlers are synchronized.

No, don't think of it like that. Just think of it as events calling
methods. There's no inherent synchronization involved because the
event calls its handlers within the same thread.

(Pedantic aside: by default the event subscription/unsubscription
acquires a lock. It's irrelevant to your question, but it *is* a bit
of inherent synchronization.)

Jon
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top