有谁研究过《Windows核心编程》里的第22章的LastMsgBoxInfo程序?

sdcer 2006-01-19 08:12:16
这个程序是windows api挂接的,看了文字介绍,我大概明白了的原理和操作过程。
但exe模块中有一些代码,我太明白的,而且程序运行时,感觉也不正确,特向各位请教。

1.

int WINAPI _tWinMain(HINSTANCE hinstExe, HINSTANCE, PTSTR pszCmdLine, int) {

DWORD dwThreadId = 0;
#ifdef _DEBUG
HWND hwnd = FindWindow(NULL, TEXT("Untitled - Paint"));
dwThreadId = GetWindowThreadProcessId(hwnd, NULL);
#endif
LastMsgBoxInfo_HookAllApps(TRUE, dwThreadId);
DialogBox(hinstExe, MAKEINTRESOURCE(IDD_LASTMSGBOXINFO), NULL, Dlg_Proc);
LastMsgBoxInfo_HookAllApps(FALSE, 0);
return(0);
}
上面的代码,我不太明白:HWND hwnd = FindWindow(NULL, TEXT("Untitled - Paint"));
为什么要找一个标题为"Untitled-Paint"的窗口?这个窗口有什么意义吗?是谁建立的?
我在直接运行时,好象hwnd一直返回0,dwThreadId也一直是0。我想,如果只是想为
LastMsgBoxInfo_HookAllApps()函数的第二个参数赋值0,可以直接赋啊,没必要这么麻烦啊。不明白为什么要这么做。

2.这个程序(包括exe、dll),在安装了最新的SDK后,可以编译,可执行程序和dll程序都可以成功编译,但直接运行这个LastMsgBoxInfo.exe,窗口会一闪而过。根本不象文字部分描述的那样。经过跟踪,执行DialogBox(hinstExe, MAKEINTRESOURCE(IDD_LASTMSGBOXINFO), NULL, Dlg_Proc)时,提示"Stack overflow....",这是怎么回事呢?

有谁研究过这个程序吗?请指点一二、谢谢了!!!
...全文
277 11 打赏 收藏 转发到动态 举报
写回复
用AI写文章
11 条回复
切换为时间正序
请发表友善的回复…
发表回复
皮皮鲁 2006-01-23
  • 打赏
  • 举报
回复
恩,其实是这样的

API HOOK分两步,第一步是将你的DLL注入到目标程序中,如果你想HOOK系统中的所有API,则必须注入到所有系统的。钩子只是实现了这一步。用SetWindowsHookEx只能将DLL注入GUI程序中,因为Console程序没有Message,所以无法注入。如果要注入Console程序,可以参照Jeffery Ritcher书上其他的注入DLL的方法,比如说远程线程等

在将dll注入目标进程之后,然后就可以开始HOOK API了,Jeffery Ritcher也给出了两种方法。1。直接修改代码,加入JMP语句在原先的代码处,直接跳转到你的代码中
2。修改Import Address Table
sdcer 2006-01-23
  • 打赏
  • 举报
回复
to 皮皮鲁

我知道用Hook api,但是具体怎么Hook api?

Jeffery的那个例子,也是通过钩子SetWindowsHookEx来挂接api的,但他那个,只限于GUI程序(console的不行),我认为。

我需要挂接所有的进程,而不只是GUI进程。
皮皮鲁 2006-01-23
  • 打赏
  • 举报
回复
1。你应该用HOOK API而不是钩子

2。PROC是一个Jeffery Ritcher用typedef定义的类型,c++可以定义操作符,可以自动将一个类型转换成另外一个类型。——拿本C++的书看看就明白了
sdcer 2006-01-22
  • 打赏
  • 举报
回复
还是没搞定,我有几个看不懂它这个程序的地方,另外也有我的一些疑问:
1.如果我想挂接系统的CreateFile函数,设置钩子类型为WH_GETMESSAGE可以吗?为什么?系统调用CreateFile时,发生了什么?是发送消息吗。我不明白挂接CreateFile时,到底应该设置何种钩子类型,为什么?

2.它这个程序中,apihook.h中,定义了一个操作符(PROC)!?
// Returns the original address of the hooked function
operator PROC() { return(m_pfnOrig); }
根据提示,这个函数的目的是返回m_pfnOrig的地址。

可是,下面又有如下形式的定义:
PROC m_pfnOrig; // Original function address in callee

为什么m_pfnOrig的类型是PROC?没看懂这是什么意思。PROC是一种数据类型吗?


恳请各位赐教,在下感激不尽!!
sdcer 2006-01-20
  • 打赏
  • 举报
回复
to 皮皮鲁。

什么叫“当应用程序被Debug时”,是指设断点、调试程序吗?

还有,什么是“PE文件格式”,不懂啊。

此外,我也没改过原来它这段代码啊,只是把dll程序的输出文件名改了改,原来是"22 ....lib.dll",现在,我把前面的“22+空格”,去掉了。这应该对程序没有影响吧?

而且,是不是运行这个程序,必须要打开画图程序呢?现在的问题是,打开画图程序,就能出现对话框,而不打开画图程序,程序就一闪而过,到底应该是怎么样的现象呢?

皮皮鲁 2006-01-20
  • 打赏
  • 举报
回复
什么叫“当应用程序被Debug时”,是指设断点、调试程序吗?

恩,差不多就是这个意思,不过不光是设断点,调试程序,只要程序是被调试器调试运行就是使被Debug。

还有,什么是“PE文件格式”,不懂啊。

这是Windows下所有可执行文件的格式,到Google上搜一下,你可以得到很多内容。

而且,是不是运行这个程序,必须要打开画图程序呢?现在的问题是,打开画图程序,就能出现对话框,而不打开画图程序,程序就一闪而过,到底应该是怎么样的现象呢?

不需要打开画图程序,打开画图程序只是为了方便调试。
至于你说的问题,需要debug到底是怎么回事。
皮皮鲁 2006-01-19
  • 打赏
  • 举报
回复
意思是说说在Windows98操作系统下,当应用程序被Debug时,它的Import Section会指向一个代码段,这个代码段再调用实际的函数,所以,Jeffery Ritcher,写了一个比较奇怪的代码,就是为了解决这个问题。

关于Import Section,需要看看后面的dll相关章节才能够明白,最好能够懂PE文件格式就更好了,不过就现在来说,你可以暂时先别管他了,你的问题跟这个也没有关系
sdcer 2006-01-19
  • 打赏
  • 举报
回复
如果打开画图程序,即打开一个窗口标题为"未命名-画图"的窗口,

这个程序,可以运行起来(即,不会一闪而过),但是,它好象截不到MessageBox啊。

我保存这个画图板时,弹出了一个MessageBox,但好象这个程序没有截到,记事本的MessageBox也没有截到啊。。。。。这是怎么回事呢?

而且,不我不明白apihook.cpp中开始的一段代码的意思:
// When an application runs on Windows 98 under a debugger, the debugger
// makes the module's import section point to a stub that calls the desired
// function. To account for this, the code in this module must do some crazy
// stuff. These variables are needed to help with the crazy stuff.


// The highest private memory address (used for Windows 98 only)
PVOID CAPIHook::sm_pvMaxAppAddr = NULL;
const BYTE cPushOpCode = 0x68; // The PUSH opcode on x86 platforms


没明白上面这段是啥意思。。。

大侠帮帮我啊?感激不尽
皮皮鲁 2006-01-19
  • 打赏
  • 举报
回复
我这里没问题,大概是你什么地方搞出问题了
sdcer 2006-01-19
  • 打赏
  • 举报
回复
多谢 xing_xing_xing(ζ未名ζ)!!

你帮我解答了第一个疑惑,也就是说,FindWindow()...这段代码可以要,也可以不要。

但第二个问题还是没有解决,程序一运行,主窗口只是一闪而过。。。。。?按照书中介绍,应该出现一个等待MessageBox的窗体才对啊。???

我的系统是windows xp,这个程序应该可以运行在windows xp上吧。。。。???
xing_xing_xing 2006-01-19
  • 打赏
  • 举报
回复
1.这个东西是Windows自带的画笔的窗口标题,中文的是 "未命名 - 画图"
这个是调试用的,改一下名字,然后打开画笔就可以了
内容概要:本文介绍了基于蝴蝶优化算法(Butterfly Optimization Algorithm, BOA)解决电力系统中最优无功功率分配问题的研究,采用IEEE30节点标准测试系统进行仿真验证。通过Matlab编程实现该智能优化算法,对无功电源出力、变压器变比及并联补偿设备等控制变量进行优化调节,以降低网损、改善电压质量、提高系统运行效率为目标,构建多目标优化模型并求解。文中详细阐述了算法原理、数学建模过程、约束条件处理及仿真结果分析,展示了BOA在电力系统无功优化领域的有效性和收敛性能。; 适合人群:电气工程及相关专业背景,具备一定电力系统分析基础和Matlab编程能力的高校研究生、科研人员及从事电力系统优化运行的工程技术人员。; 使用场景及目标:①应用于电力系统运行与控制中的无功优化调度,提升电网经济性与稳定性;②作为智能优化算法在电力系统中应用的教学案例,帮助理解BOA算法的设计思想与实现流程;③为微电网、主动配电网等复杂系统的无功电压协调控制提供技术参考。; 阅读建议:建议读者结合IEEE30节点系统数据文件与Matlab代码进行实操演练,重点关注目标函数构建、约束条件处理及算法参数设置部分,通过调整算法参数观察优化效果变化,深入掌握蝴蝶优化算法的调参规律与工程应用技巧。
内容概要:本文介绍了基于Python的课程达成度分析系统的设计与实现,旨在通过自动化、智能化手段提升高校教学质量评价的科学性与效率。系统整合多源异构教学数据(如成绩、作业、课堂行为等),利用Python强大的数据处理库(如pandas、NumPy、SQLAlchemy)进行数据采集、清洗与融合,并构建标准化的课程目标达成度评价模型。系统采用分层架构,涵盖数据层、业务逻辑层、前端呈现层、安全控制模块及拓展维护层,支持多维度数据分析、异常监测、群体对比与可视化报告生成,形成“评价—反馈—改进”的教学闭环,助力教育信息化与数据驱动决策。文中还提供了关键模块的代码示例,如数据合并、标准化处理与加权计算等。; 适合人群:具备一定Python编程与数据分析基础,从事教育信息化研究、教学质量管理或教育技术开发的高校教师、研究人员及软件开发者。; 使用场景及目标:①实现课程目标达成度的自动化计算与动态监控;②支持多班级、多课程的教学质量横向对比与异常预警;③为专业认证、教学评估和持续改进提供数据支撑;④推动高校教学评价从经验型向数据驱动型转变。; 阅读建议:此资源以实际项目为导向,结合模型设计与代码实践,建议读者结合完整代码与GUI实现深入学习,并根据所在院校的数据结构进行适配开发,重点关注数据标准化、权重配置与可视化交互设计。

16,551

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC相关问题讨论
社区管理员
  • 基础类社区
  • Creator Browser
  • encoderlee
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

        VC/MFC社区版块或许是CSDN最“古老”的版块了,记忆之中,与CSDN的年龄几乎差不多。随着时间的推移,MFC技术渐渐的偏离了开发主流,若干年之后的今天,当我们面对着微软的这个经典之笔,内心充满着敬意,那些曾经的记忆,可以说代表着二十年前曾经的辉煌……
        向经典致敬,或许是老一代程序员内心里面难以释怀的感受。互联网大行其道的今天,我们期待着MFC技术能够恢复其曾经的辉煌,或许这个期待会永远成为一种“梦想”,或许一切皆有可能……
        我们希望这个版块可以很好的适配Web时代,期待更好的互联网技术能够使得MFC技术框架得以重现活力,……

试试用AI创作助手写篇文章吧