能力值:
( LV2,RANK:10 )
|
-
-
2 楼
象你这要的要求,我觉得可以用这样的方法。
比如,你要调试kernel32.dll,先用ida静态分析找到要调试的api,然后在api入口处,修改为int 3,当然还要记得
入口处的原始代码,比如mov edi,edi,修改为int 3以后,存盘,记住是磁盘文件kernel32.dll被修改为int 3了,而不是内存被修改为int 3.重新启动系统,这样,在系统重启以后,从磁盘载入kernel32.dll的时候,都会自动在
修改的地方int 3被中断,你使用vmware和windbg双机调试就可以了。注意在中断以后,必须把int 3的指令修改为mov edi,edi再继续执行。
或者,比如你要中断的函数前几个字节是0xcc,那么可以利用前几个字节,就不必每次都中断都手工修改int 3为原始指令了。
比如下面这个样子。
41002a db 0xcc
41002b db 0xcc
41002c db 0xcc
41002d db 0xcc
41002e db 0xcc
41002f db 0xcc
apistart:
410030 mov edi,edi
410032 push ebp
......
以上代码可以修改为
41002a int 3
41002b mov edi,edi ;mov edi,edi是其他指令也可以,注意其占用了几个字节,要保证有足够的空间容纳这几个字节的修改
41002d jmp 410032
41002f db 0xcc
apistart:
410030 jmp 41002a
410032 push ebp
......
这样就不用每次中断以后再手工修改int3的指令为mov edi,edi
而且这样修改以后,如果不想中断了,把int 3修改为nop就没有中断了。
|
能力值:
( LV9,RANK:170 )
|
-
-
3 楼
感谢兄弟的主意,这个方法我想过,只是要下断的函数是常用函数,那样就会让系统死掉了。
另外,想对KERNEL32下手,这事就有些大了。因为W7要想改核心文件,事还是挺多的。
我今天又整来一台机器,不行就只能是二机联了。唉。虚拟机无法虚拟双输出的问题。
头痛。
|
能力值:
( LV2,RANK:10 )
|
-
-
4 楼
你既然说要对核心dll下断,又说怕系统死掉,这就自相矛盾了。我这个方法就是对核心dll下断啊,但是系统不会死掉,只是执行到这个被断的api的时候,会中断到windbg里面,在windbg里面继续执行就可以了,只是,如果这个api被系统执行的次数过多,那么被中断的次数比较多而已,稍微麻烦一点。但是你的要求是要中断核心api啊,不知道你要断那个 api,你自己就用这个方法中断这个api就是,肯定不会系统死掉的嘛。再说 kernel32.dll不是驱动程序,x64系统也不会受到PG影响的,只有驱动层才受PG监视,而且sys文件要修改比较麻烦,因为有校验和,而dll不是sys文件,没有校验和,直接修改就是了。
如果嫌系统执行这个api的次数过多造成中断次数过多,那还可以在修改api的时候找一大段空闲地区,比如有100,200个字节甚至更多的空闲地区,写入一些条件判断,符合条件的才中断,不符合的就放过,那样就可以避免中断次数过多的问题。
还有一个方法,就是写一个驱动程序,对要中断的kernel32.dll进行inline hook,跳转到你自己的代码,在你自己的代码里面中断就可以了。这样不必修改kernel32.dll。
=========================
我刚才试了一下,手工修改kernel32.dll的GetModuleHandleA,能够用windbg断下来,从启动到进入桌面,大概断下了30-40次,最后进入桌面,系统不会死,是正常的,而且达到了要求,把所有的GetModuleA的调用都断下来了,不管是哪个进程调用的,都必然被断下来。而且如果你不想系统被自动断下来,可以修改int 3的地方为nop,就不会断下30-40次了,自动进入桌面,然后你在启动你想要调试的程序以前,再用windbg先断下来,修改nop为int 3,再继续执行,在被调试机里面再运行你想调试的程序,就会在GetModuleHandleA被断下来。
==============================
最后,我又发现,其实你不用修改kernel32.dll磁盘文件,直接在内存中修改GetModuleHandleA的代码,原始的是mov edi,edi,你直接在内存中修改成 int 3,nop就可以了,因为所有的进程执行的kernel32.dll都是同一份拷贝,所以你修改的时候,
任何进程执行GetModuleHandleA 都会转到你修改的地方来,因为所有的拷贝是对应同一个物理地址,而不是对应多份拷贝,所以你修改一次内存就可以了,不必修改 kernel32.dll的磁盘文件。
|
能力值:
( LV3,RANK:20 )
|
-
-
5 楼
ssdt Hook?
|
能力值:
( LV9,RANK:170 )
|
-
-
6 楼
原理我看明白了,但现在的情况是这样的。
我要分析的软件是ABC,这个程序在启动之后,会用这个软件启动dmw.exe程序,这个应该是管理窗口的程序,并且,在DMW程序是放入了软件ABC自己的二个动态库。这个DMW程序,还会调用uxsms系统的服务程序,如果UXSMS在起动之后,找不到相关的硬件,就会在第2个屏幕上出现一个错误提示,找到了就不会出。
我试验了多次,直接在W7的任务管理器中启动或关闭uxsms服务,就可以看到屏幕上的错误信息,UXSMS具体的运行方式我不清楚,但我知道他要与硬件通讯一定会用到的函数。
我以前在W2K下直接用SICE就可下断点,直接在函数头上断下来,但现在是采用W7系统(这个软件只能在W7上运行)后,我注入了UXSMS之后事,下了函数的断点也不断,而且屏幕显示也受了影响!
我的Q:76451925,有空请兄弟指教一下。谢谢。
|
能力值:
( LV2,RANK:10 )
|
-
-
7 楼
你要断的是那个函数,在那个DLL里面,你就像我断kernel32.dll的GetModuleHandleA一样, 修改mov edi,edi为int 3,nop就可以了啊。当然,如果起始语句不是mov edi,edi,那么是别的语句,就要注意执行那个语句,要保留那个语句执行以后的结果,这样才可以让系统继续执行下去而不会出错。
|
能力值:
( LV2,RANK:10 )
|
-
-
8 楼
可以用x64_dbg呀,应该能满足你的要求
|
能力值:
( LV9,RANK:170 )
|
-
-
9 楼
尝试了直接将函数头的字节直接改成CC后,将windbg设成系统调试程序,让程序调用DLL,结果是DMW直接出一个C0000083错误后,退出,WINDBG未抓到错误处理,之后DMW退出,程序是用UXSMS调用运行的。
接着蒙圈!
|
能力值:
( LV12,RANK:210 )
|
-
-
10 楼
用windbg内核调试。设置好符号。先写个简单程序调用一下int3,运行,断下来。随后敲.reload命令载入符号,然后你就可以对kernel32等dll里面的函数下断点了,例如
bp kernel32!CreateThread
断点是全局的,任何进程调用这个函数都会断下来。
|
|
|