图片 5

Windows消息机制要点,hang的原因分析

5 PostMessage(PostThreadMessage), SendMessage 
PostMessage:把新闻放到钦赐窗口所在的线程消息队列中后立马回到。
PostThreadMessage:把消息放到钦命线程的新闻队列中后即刻重临。
SendMessage:直接把音信送到窗口进程管理,管理完了才再次回到。

图片 1

9 BroadcastSystemMessage 
我们一般所接触到的新闻都以发送给窗口的,其实,
消息的收信人可以是美妙绝伦的,它能够是应用程序(applications),
可设置驱动(installable drivers),网络设施(network drivers),
系统级设备驱动(system-level device drivers)等, 
布罗兹castSystemMessage这些API能够对以上系统组件发送消息。

图片 2

6 GetMessage, PeekMessage 
PeekMessage会马上回到能够保留音信
GetMessage在有新闻时重回会去除新闻

NtUserMessageCall(HWND_BROADCAST, WM_DDE_INITIATE)

3 新闻队列(Message Queues) 
Windows中有两体系型的音讯队列
1) 系统音信队列(System Message Queue) 那是七个体系唯一的Queue,设备驱动(mouse,
keyboard)会把操作输入转化成音讯存在系统队列中,然后系统会把此新闻放到目的窗口所在的线程的音讯队列(thread-specific
message queue)中等待管理
2) 线程音讯队列(Thread-specific Message Queue) 每三个GUI线程都会保养这么叁个线程音信队列。(那些行列唯有在线程调用GDI函数时才会创制,私下认可不成立)。然后线程新闻队列中的消息会被送到对应的窗口过程(WndProc)管理.
留神:
线程音信队列中WM_PAINT,WM_TIMERubicon唯有在Queue中尚无此外音信的时候才会被管理,WM_PAINT音信还会被统一以提升成效。别的兼具音信以先进先出(FIFO)的办法被拍卖。

图片 3

4> ShellExecuteEx实施落成,但并不destroy “WorkerW”窗口

8(音讯死锁( Message Deadlocks) 
万一无线程A和B, 今后有以下下步骤
1) 线程A SendMessage给线程B, A等待音讯在线程B中拍卖后重返
2) 线程B收到了线程A发来的消息,并实行拍卖, 在管理进度中,B也向线程A
SendMessgae,然后等待从A再次回到。
因为这时, 线程A正等待从线程B重回, 不能够管理B发来的音讯,
从而导致了/线程A,B互相等待, 变成死锁。多少个线程也足以造成环形死锁。
能够接纳 SendNotifyMessage或SendMessageTimeout来防止出现死锁。

3.2.2 为了验证3.2.1的结论,在PostMessageW上下断点追踪一下

4 队列音信(Queued Messages)和非队列音讯(Non-Queued Messages)
1)队列音信(Queued Messages)
 
音信会先保存在音信队列中,新闻循环会从此队列中取音信并散发到各窗口管理
如鼠标,键盘音信。
2) 非队列音信(NonQueued Messages) 音信会绕过系统音讯队列和线程音讯队列直接发送到窗口进程被拍卖
如: WM_ACTIVATE, WM_SETFOCUS, WM_SETCURSOR, WM_WINDOWPOSCHANGED 
留意: postMessage发送的新闻是队列音信,它会把音讯Post到消息队列中;
SendMessage发送的新闻是非队列信息, 被平昔送到窗口进度处理

图片 4

1. 窗口进程 
各类窗口会有多个名称为窗口进度的回调函数(WndProc),它含有多个参数,分别为:窗口句柄(Window
Handle),音讯ID(Message ID),和多少个新闻参数(wParam,
lParam),当窗口收到音讯时系统就能够调用此窗口过程来处理新闻。(所以叫回调函数)

2> 运行http_server.py(需先安装python)

2 消息类型 
1) 系统定义音讯(System-Defined Messages)
 
在SDK中先行定义好的音信,非用户定义的,其范围在[0x0000, 0x03ff]里头,
能够分成以下三类:
1>窗口音讯(Windows Message) 
与窗口的里边运行有关,如创立窗口,绘制窗口,销毁窗口等。能够是形似的窗口,也得以是Dialog,控件等。
如:WM_CREATE, WM_PAINT, WM_MOUSEMOVE, WM_CTLCOLOR, WM_HSCROLL…
2>命令音信(Command Message):注意那类音讯通称为WM_COMMAND
与管理用户央求有关, 如单击菜单项或工具栏或控件时, 就能时有爆发命令音信。
WM_COMMAND, LOWORubiconD(wParam)表示菜单项,工具栏开关或控件的ID。假设是控件,
HIWOCR-VD(wParam)表示控件新闻类型
3> 控件布告(Notify Message) 
控件通告音讯, 那是最灵敏的音信格式, 其Message, wParam,
lParam分别为:WM_NOTIFY,
控件ID,指向NMHD大切诺基的指针。NMHDR蕴含控件文告的内容, 能够随意扩展。
2) 程序定义音信(Application-Defined Messages) 
用户自定义的音信, 对于其范围有如下规定:
WM_USER: 0x0400-0x7FFF    (ex. WM_USER+10)
WM_APP(winver>4.0): 0x8000-0xBFFF (ex.WM_APP+4)
RegisterWindowMessage: 0xC000-0xFFFF

3. 原因分析

7 TranslateMessage, TranslateAccelerator 
TranslateMessage: 把二个virtual-key音信转化成字符音讯(character
message),并置于当前线程的新闻队列中,音讯循环下一遍抽取管理。
TranslateAccelerator:将快速键对应到对应的美食做法命令。它会把WM_KEYDOWN 或
WM_SYSKEYDOWN转化成急迅键表中相应的WM_COMMAND或WM_SYSCOMMAND音讯,
然后把转化后的 WM_COMMAND或WM_SYSCOMMAND直接发送到窗口进程管理,
管理完后才会回来。

shell_execute.exe的主要code:

消息1000为WM_DDE_EXECUTE,Post窗口句柄为0x00310172。

在意到下七个API GetWindowThreadProcessId ( 0x00310172 , 0x0012fb70
),刚好是获得那么些窗口的pid和tid,查看下参数窗口:

因为双击展开实际是用explorer.exe展开,而explorer.exe是有窗口的,可以健康的选取管理WM_DDE_INITIATE消息

1> 解压iqy_test.zip

通过能够疑忌是由于console进度在和excel用DDE音信通讯时,console没有响应excel发送的DDE音信,导致excel
hang住

依据DDE的音讯参数,可见wParam正是出殡和埋葬音讯的窗口,其句柄为2425190 =
0x250166,反向查询知那是ShellExecuteEx创制的”WorkerW”窗口

翻开参数知excel调用NtUserMessageCall()类似如下:

2. 重现步骤

复出情状:XP sp3 / Office 二〇〇五(别的office版本应该也能够,未有测试)

3.1 excel hang在哪里?

3.3 总结

5>
excel收到WM_DDE_EXECUTE音讯后会广播WM_DDE_INITIATE音信,”WorkerW”窗口所在的console进度由于尚未概念信息管理函数,ShellExecuteEx定义的”WorkerW”窗口语资源新闻息管理函数得不到CPU实践机会,导致不会response该新闻,从而导致excel
hang住

注意到win7下PostMessageW是用的线程2调用的,搜一下线程创设API
CreateThread

翻看一下buff的地址:

图片 5

 

临近,我们得以创制二个带窗口的次第,运转后将其挂起,那时,尽管直接双击张开test.iqy也会hang住。

1. 问题

call stack突显的确是ShellExecuteEx所调用

发表评论

电子邮件地址不会被公开。 必填项已用*标注