I'm having trouble performing a search operation in the background, and displaying the results to the user in the foreground inside a list box.
The program uses SendMessage
to send the query results back to the GUI.
When the program is closed, the GUI marks a global (volatile) variable as "completed", and uses MsgWaitForMultipleObjects
to wait on the thread handle, to join the thread.
When I break the program, I see a deadlock: the GUI is waiting for the background thread to terminate, whereas the background thread is waiting in SendMessage
.
This deadlock still occurs when I use a 100-ms timeout for MsgWaitForMultipleObjects
and call it inside a loop, with QS_ALLINPUT
. I can't figure out why.
Is this design even correct? Is there a better way to wait for the thread to terminate?
If not, what is the issue?
You need a double-buffering scheme to avoid overrunning the message queue. Lay it out like this:
Thread 1 performs the search and uses PostMessage to send results.
Thread 2 reads the message queue, selectively removes search result messages, and stores them in an internal memory-based queue that can handle any number of entries.
Thread 3 reads results from the internal queue and displays them.
Note that you'll need a get/put API for the queue with mutex protection to prevent threads 2 and 3 from stepping on each other.