I am implementing a preemptive, exclusive function in a multithreaded environment, where if a cancel request occurs even when the function is not running, when the function does run, it knows about this cancel request and does not run. I came across various different ways to do this in C# using ManualResetEvent and the like(something like the answer to this question Synchronizing a Timers.Timer elapsed method when stopping ), however I was wondering if something as simple as what I am doing in the code below would suffice. Are there any inadvertent bugs that I am introducing here?
bool cancel = false;
bool running = false;
object Lock = new object();
void PremptiveExclusiveFunction() {
lock(Lock) {
if(running)
return;
running = true;
}
for(int i=0; i < numIter; i++) {
lock(Lock) {
if(cancel) {
cancel = false;
running = false;
return;
}
}
// iteration code
}
lock(Lock) {
running = false;
}
}
void Stop() {
lock(Lock) {
cancel = true;
}
}
As far as I know, this seems to handle my 3 requirements:
1. ability to preempt
2. exclusivity in time, where this only copy of this function can be running
3. a cancel request not being lost because Stop is called before PreemptiveExclusiveFunction
I'd be grateful if more experienced minds could point out if I am indeed missing something.
Entire function body can be locked to eliminate the running
boolean:
object @lock = new object();
volatile bool cancel = false;
void Function () {
if (!Monitor.TryEnter(@lock))
return;
try {
for (var i = 0; i < 100; i++) {
if (cancel) {
cancel = false;
return;
}
// code
}
} finally {
Monitor.Exit(@lock);
}
}
void Stop () {
cancel = true;
}
+ Notice the volatile
keyword:
http://msdn.microsoft.com/en-us/library/vstudio/x13ttww7(v=vs.100).aspx
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.