在内存中读取函数的ShellCode并执行
下面是一个例子,实现的效果是将fun1函数的十六进制读取出来,在内存中将str1的地址改成str2,分配一块内存,将改好的函数的ShellCode写入并执行。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 |
// FunTest.cpp : 定义控制台应用程序的入口点。 // // #include "stdafx.h" #include <windows.h> #pragma comment(lib,"user32.lib") char *str1 = "aaaa"; //字符串指针1 char *str2 = "bbbb"; //字符串指针2 void fun1() { MessageBox(0,str1,0,0); } void fun2() { MessageBox(0,"2",0,0); } int _tmain(int argc, _TCHAR* argv[]) { fun1(); //调用fun1函数测试一下 //获取fun1函数的大小 int iFun1Size = ((DWORD)fun2) - ((DWORD)fun1); printf("fun1 size: %d\n",iFun1Size); //获取fun1函数的十六进制内容 BYTE *pFun1Body = new BYTE [iFun1Size]; memcpy(pFun1Body,&fun1,iFun1Size); for (int i=0;i<=iFun1Size;i++) { printf("%x",*(pFun1Body+i)); } printf("\n"); //打印字符指针地址 DWORD dwstrAddress1 = (DWORD)&str1; DWORD dwstrAddress2 = (DWORD)&str2; printf("Address1 %x\n",dwstrAddress1); printf("Address2 %x\n",dwstrAddress2); //判断 for (int i=0;i<(iFun1Size-4);i++) { DWORD *dwPtr = (DWORD *)((BYTE *)pFun1Body + i); //找str1的地址 if (*dwPtr == dwstrAddress1) { *dwPtr = (DWORD)dwstrAddress2; //替换字符串指针地址 printf("dwstrAddress1 found\n"); } else if (*dwPtr == dwstrAddress2) { printf("dwstrAddress2 found\n"); } } //分配内存 PVOID pData = VirtualAlloc(NULL,iFun1Size,MEM_COMMIT,PAGE_EXECUTE_READWRITE); if(!pData) { DWORD dwError = GetLastError(); printf("VirtualAllocEx error %d \n",dwError); return 0; } //写内存 HANDLE h = OpenProcess(PROCESS_ALL_ACCESS,0,GetCurrentProcessId()); if(!WriteProcessMemory(h,pData,pFun1Body,iFun1Size,0)) { DWORD dwError = GetLastError(); printf("WriteProcessMemory error %d\n",dwError); return 0; } //执行 _asm { mov eax,pData; call eax } //释放内存 VirtualFree(pData,0,MEM_RELEASE); delete []pFun1Body; getchar(); return 0; } |
转载请注明:exchen's blog » 在内存中读取函数的ShellCode并执行