>>This code cannot work correctly.
Of course it can…
> What is not shown here is where the event is set. If there is a race
> condition such that the thread
> that sets the event does the set a microsecond before the other thread
> does the clear, you
> have a deadlock.
Apparently, what you are saying is that it is not shown where this event
gets reset, right?
This is why I made it clear that we are speaking about synchronization
event and not a notification one.
Unlike notification event, synchronization one does not need to be reset
explicitly - it happens upon the release of the waiting thread…
Synchronization events have their own problems, which is why they are not
used very much…in fact, I remember someone from Microsoft rolling his
eyes and saying “Don’t DO that!”
> In this case, you should be using a semaphore, which guarantees
> atomicity across such conditions.
Syncronization event is, for all practical purposes, just a semaphore
that has maxcount of 1 (i.e a binary semaphore). Windows implementation
of semaphores in just broken by design. This is why synch event is
normally used under Windows in situations when other OSes use binary
semaphores…
How is the Windows implementation of semaphores broken?
> NEVER, EVER think priority can be used to guarantee correctness of
> concurrent code.
Sure…
However, the code shown does NOT rely upon the priorities for this
purpose. The only reason why the priorities are mentioned here is because
this event has to get signaled by someone. If a thread that wakes up once
in a VERY while also happens to be of low priority as well…well, I
am afraid the waiting thread would have a chance to perform its actual
task too infrequently to be observed…
Thread starvation is a very real problem.
> This is nonsense.
Do you mean your own participation on this thread? Indeed, up to the point
it seems to be non-sensical - you seem to be arguing against yourself,
because you are arguing against the statements and assumptions that no one
on this thread made…
> There is no way to tell what an “urgent” task is,
Well, as long as you mean priorities of a dynamic class, on my books an
“urgent” task is the one that currently interacts with the user.
That is not an urgent class. In fact, it is running at priority around 8
(it has changed a few times, but I believe it is in that range). This
puts seven more levels of “urgent” above it, and also means that there are
seven (not counting 0) “non-urgent” levels below it. Note that background
threads run two priority levels lower than the foreground thread (defined
as “that thread that owns the window that has the focus”). I have played
some very weird games with thread priorities to get video processing to
run at priority 15 while not killing the UI thread. This trick falls
under the VERY CAREFULLY rubric.
> or what priority it is running at.
… and this part gets addressed by assigning the priorities of either RT
class (in case of high-priority tasks),
or, instead, of an IDLE class for something that is supposed to run only
when there is nothing else to be done at the moment…
Well, not quite. Remember there is an IDLE class in the “realtime” (or
The Class Formerly Known As Realtime, because realtime people would make
faces and laugh at Microsoft people when they used this term), which is
Priority 16, and it preempts ALL of the normal user thread classes (1-15).
So if you put an “idle loop” in this “idle” thread, you are screwed.
In any case, you cannot say what the “urgent” task is unless you compare
its"urgency" to the one of other tasks…
I agree.
> And it doesn’t address the issue of priority inversion if the “low
> priority” thread shares some
> resource with an “urgent task”.
Bu the way, once we are at it, this problem has been solved in the UNIX
world ages ago. In the early UNIX this problem did not exist at all
because all kernel code was non-preemptible by anyone, apart from
interrupt handlers. When Solaris introduced kernel pre-emption it also
ensured that all code that runs in the kernel has a priority above the one
in the userland (RT threads are an exception which, IMHO, simply don’t
belong in the world of GPOSes, in the first place), effectively
introducing a kind of priority ceiling protocol…
Well, as it turns out, that doesn’t “solve” the priority inversion
problem, it just suggests that it is harder for a user-priority thread to
induce it. There is a huge body of literature on solutions to the
priority-inversion problem, dating back to at least the early 1960s;
MULTICS knew about it; RTOS people have created working solutions (there
is a famous documented example of fixing the priority inversion problem on
one of the robotic space missions by uploaded a patch that implemented the
priority-inversion-avoidance algorithm, within the last couple years).
General purpose operating systems rarely have any mechanism for dealing
with priority inversion in the general case, just hacks (like the Balance
Set Manager and the mutex-to-31 hack). These hacks heuristically solve
the problem in the most common cases, but they don’t solve it for special
cases.
joe
Anton Bassov
NTDEV is sponsored by OSR
Visit the list at: http://www.osronline.com/showlists.cfm?list=ntdev
OSR is HIRING!! See http://www.osr.com/careers
For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars
To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer