吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 1915|回复: 10
收起左侧

[C&C++ 转载] 利用shellCode跨进程调用函数x86

[复制链接]
揰掵佲 发表于 2021-3-17 18:01
之前发过一个帖子,是用易语言实现的
调用QQ/TIM算法实现获取当前登陆账号和ClientKey
https://www.52pojie.cn/thread-1037514-1-1.html

最近这段时间呢,一直在搞跨进程调用,经过不断的测试,找到一个稳定跨进程调用的方法,简单明了.易语言比较熟练,代码早已经封装完成,这次用的是C++还是以https://www.52pojie.cn/thread-1037514-1-1.html为例子跨进程取出指定QQ进程的QQ号
先看效果
2.jpg
然后说一下思路
在进程中利用以下代码调用函数,可以达到稳定
[Asm] 纯文本查看 复制代码
  00000000  55                push ebp
  00000001  89E5              mov ebp, esp
  00000003  C9                leave
  00000004  58                pop eax
  00000005  870424            xchg eax, [esp]
  00000008  FFE0              jmp eax
  0000000A  89EC              mov esp, ebp
  0000000C  5D                pop ebp
  0000000D  C3                ret


构建的远程调用函数有最大支持15个参数的传递,只支持int类型
[Asm] 纯文本查看 复制代码
/*
* 定义调用函数的代码
* push ebp
* mov ebp,esp
* sub esp,0x3c
* push arg15
* push arg14
* push arg13
* push arg12
* push arg11
* push arg10
* push arg9
* push arg8
* push arg7
* push arg6
* push arg5
* push arg4
* push arg3
* push arg2
* push arg1
* call pCallFun    //这里需要注意的是,我们call的是上面的汇编代码,并非指定的函数
* mov dword [resEax],eax
* add esp,0x3c
* mov esp,ebp
* pop ebp
* ret
*/


代码比较粗糙,贴上来
[C++] 纯文本查看 复制代码
void getPushBin(int arg, LPVOID& pShellCode, HANDLE hProcess)
{
    if (arg >= -128 && arg <= 127)
    {
        unsigned char code = { 106 };
        WriteProcessMemory(hProcess, pShellCode, &code, 1, NULL);
        pShellCode = LPVOID((int)pShellCode + 1);
        WriteProcessMemory(hProcess, pShellCode, (LPVOID)arg, 1, NULL);
        pShellCode = LPVOID((int)pShellCode + 1);
    }
    else {
        unsigned char code = { 104 };
        WriteProcessMemory(hProcess, pShellCode, &code, 1, NULL);
        pShellCode = LPVOID((int)pShellCode + 1);
        WriteProcessMemory(hProcess, pShellCode, (LPVOID)&arg, 4, NULL);
        pShellCode = LPVOID((int)pShellCode + 4);
    }
 
}
 
void getCallBin(int src, int Dest, LPVOID& pShellCode, HANDLE hProcess)
{
    unsigned char code = { 232 };
    WriteProcessMemory(hProcess, pShellCode, &code, 1, NULL);
    pShellCode = LPVOID((int)pShellCode + 1);
    int arg = Dest - src - 5;
    WriteProcessMemory(hProcess, pShellCode, (LPVOID)&arg, 4, NULL);
    pShellCode = LPVOID((int)pShellCode + 4);
}
 
void getresEaxBin(int src, LPVOID& pShellCode, HANDLE hProcess)
{
    unsigned char code = { 163 };
    WriteProcessMemory(hProcess, pShellCode, &code, 1, NULL);
    pShellCode = LPVOID((int)pShellCode + 1);
    WriteProcessMemory(hProcess, pShellCode, (LPVOID)&src, 4, NULL);
    pShellCode = LPVOID((int)pShellCode + 4);
}
int runRemoteFunc(HANDLE hProcess, int pFunc, int arg1 = 0, int arg2 = 0, int arg3 = 0, int arg4 = 0, int arg5 = 0, int arg6 = 0, int arg7 = 0, int arg8 = 0, int arg9 = 0, int arg10 = 0, int arg11 = 0, int arg12 = 0, int arg13 = 0, int arg14 = 0, int arg15 = 0) {
 
 
 
 
    /*
    * 定义callFunCode 这个是调用call的代码
      00000000  55                push ebp
      00000001  89E5              mov ebp, esp
      00000003  C9                leave
      00000004  58                pop eax
      00000005  870424            xchg eax, [esp]
      00000008  FFE0              jmp eax
      0000000A  89EC              mov esp, ebp
      0000000C  5D                pop ebp
      0000000D  C3                ret
   */
    unsigned char callFunCode[] = { 85, 137, 229, 201, 88, 135, 4, 36, 255, 224, 137, 236, 93, 195 };
    SIZE_T codelen = sizeof(callFunCode);
    //分配适当内存
    LPVOID pCallFun = VirtualAllocEx(hProcess, NULL, codelen, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
    //准备写入代码
    bool res = WriteProcessMemory(hProcess, pCallFun, callFunCode, codelen, NULL);
    if (!res)
    {
        //写入失败,释放内存
        MessageBox(NULL, L"写入shellCode失败", L"提示", 0);
        VirtualFreeEx(hProcess, pCallFun, 0, MEM_RELEASE);
        return -1;
    }
    //分配调用函数的地址
    LPVOID pShellCodeStart = VirtualAllocEx(hProcess, NULL, 0x200, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
    //保存原有地址
    LPVOID pShellCode = pShellCodeStart;
    //分配返回值地址
 
 
    LPVOID resEax = VirtualAllocEx(hProcess, NULL, 4, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
 
    /*
    * 定义调用函数的代码
    * push ebp
    * mov ebp,esp
    * sub esp,0x3c
    * push arg15
    * push arg14
    * push arg13
    * push arg12
    * push arg11
    * push arg10
    * push arg9
    * push arg8
    * push arg7
    * push arg6
    * push arg5
    * push arg4
    * push arg3
    * push arg2
    * push arg1
    * call pCallFun
    * mov dword [resEax],eax
    * add esp,0x3c
    * mov esp,ebp
    * pop ebp
    * ret
    */
 
    unsigned char pfunHead[6] = { 85,137,229,131,236,60 };
    codelen = sizeof(pfunHead);
    WriteProcessMemory(hProcess, pShellCode, pfunHead, codelen, NULL);
    pShellCode = LPVOID((int)pShellCode + codelen);
    getPushBin(arg15, pShellCode, hProcess);
    getPushBin(arg14, pShellCode, hProcess);
    getPushBin(arg13, pShellCode, hProcess);
    getPushBin(arg12, pShellCode, hProcess);
    getPushBin(arg11, pShellCode, hProcess);
    getPushBin(arg10, pShellCode, hProcess);
    getPushBin(arg9, pShellCode, hProcess);
    getPushBin(arg8, pShellCode, hProcess);
    getPushBin(arg7, pShellCode, hProcess);
    getPushBin(arg6, pShellCode, hProcess);
    getPushBin(arg5, pShellCode, hProcess);
    getPushBin(arg4, pShellCode, hProcess);
    getPushBin(arg3, pShellCode, hProcess);
    getPushBin(arg2, pShellCode, hProcess);
    getPushBin(arg1, pShellCode, hProcess);
    getCallBin((int)pShellCode, pFunc, pShellCode, hProcess);
    getresEaxBin((int)resEax, pShellCode, hProcess);
    unsigned char pfunEnd[] = { 131,196,60,137,236,93,195 };
    codelen = sizeof(pfunEnd);
    WriteProcessMemory(hProcess, pShellCode, pfunEnd, codelen, NULL);
    pShellCode = LPVOID((int)pShellCode + codelen);
    DWORD Tid;
    HANDLE tHandle = CreateRemoteThread(hProcess, NULL, 0, (LPTHREAD_START_ROUTINE)pShellCodeStart, NULL, NULL, &Tid);
    if (!tHandle)
    {
        VirtualFreeEx(hProcess, pCallFun, 0, MEM_RELEASE);
        VirtualFreeEx(hProcess, resEax, 0, MEM_RELEASE);
        VirtualFreeEx(hProcess, pShellCodeStart, 0, MEM_RELEASE);
        MessageBox(NULL, L"执行线程失败失败", L"提示", 0);
        return -1;
    }
    WaitForSingleObject(tHandle, -1);
    int resa = 0;
    ReadProcessMemory(hProcess, resEax, &resa, 4, 0);
    VirtualFreeEx(hProcess, pCallFun, 0, MEM_RELEASE);
    VirtualFreeEx(hProcess, resEax, 0, MEM_RELEASE);
    VirtualFreeEx(hProcess, pShellCodeStart, 0, MEM_RELEASE);
    return resa;
}
 
 
 
int main()
{
    int nRetCode = 0;
    HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, false, 20368);// 人懒固定了QQ的PID
    HMODULE hModule = LoadLibraryW(L"kernel32.dll");
    int pGetModuleHandleA = (int)GetProcAddress(hModule, "GetModuleHandleA");
    int pGetProcAddress = (int)GetProcAddress(hModule, "GetProcAddress");
    unsigned char dllName[] = "KernelUtil.dll";
    unsigned char funName[] = "?GetSelfUin@Contact@Util@@YAKXZ";
    LPVOID pDllName = VirtualAllocEx(hProcess, NULL, sizeof(dllName), MEM_COMMIT, PAGE_EXECUTE_READWRITE);
    WriteProcessMemory(hProcess, pDllName, &dllName, sizeof(dllName), 0);
    LPVOID pFunName = VirtualAllocEx(hProcess, NULL, sizeof(funName), MEM_COMMIT, PAGE_EXECUTE_READWRITE);
    WriteProcessMemory(hProcess, pFunName, &funName, sizeof(funName), 0);
    int kernelMoudle = runRemoteFunc(hProcess, pGetModuleHandleA, (int)pDllName);
    int getUin = runRemoteFunc(hProcess, pGetProcAddress, kernelMoudle, (int)pFunName);
    int res = runRemoteFunc(hProcess, getUin);
    CloseHandle(hProcess);
    cout << "函数执行完毕:结果是\n\r";
    cout << res;
    cout << "\n\r\n\r";
    return nRetCode;
}


其中 以下3个函数是构建汇编代码的,因为,当无参调用时,默认为0 从  unsigned char* 之后会缺少,导致汇编代码错乱,所以分别在函数内部直接写入到内存

[C++] 纯文本查看 复制代码
getPushBin //push xxx
getCallBin //call xxx
getresEaxBin //mov dword [xxx],eax

求指教如何解决,代码比较糙,轻喷

RemoteFunc.zip (7.86 KB, 下载次数: 12)

免费评分

参与人数 2吾爱币 +2 热心值 +2 收起 理由
zhuzhuxia111 + 1 + 1 我很赞同!
朱朱你堕落了 + 1 + 1 感谢发布原创作品,吾爱破解论坛因你更精彩!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

wylksy 发表于 2021-3-17 18:08
感谢分享
mangmangxiyu 发表于 2021-3-17 18:11
turuoyang 发表于 2021-3-17 18:20
智趣库 发表于 2021-3-17 18:27
学到了,感觉分享
lin326326 发表于 2021-3-17 18:43
厉害,感谢分享
朱朱你堕落了 发表于 2021-3-17 20:05
孤陋寡闻了,第一次吹说跨进程调用的,膜拜大佬。
 楼主| 揰掵佲 发表于 2021-3-17 20:09
朱朱你堕落了 发表于 2021-3-17 20:05
孤陋寡闻了,第一次吹说跨进程调用的,膜拜大佬。

表述不好,也叫远程
bester 发表于 2021-3-17 22:28
看起来得实际跑一下代码才能看得懂
夜泉 发表于 2021-3-18 04:52
感谢发布原创作品,吾爱破解论坛因你更精彩
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-11-25 19:15

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表