问题
I'm having issues understanding the Mutex class and how to properly use it in a WP8 application. What I'm attempting to do is allow only a ScheduledAgent or the application to read/write a file to storage at a time. I've tried this various ways with no luck. Any help would be appreciated.
ScheduledAgent code:
Below code errors out when I call ReleaseMutex(). This issue is fixed when I create the Mutex object like so: new Mutex(true, "FlightPathData"). But then I can never get a lock and hangs on WaitOne()
Error
Object synchronization method was called from an unsynchronized block of code.
Code
readonly Mutex mutex = new Mutex(false, "FlightPathData");
protected async override void OnInvoke(ScheduledTask task)
{
List<METAR> savedMetars = null;
var facility = ....;
bool mutexAcquired = mutex.WaitOne();
try
{
if (mutexAcquired)
{
savedMetars = await Data.LoadMetarsAsync(facility.Identifier);
//Thread.Sleep(15000);
}
}
finally
{
if (mutexAcquired)
{
mutex.ReleaseMutex();
}
}
NotifyComplete();
}
ViewModelCode (Works fine till the ScheduledAgent ReleaseMutex() fails)
static readonly Mutex mutex = new Mutex(true, "FlightPathData");
...
mutex.WaitOne();
var savedMetars = await Data.LoadMetarsAsync(this.Facility.Identifier);
mutex.ReleaseMutex();
回答1:
You can't use thread-affine locks with async
code. This is because the await
can cause the method to return (while holding the mutex) and then another thread can continue the async
method and attempt to release a mutex it does not own. If this is confusing, I have an async intro blog post that you may find helpful.
So you can't use Mutex
or other thread-affine locks such as lock
. However, you can use SemaphoreSlim. In your async
methods, you would use await WaitAsync
instead of Wait
.
来源:https://stackoverflow.com/questions/16876081/wp8-mutex-resource-locking