# HG changeset patch # User Andrew Innes # Date 930858452 0 # Node ID ff85091a55e792e60cb5b05f9cf493f4a3fd7663 # Parent 71f071c1bdf7a1ac59e92ab9af3866046c355bea (sys_select): Call MsgWaitForMultipleObjects instead of WaitForMultipleObjects when user input is allowed, so we can handle incoming window messages. Call drain_message_queue when there are messages waiting; this ensures that windows created indirectly from the lisp thread get processed properly, and don't hang other applications by failing to respond to broadcasts. diff -r 71f071c1bdf7 -r ff85091a55e7 src/w32proc.c --- a/src/w32proc.c Thu Jul 01 19:44:38 1999 +0000 +++ b/src/w32proc.c Thu Jul 01 19:47:32 1999 +0000 @@ -1175,9 +1175,15 @@ return 0; } - /* Wait for input or child death to be signalled. */ start_time = GetTickCount (); - active = WaitForMultipleObjects (nh + nc, wait_hnd, FALSE, timeout_ms); + + /* Wait for input or child death to be signalled. If user input is + allowed, then also accept window messages. */ + if (FD_ISSET (0, &orfds)) + active = MsgWaitForMultipleObjects (nh + nc, wait_hnd, FALSE, timeout_ms, + QS_ALLINPUT); + else + active = WaitForMultipleObjects (nh + nc, wait_hnd, FALSE, timeout_ms); if (active == WAIT_FAILED) { @@ -1213,7 +1219,26 @@ processed - otherwise higher numbered channels could be starved. */ do { - if (active >= nh) + if (active == nh + nc) + { + /* There are messages in the lisp thread's queue; we must + drain the queue now to ensure they are processed promptly, + because if we don't do so, we will not be woken again until + further messages arrive. + + NB. If ever we allow window message procedures to callback + into lisp, we will need to ensure messages are dispatched + at a safe time for lisp code to be run (*), and we may also + want to provide some hooks in the dispatch loop to cater + for modeless dialogs created by lisp (ie. to register + window handles to pass to IsDialogMessage). + + (*) Note that MsgWaitForMultipleObjects above is an + internal dispatch point for messages that are sent to + windows created by this thread. */ + drain_message_queue (); + } + else if (active >= nh) { cp = cps[active - nh];