吾爱破解 - LCG - LSG |安卓破解|病毒分析|www.52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 88|回复: 4
上一主题 下一主题
收起左侧

[求助] 求助写段代码对EXE打补丁

[复制链接]
跳转到指定楼层
楼主
朱朱你堕落了 发表于 2024-9-22 22:48 回帖奖励
66吾爱币
本帖最后由 朱朱你堕落了 于 2024-9-23 03:27 编辑

目标测试程序"abcdefg.exe"是个x64位程序,动态基址。
我需要写个64位的补丁程序,对abcdefg.exe进行补丁。
现在遇到个小问题,如何获取到目标程序的动态基址。
迷糊了,搞不出来了,请大佬完善一下,暂时只有这点CB了。

[C++] 纯文本查看 复制代码
#include "stdafx.h"
#include <Windows.h>
#include <Psapi.h>
#pragma comment(lib, "Psapi.lib"
//static void dbgprintex(LPCSTR fmt,...)
//{
////#ifdef _DEBUG
//        va_list marker;
//        va_start(marker,fmt);
//        char sbuf_dbgprintex[1024]={0};        
//        vsprintf_s(sbuf_dbgprintex,fmt,marker);
//        va_end(marker);
//        OutputDebugStringA(sbuf_dbgprintex);
////#endif
//}


#define dbgprintex printf


int _tmain(int argc, _TCHAR* argv[])
{
        CHAR m_ExePath[] = "abcdefg.exe";
        STARTUPINFOA si = {0};
        si.cb = sizeof(si);
        PROCESS_INFORMATION pi = {0};
        BOOL bRet = FALSE;
        //我这里写暂停行不行?
        bRet = CreateProcessA(m_ExePath, NULL, NULL, NULL, FALSE, CREATE_SUSPENDED, NULL, NULL, &si, &pi);
        //bRet = CreateProcessA(m_ExePath, NULL, NULL, NULL, FALSE, NULL, NULL, NULL, &si, &pi);
        if (!bRet)
        {
                dbgprintex("创建子进程失败!\n");
                return 0;
        }

        HANDLE m_Process = OpenProcess(PROCESS_ALL_ACCESS, 0, pi.dwProcessId);
        if (m_Process == NULL)
        {
                dbgprintex("打开子进程失败! 错误码: %d\n", GetLastError());
                CloseHandle(pi.hThread);
                CloseHandle(pi.hProcess);
                return 0;
        }

      


        //程序动态基址,这里如何动态获取基址?动态基址+偏移 计算后写补丁

        DWORD dwOffset = 0x14AA;

        //这样肯定不对的,因为这里是启动目标EXE,GetModuleHandleA(NULL);获取的是自身无意义的基址/
        //这里需要获取的是被补丁的目标EXE的基址(abcdefg.exe)。
        //DWORD dwExeBase = (DWORD)GetModuleHandleA(NULL);

        DWORD dwPatchAddr = dwExeBase + dwOffset;

        BYTE bPatchData[] = {0x90, 0x90};
        DWORD dOldProtect = 0;
        VirtualProtectEx(m_Process, (LPVOID)dwPatchAddr, sizeof(bPatchData), PAGE_EXECUTE_READWRITE, &dOldProtect);

        if(WriteProcessMemory(m_Process, (LPVOID)dwPatchAddr, (LPVOID)bPatchData, sizeof(bPatchData),NULL) == FALSE)
        {
                dbgprintex("写补丁失败,错误码:%d\n", GetLastError());
        }

        VirtualProtectEx(m_Process, (LPVOID)dwPatchAddr, sizeof(bPatchData), dOldProtect, &dOldProtect);

        ResumeThread(pi.hThread);
        CloseHandle(pi.hThread);
        CloseHandle(pi.hProcess);

        system("pause");

        return 0;
}


测试程序:
https://www.123pan.com/s/YL29-XLTRh

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

沙发
romobin 发表于 2024-9-22 23:45
int main() {
    HANDLE hProcess;
    DWORD_PTR baseAddress;
    MODULEINFO moduleInfo;

    // 获取当前进程的句柄
    hProcess = GetCurrentProcess();

    // 获取主模块的信息
    if (GetModuleHandleEx(
        GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT,
        (LPCTSTR)&baseAddress, // 传入程序的任意地址,这里传入main函数的地址
        (HMODULE *)&moduleInfo)) {
        printf("Base Address: %p\n", (void *)moduleInfo.lpBaseOfDll);
        printf("Module Size: %lu\n", moduleInfo.SizeOfImage);
    }

    CloseHandle(hProcess);
    return 0;
}


或者我有发过 aslr 补丁工具,   让动态地址固定 然后再patch ,
另外如果程序加壳的话 需要hook 程序api 等程序解码完成后再写内存,无壳的话最简单方法就是创建进程并且暂停进程 ,写内存补丁后恢复进程

点评

https://f.ws28.cn/f/f5fdqe40wh9 复制链接到浏览器打开  发表于 2024-9-23 01:08
我的测试程序就是无壳的,如果使用工具去掉动态基址,大佬,我就不需要发贴求助了,固定基址写死就行了,那太简单了。  详情 回复 发表于 2024-9-22 23:49
3#
 楼主| 朱朱你堕落了 发表于 2024-9-22 23:49 |楼主
romobin 发表于 2024-9-22 23:45
int main() {
    HANDLE hProcess;
    DWORD_PTR baseAddress;

我的测试程序就是无壳的,如果使用工具去掉动态基址,大佬,我就不需要发贴求助了,固定基址写死就行了,那太简单了。
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

快速回复 收藏帖子 返回列表 搜索

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

GMT+8, 2024-9-23 03:35

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

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