views:

269

answers:

1

I have a multi-threaded simulation running on Windows Vista. When I use PostThreadMessage to send messages between threads, I am getting ERROR_INVALID_THREAD_ID, even though I am quite certain (from stepping through the debugger) that the thread id is valid, and the thread has a message queue, since I call PeekMessage from every thread after I create them, as specified in MSDN. It's likely the target thread is suspended, but that should not be a problem, as far as I can tell.

Any clues on what to try? I am simulating an RTOS based application, so I'm hoping not to have to put in too much Windows specific code.

EDIT -

Another clue - if I remove all the semaphore blocking, the messages work fine (although there are some known race conditions). But message queues should not be affected by thread blocking, right?

Edit 2 The code also has the following retry mechanism, as suggested by MSDN. But it still does not work - the retry always fails. hmmm.....

BOOL bResult = false;
int retry = 0;
DWORD dwError = 0;
do 
{
   bResult = PostThreadMessage(pTaskHandle->dwThreadID,0,0,(LPARAM)pMessage);
   if (!bResult)
   {
      dwError = GetLastError();
      retry++;    // should only happen once, if the dest thread has no msg queue
                  // the retry establishes the queue
      Sleep(500);
   }
} while (!bResult && retry<3); // MSDN says try this a few times to start msg queue
A: 

hey, you mention you call PeekMessage after creating the threads but do these threads have full, active message processing loops that are dispatching the messages? msdn says:

Call PostThreadMessage. If it fails, call the Sleep function and call PostThreadMessage again. Repeat until PostThreadMessage succeeds.

which sounds a little goofy if the only requirement is that the thread called PeekMessage once.

also be aware that messages posted via. PostThreadMessage don't get dispatched in DispatchMessage. this seems obvious since there's no window for the message to go to, but i've seen people do it, especially when using MsgWaitForMultipleObjects and such to wait on a handle. in this case it seems unlikely you'd get ERROR_INVALID_THREAD_ID... more likely you'd just miss the message.

~jewel

Jewel S
Thanks - I should have mentioned that I have the Sleep retry function already in the code. The threads do not have window objects associated with them, so they do not have traditional message processing loops - I am using MsgWaitForMultipleObjects, using the QS_ALLEVENTS mask, which returns after the PostThreadMessage. I wonder if there is omething wrong there. I will check
Jeff