直接操纵内存,动态调用API函数,强悍!!
//大家有没有发现VB调用API函数的方法很“另类”?来看看这个程序:/*[转载]在程序中动态调用API函数
原创作者:Lightning(kxsystem@)
这是KsSafetyCenter中的一个技术,代码的注释比较少,自己看着理解吧^。^,算是我自己一次大的开源吧。。
目前仅仅是STDCALL的函数调用,其它类型的函数调用大家可以自己写出。
代码可能有错,欢迎指出。*/
// 注:代码必须用VC编译,否则像DEV C++这样的编译器不会通过编译的。
//----------------------------------------KsRunFunc.h----------------------------------//
/* 原创作者:Lightning(kxsystem@) */
/* 转载和使用请声明,谢谢 */
#define FUNC_NAME_LENGTH 64 // 函数名最大长度
#define FUNC_PARAM_MAX 16 // 参数个数最大值
#define KSPARAM_DWORD 0x0 // 参数类型
#define KSPARAM_STRING 0x1
#include <windows.h>
#include <stdio.h>
// KS是我的代号kxsystem的简写。
// 信息头
struct KSFUNC_CALL
{
KSFUNC_CALL* pNext; // 可以用一个链表将所有调用过的函数连接起来,便于制作"调用堆栈"
DWORD dwSize; // 本结构大小,包括后面缓冲区大小
BOOL bRaiseError; // 出错了吗??
BOOL bIsKernel; // 内核模式? 现在还没有使用.
char pszFuncName[FUNC_NAME_LENGTH]; // 函数名
DWORD pfn; // 函数指针
DWORD hModule;// 模块句柄
DWORD dwReturn; // 返回值
int nParamCount; // 参数个数
char cTypeOfParams[FUNC_PARAM_MAX]; // 参数类型
DWORD dwRVAs[FUNC_PARAM_MAX]; // 参数地址偏移,使用时需要加上GetBuffer()
PBYTE GetBuffer(){ return (PBYTE)(this+1); } // 返回本结构以后的内存区.
};
#ifndef _KERNEL
DWORD htoi(const char* szHex)
{
DWORD temp;
scanf(szHex, "%x", &temp);
return temp;
}
/*
下面这个函数的代码很难理解,我又比较L,与主要技术无关,主要是对字符串的解析.具体代码就不列出了.
主要的功能为:解析字符串,将函数地址,函数模块,函数名,函数参数及其偏移地址,以及是否对参数进行取值等信息写入到KSFUNC_CALL结构中.
*/
BOOL InitFunctionCall( char* lpString, KSFUNC_CALL* fc)
{
//这里没有代码,作者好懒
}
#endif
DWORD CallFunction(KSFUNC_CALL* fc)
{
DWORD Addr=fc->pfn;
int nCount=fc->nParamCount;
DWORD dwPop=nCount*sizeof(DWORD) ;
DWORD dwRet;
DWORD Value;
__try
{
for(int b=fc->nParamCount-1;b>=0 ;b--)
{
Value=(DWORD)(fc->GetBuffer()+fc->dwRVAs[b]);
if(fc->cTypeOfParams [b]==KSPARAM_DWORD)
{
Value=*(DWORD*)Value;
}
_asm mov edx,Value
_asm push edx
}
_asm
{
mov eax,Addr
call eax
// add esp,dwPop
mov dwRet,eax
}
fc->dwReturn =dwRet;
}
__except(EXCEPTION_EXECUTE_HANDLER)
{
fc->bRaiseError =TRUE;
}
return dwRet;
}
//有了以上的头文件,其它的就简单得多了,下面是一个简单的console程序。
int main()
{
char st[0x100];
memset(st,0,0x100);
KSFUNC_CALL* p=(KSFUNC_CALL*)st;
if(InitFunctionCall("user32.dll!MessageBoxA(0,\"Hello World!\",\"App\",0);",p))
{
printf("Function Name=%s\n",p->pszFuncName);
printf("Function Module=0x%0X\n",p->hModule);
printf("Function Address=0x%0X\n",p->pfn);
if(p->nParamCount !=0)
{
for(int b=0;b<p->nParamCount ;b++)
{
if(p->cTypeOfParams [b]==KSPARAM_DWORD)
printf("Function Parameter %d = 0x%0X\n",b+1,*(DWORD*)(p->GetBuffer()+p->dwRVAs[b]) );
else
printf("Function Parameter %d = %s\n",b+1,(char*)(p->GetBuffer()+p->dwRVAs[b]));
}
}
printf("Return =0x%0X",CallFunction(p));
}
getchar();
return 0;
}
[[it] 本帖最后由 flyue 于 2008-5-1 21:56 编辑 [/it]]