最近搞个程序,用到md5加密,结果看了几个md5加密后,相同的数据结果不同,郁闷了!后面找到一个别人的加密程序算的结果一样,还好它里面算法是用dll实现的,呵呵!借来用了!
先用od把它载入,然后查看可执行模块,选择我们的程序,右键查看名称,找到里面MD.dll导入的几个函数的地方,里面支持md2,md4,md5.我只要md5了,右键在每个参考上设置断点,运行,找到计算md5的地方,让它调用md5函数,od断下
断到这里
004520CF . 68 6ED94500 push 0045D96E ; ASCII "sfddfdsfsdf"
004520D4 . 50 push eax
004520D5 . 68 6EF14500 push 0045F16E
004520DA . E8 D34E0000 call <jmp.&MD.MD5>
从call 的地方看.前面3个push是参数了.
函数的基本原型应该可以这样定义 int md5(参数1,参数2,参数3) (一般dll的导出函数都遵循从右到左压参)
现在就是来查清楚每个参数对应的是甚么了.
004520CF . 68 6ED94500 push 0045D96E ; ASCII "sfddfdsfsdf"
从od给的提示看,很明显参数3对应的是 原字符串的地址
004520D4 . 50 push eax
我们看eax 寄存器存的是甚么? 其内容是 0000000B (正好是原字符串长度),基本确定参数2就是参数3的长度了
004520D5 . 68 6EF14500 push 0045F16E
这个是个内存地址,在od的数据窗口里面,选中这个地址段,看到的数据是乱码.(怀疑应该是返回值)
0045F16E C6 B9 90 85 27 A3 D3 74 45 8A 9C 3F 2B 07 B4 C1 乒悈'StE姕?+戳
F8单步跟踪,同时查看 0045F16E 地址的内存数据变化
0045F16E 4E BC CE 0B F5 73 0E E0 53 68 91 A3 47 3A A5 06 N嘉 鮯郤h懀G:?
看内容变化,基本确定是返回值了!
现在函数原型我们就基本确定了!
int md5(char* reback,int len,char* input);
基本来说这边的事情已经就完成了.
现在可以搞程序了
在程序里面先定义函数指针类型
typedef int (_stdcall *MYMD5)(char* reback,int len,char* input);
开始调用dll
HMODULE hDll = NULL;
MYMD5 md5 = NULL;
hDll = ::LoadLibrary("md.dll"); //载入dll
if (hDll)
{
md5 = (MYMD5)::GetProcAddress(hDll,(LPCSTR)4);//载入函数
//在md.dll里面md5函数的编号是4,用工具DEPENDS.EXE可以查看dll的导出函数名和编号
if (md5 == NULL)
{
return FALSE;
}
}
//................
//这里中间就可以使用 函数md5了
//....................
if (hDll)
::FreeLibrary(hDll);//最后释放dll