January 27th, 2006

Waiting for all handles with MsgWaitForMultipleObjects is a bug waiting to happen

The MsgWaitForMultipleObjects and MsgWaitForMultipleObjectsEx functions allow you to specify whether you want to want for any or all of the handles (either by passing bWaitAll = TRUE or by passing dwFlags = MWMO_WAITALL, accordingly). But you never want to wait for all handles. Waiting for all handles means that the call does not return unless all the handles are signalled and a window message meeting your wake criteria has arrived. Since you are typically waiting for messages out of a sense of obligation (keeping the UI thread responsive) rather than one of expectation, even if all the handles you pass become signalled, your program will still stall until a window message arrives. (And if you thought you were being a good UI citizen by using MsgWaitForMultipleObjectsEx, you aren’t actually helping any because waiting for all objects means that the call will not return even if a message is ready, since it’s also waiting for those handles you passed.) Functions which are built on top of the MsgWaitForMultipleObjectsEx function such as MsgWaitForMultipleObjects and CoWaitForMultipleHandles suffer from the same problem. The reason for this can be gleaned from the MsgWaitForMultipleObjectsEx documentation; you just have to put on your thinking cap. Notice that if a message arrives when you are waiting for any handle, the return value is WAIT_OBJECT_0 + cHandles. Notice also that the maximum number of objects you can wait on is MAXIMUM_WAIT_OBJECTS - 1. Obviously, what’s happening under the covers is that the MsgWaitForMultipleObjectsEx function creates a handle that will be signalled when the message queue reaches one of the states you requested in the wake mask, adds that handle to the end of the array you passed in, and then passes the whole thing to the WaitForMultipleObjectsEx function. (Note that the getting access to that internal handle won’t be of any use to you, the application, since you don’t know how to tell the window manager what wait states should result in the event being set.)

(Larry Osterman reminded me that he covered the same topic a while back. So now you get to see it twice.)

Topics
Code

Author

Raymond has been involved in the evolution of Windows for more than 30 years. In 2003, he began a Web site known as The Old New Thing which has grown in popularity far beyond his wildest imagination, a development which still gives him the heebie-jeebies. The Web site spawned a book, coincidentally also titled The Old New Thing (Addison Wesley 2007). He occasionally appears on the Windows Dev Docs Twitter account to tell stories which convey no useful information.

0 comments

Discussion are closed.