如果接收线程开始传送消息,SendMessage可以提前返回吗?

时间:2009-12-10 16:51:58

标签: winapi sendmessage

Windows如何确定SendMessage应该返回 - 也就是说,它如何决定接收线程是否已完成处理已发送的消息?

详细方案: 我有线程A使用SendMessage将线程发送到线程B.显然,在线程B完成处理消息之前,SendMessage不会返回。线程B弹出一个对话框并开始传送消息。在我的场景中,队列上有一条WM_KILLFOCUS消息,它被线程B抽取。这个结果是线程B上的WM_COMMAND消息。线程B将此WM_COMMAND消息传递给默认窗口proc。当它执行此操作时,即使原始消息尚未完成处理,SendMessage也会返回到线程A!到底是怎么回事?看起来某种程度上,默认的窗口过程会使Windows认为原始发送的消息已经完成。

那么有没有已知的情况,泵送消息和调用默认窗口proc可以欺骗SendMessage返回?

谢谢! 菲尔

4 个答案:

答案 0 :(得分:4)

只要处理消息已启动,处理内线消息的WindowProc就可以调用ReplyMessage以允许调用线程在处理继续时继续。

答案 1 :(得分:2)

由于SendMessage具有返回值,因此始终在处理消息之后。

另一方面,

PostMessage不会等待处理消息。

来自SendMessage上的MSDN:

  

SendMessage函数调用   指定的窗口过程   窗口并没有返回,直到   窗口程序已经处理完了   消息。

在处理邮件之前,不存在返回的情况。

答案 2 :(得分:1)

从MSDN,听起来问题可能是在线程B中显示一个对话框可能会导致死锁。请参阅Message Deadlocks


可能是因为线程A收到的消息是非排队消息。来自MSDN:

  

但是,发送线程会   处理传入的非排队消息   在等待它的消息时   处理。为防止这种情况,请使用   使用SMTO_BLOCK发送SendMessageTimeout   组。有关非排队的更多信息   消息,请参阅Nonqueued Messages

答案 3 :(得分:0)

听起来好像你的原始SendMessage没有返回,而是在处理发送的消息期间调用了线程A中的WindowProc。不要求消息处理程序必须避免在收到消息时调用SendMessage。

在收到您为响应焦点更改消息而发送的WM_COMMAND时,您应该能够在callstack中看到对SendMessage的原始调用。