R-R, 发表于 2020-12-14 12:30

Inline Patch 补丁 C++源码分享了 !

//inline Patch补丁源码
//部分代码搬运至 https://www.52pojie.cn/thread-688291-1-1.html
//添加获取文件 AddressOfEntryPointPEB获取imagebase获取内存实时OEP 主要针对EXE动态内存地址和电脑开始了ALSR




#include "stdafx.h"
#include "windows.h"

int GetOep(TCHAR* PeFileName){

        TCHAR* FileName = PeFileName;
        char* buf = nullptr;
        HANDLE hFile;
        DWORD dwFileSize;
        DWORD ReadSize = 0;
        DWORD OEP = 0;

        hFile = CreateFile(
                FileName, GENERIC_READ | GENERIC_WRITE,
                0,
                NULL,
                OPEN_EXISTING,
                FILE_ATTRIBUTE_NORMAL,
                NULL);

        dwFileSize = GetFileSize(hFile, NULL);
        buf = new char;
        ReadFile(hFile, buf, dwFileSize, &
                ReadSize, NULL);

        PIMAGE_DOS_HEADER pDosH = (PIMAGE_DOS_HEADER)buf;
        PIMAGE_NT_HEADERS32 pNtH = (PIMAGE_NT_HEADERS32)(buf + pDosH->e_lfanew);
        PIMAGE_OPTIONAL_HEADER32 pOptH = (PIMAGE_OPTIONAL_HEADER32)((DWORD)pNtH + IMAGE_SIZEOF_FILE_HEADER + 4);

        if (pDosH->e_magic != IMAGE_DOS_SIGNATURE)
        {
                MessageBoxW(NULL, L"DOS头错误!", L"Error", MB_OK);
                CloseHandle(hFile);
                return 0;
        }
        if (pNtH->Signature != IMAGE_NT_SIGNATURE)
        {
                MessageBoxW(NULL, L"NT头错误!", L"Error", MB_OK);
                CloseHandle(hFile);
                return 0;
        }

        OEP = pOptH->AddressOfEntryPoint;
        delete[] buf;
        CloseHandle(hFile);
        return OEP;
}

STARTUPINFO Si;
PROCESS_INFORMATION Pi;

typedef LONG(NTAPI* _NtQueryInformationProcess)(
        IN HANDLE ProcessHandle,
        IN ULONG ProcessInformationClass,
        OUT PVOID ProcessInformation,
        IN ULONG ProcessInformationLength,
        OUT PULONG ReturnLength OPTIONAL
        );

typedef struct
{
        DWORD ExitStatus;
        DWORD PebBaseAddress;
        DWORD AffinityMask;
        DWORD BasePriority;
        ULONG UniqueProcessId;
        ULONG InheritedFromUniqueProcessId;
} PROCESS_BASIC_INFORMATION;




int _tmain(int argc, _TCHAR* argv[])
{
       
        TCHAR *PePatch = _T("C:\\Users\\Administrator\\Desktop\\1.exe");
        DWORD FileOep = GetOep(PePatch);
       
        if (FileOep == 0){
                MessageBoxW(NULL, L"获取FileOep失败!", L"Error", MB_OK);
                return 0;
        }
        //printf("%x", FileOep);


        BOOL Cret;
        Si = { 0 };
        Si.cb = sizeof(STARTUPINFO);
        PROCESS_INFORMATION Pi = { 0 };
        Cret = CreateProcess(PePatch, NULL, NULL, NULL, FALSE, CREATE_SUSPENDED, NULL, NULL, &Si, &Pi);
        if (!Cret)
        {
                printf("创建进程失败!\n");
                return 0;
        }
       
        _NtQueryInformationProcess ZwQueryInformationProcess;
        HMODULE hNtDll = LoadLibrary(_T("ntdll.dll"));
        if (hNtDll == NULL){
                MessageBoxW(NULL, L"Ntdll加载失败!", L"Error", MB_OK);
                return 0;
        }
        ZwQueryInformationProcess = (_NtQueryInformationProcess)GetProcAddress(hNtDll,"NtQueryInformationProcess");

        if (ZwQueryInformationProcess == NULL) {
                MessageBoxW(NULL, L"ZwQueryInformationProcess地址获取失败!", L"Error", MB_OK);
                FreeLibrary(hNtDll);
                return 0;
        }
        //printf("%x", ZwQueryInformationProcess);
        PROCESS_BASIC_INFORMATION Peb;
        ZwQueryInformationProcess(Pi.hProcess, NULL, (PVOID)&Peb, sizeof(Peb), NULL);
        //printf("%x", Peb.PebBaseAddress);
        DWORD        PebImaggeBase = Peb.PebBaseAddress + 8;
        BOOL ModuleRet;
        LPVOID ModuleBase = new int;
        ModuleRet = ReadProcessMemory(Pi.hProcess, LPCVOID(PebImaggeBase), ModuleBase, 4, NULL);
        if (ModuleRet == 0)
        {
                MessageBoxW(NULL, L"ModuleBase获取失败!", L"Error", MB_OK);
                return 0;
        }
        DWORD MemOep = *((PDWORD)ModuleBase) + FileOep;
        delete ModuleBase;
        //printf("%x", MemOep);

        BOOL bRet = FALSE;
        BYTE szEntryPointData = { 0 };
        bRet = ReadProcessMemory(Pi.hProcess, (LPVOID)MemOep, szEntryPointData, 2, NULL);
        if (!bRet)
        {
                printf("读取入口点数据失败!\n");
                return 0;
        }

        WriteProcessMemory(Pi.hProcess, (LPVOID)MemOep, "\xEB\xFE", 2, NULL);
        if (!bRet)
        {
                printf("写入到入口点数据失败!\n");
                return 0;
        }

        ResumeThread(Pi.hThread);
        CONTEXT Context;
        Context.ContextFlags = 65543;
        GetThreadContext(Pi.hThread, &Context);
        while (Context.Eip != MemOep)
        {
                Sleep(50);
                GetThreadContext(Pi.hThread, &Context);
        }
        SuspendThread(Pi.hThread);

        DWORD dApiAddress = (DWORD)GetProcAddress(GetModuleHandle(TEXT("User32.dll")), "CreateWindowExA");
        printf("dApiAddress = 0x%08x\n", dApiAddress);

        BYTE szApiAddressData = { 0 };

        bRet = ReadProcessMemory(Pi.hProcess, (LPVOID)dApiAddress, szApiAddressData, 2, NULL);
        if (!bRet)
        {
                printf("读API数据失败\n");
                return 0;
        }

        bRet = WriteProcessMemory(Pi.hProcess, (LPVOID)dApiAddress, "\xEB\xFE", 2, NULL);
        if (!bRet)
        {
                printf("写API地址数据失败\n");
                return 0;
        }

        bRet = WriteProcessMemory(Pi.hProcess, (LPVOID)MemOep, szEntryPointData, 2, NULL);
        if (!bRet)
        {
                printf("写API地址数据失败\n");
                return 0;
        }


        ResumeThread(Pi.hThread);
        GetThreadContext(Pi.hThread, &Context);
        while (Context.Eip != dApiAddress)
        {
                Sleep(50);
                GetThreadContext(Pi.hThread, &Context);
        }
        SuspendThread(Pi.hThread);


        //写补丁数据

        LPVOID Address = (LPVOID)0x0040100C;
        BYTE Data[] = {0xC3};
        DWORD Datasize = sizeof(Data);
        WriteProcessMemory(Pi.hProcess, Address, (LPVOID)Data, Datasize, NULL);

        WriteProcessMemory(Pi.hProcess, (LPVOID)dApiAddress, szApiAddressData, 2, NULL);
        ResumeThread(Pi.hThread);
        CloseHandle(Pi.hThread);
        CloseHandle(Pi.hProcess);


        /*
        DWORD dOldProtect = 0;
        VirtualProtectEx(Pi.hProcess, (LPVOID)0x004010FD, Datasize, PAGE_EXECUTE_READWRITE, &dOldProtect);
        if (WriteProcessMemory(Pi.hProcess, (LPVOID)0x004010FD, (LPVOID)bPatchData, Datasize, NULL) == FALSE)
        {
                printf("写补丁失败,错误码:%d\n", GetLastError());
        }
        VirtualProtectEx(Pi.hProcess, (LPVOID)0x004010FD, Datasize, dOldProtect, &dOldProtect);
        */
        getchar();
       
        return 0;


}

朱朱你堕落了 发表于 2020-12-14 12:45

其实我感觉这和inline hook没有啥关系,大家都这么叫,就这么叫了。

lyliucn 发表于 2020-12-14 13:19

能不能分享一下完整源代码。

aaa0827 发表于 2020-12-14 14:01

感谢R大佬!

云柔猫猫 发表于 2020-12-14 14:26

感谢R大佬

Dowson 发表于 2020-12-14 14:33

沙发坐一坐,谢谢楼主分享,日常回贴,一来可以升级,二来也可以赚经验。

kaninai 发表于 2020-12-14 22:10

感谢R大佬
页: [1]
查看完整版本: Inline Patch 补丁 C++源码分享了 !