实验环境:
实验设备环境:windows xp
实验工具:PEID,IDAPro,Ollydbg
实验过程
1、Lab09-03.exe导入了哪些dll?
我们可以通过查找PEID查看导入函数:
但是有些dll是在程序运行的时候才会加载的,所以我们需要采用IDA进行静态分析,如果想要在程序运行中加载dll文件,就需要使用loadlibrary这个API函数,查找imports窗口中的函数,双击进入,在函数上点击ctrl+X获得交叉引用窗口如下:
我们点击第一个引用函数进入:
发现其引用的是dll3.dll文件。
查看第二个引用:
其引用的是user32.dll文件。
2、dll1.dll,dll2.dll,dll3.dll要求的基地址是多少?
此问题我们使用PEID查看,进入后点击子系统获得镜像基地址:
同理dll2.dll,dll3.dll。
3、当使用OD调试exe文件时,为dll1.dll,dll2.dll,dll3.dll分配的基地址是什么?
使用OD打开此程序之后点击在屏幕上点击M查看当前内存引用情况:
我们会发现其基地址数值。现在我们使OD跳转到dll3.dll的位置查看其基地址。在IDA中查看dll3.dll的调用位置是:
即是401041
,在OD中跳转至此内存位置,在其下方下断点之后运行,这样dll3.dll才会被载入到程序中,此时我们再点击M,会发现:
4、当exe程序调用dll1.dll中的一个导入函数时,这个导入函数都做了些什么?
我们在IDAA中发现exe程序调用的第一个dll1函数是dllprint函数:
现在我们再使用IDA打开dl1.dll文件,在左侧窗口中找到dllprint函数点击进入以后:
发现其调用了一个未知函数,进入以后发现其存在两个参数,dllprint函数中的第一个参数是一段字符串,观察这个函数带有%d等字符,所以我们可以认为这个函数就是print
打印函数。我们再查看第二个参数位于eax寄存器中,其值取决于 dword_10008030
的值,点击进入以后查看其交叉引用:
第一个w标志说明是对这个值进行了写入,点击进入:
我们会发现其写入值就是GetCurrentProcessId
函数的返回值,也就是说这个变量保存的就是当前运行进程的ID的返回值。
总结来说dllprint的目的就是打印当前运行进程的ID。
5、当exe文件使用writefile时,写入的文件名是什么?
根据上图所示,如果我们想要清除writefile的文件句柄,我们就需要扥西DLL2RETURNJ函数,使用IDA打开DLL2文件,因为针对dll2其调用了两个函数,我们都分析一下:
(1)dllprint函数
同样的方法我们查看其交叉引用的w标志函数如下:
此时我们会发现此变量中存储的是temp.txt文件的句柄。也就是说dll2print
函数就是打印temp.txt文件的句柄。
(2)dll2returnj函数
其目的是将dword_1000B078
的值保存起来,保存到eax中。dword_1000B078
返回的就是文件句柄。
现在我们返回exe文件的IDA窗口:
这个eax寄存器中返回的就是temp.exe文件的句柄。所以writefile写入的就是temp.txt文件。
6、当exe文件调用NetScheduleJobAdd创建一个Job时,从哪里获取第二个参数的数据?
其在调用结束writefile函数以后会利用LoadLibraryA
载入dll3.dll,并且利用GetProcAddress
获取dll3print
函数的地址,以及DLL3GetStructure
函数的地址。
现在我们将DLL3.dll载入到IDA中,查看第dll3print函数,同样的操作查看打印数据的交叉引用,点击进入以后:
(1)dll3print
其下面调用了MultiByteToWideChar
函数,此函数的目的是将字符串转化为宽字符,整个过程就是利用此函数将上面的’ping www.malwareanalysisbook.com’转化为宽字符并保存在WideCharStr
中。所以dllprinte打印的就是字符串在内存中的地址。
(2)DLL3GetStructure
我们会发现其将dword_1000B0A0
存储在了eax寄存器中值的位置(在exe程序中就是保存在Buffer中),点击进入查看其交叉引用,点击进入:
圈出的数据就是AF_INFO类型的结构体。即第二个参数。
7、如何将dll2.dll加载到IDApro中,使得他与OD使用的加载地址匹配?
首先我们将dll2加载到IDA中:
在上图中圈出的部分要勾选上,之后就会出现:
这个是要输入基地址,我们利用OD查看基地址数据:
可以发现od中的dll2地址为003C0000
,在IDA中输入3C0000
。此时就完成了基地址的转换。