Reputation: 73
Is there a construct in c# that is like lock { }, but works when called from an event handler i.e. waits for the code block to complete before handling a subsequent event.
The problem I am having is that lock { } only prevents other threads from obtaining a lock on the object, but if an event handler on the same thread is called, the execution of code within the lock block is interrupted, and the new event is handled before returning to the execution of the original code.
object DoStuffLock = new object();
public void DoStuff()
{
lock (DoStuffLock)
{
// Do stuff that we don't want to be interrupted,
// but because it is called from an event handler
// it still can be interrupted despite the lock
}
}
I am currently working around the problem like this (but it is hardly ideal):
object DoStuffLock = new object();
// this gets called from an event, and therefore can be interrupted,
// locking does not help, so launch separate thread
public void DoStuff()
{
var x = new Thread(DoStuffInternal);
x.Start();
}
private void DoStuffInternal()
{
lock (DoStuffLock)
{
// Do stuff that we don't want to be interrupted
}
}
Upvotes: 3
Views: 8251
Reputation: 53
In operating systems like Windows you can not make any assumptions about the order of events handling. This can be done only with real time operating systems.
What you can do in your case is you could increase your thread priority. That should give your thread more time (relative to other threads). More info about threads priority in .net can be found here: http://msdn.microsoft.com/en-us/library/system.threading.threadpriority.aspx
Upvotes: 0
Reputation: 93464
UI events are all called fromt the same thread. lock is designed to protect from multiple threads. lock is specifically designed to allow the same thread to call the same lock more than once, otherwise a deadlock can occur.
I think your second solution is the correct one. If you have some piece of code that must execute in a block, then you execute it on a new thread.
Upvotes: 0
Reputation: 49271
Think about locking code, not the object.
Use the same lock object to lock pieces of code that can't be entered simultaneously.
Besides, Locks don't stop interruption, they just stop access to the same piece of code from 2 threads simultaneously.
Upvotes: 0
Reputation: 564861
The problem I am having is that lock { } only prevents other threads from obtaining a lock on the object, but if an event handler on the same thread is called
This really can't happen. If your thread is executing, an event can't occur on the same thread - it would have to be raised on a different thread.
That being said, your "second approach" is, in many ways, superior in any case. There's an implicit assumption that event handlers will return very quickly. A "blocking" event handler is typically a sign of a bad design, and will potentially cause problems, especially since the event publisher will not be expecting the event to block.
Upvotes: 4