zoukankan      html  css  js  c++  java
  • Windows 回调监控 <二>

    在之前的文章Windows 回调监控 <一> 总结了关于CreateProcessNotify,CreateProcessNotifyEx和LoadImageNotify一些用法,之后产生了一个思路,既然在进程创建的时候加载.exe文件会执行我们的回调函数,那么如果在我们回调函数之中对内存中的.exe文件的导入表增加一个项,这样进程会不会加载我们事先准备好的.dll文件,如果成功加载我们的dll话,就注入成功了。  

    #pragma once
    
    #include <ntifs.h>
    #include <ntimage.h>
    #include <WINDEF.H>
    
    VOID WPOFF();
    VOID WPON();
    VOID UnloadDriver(PDRIVER_OBJECT DriverObject);
    VOID LoadImageNotifyRoutine(PUNICODE_STRING FullImageName,HANDLE  ProcessId,PIMAGE_INFO  ImageInfor);
    extern CHAR*  PsGetProcessImageFileName(PEPROCESS EProcess);
    VOID UnicodeToChar(PUNICODE_STRING uniSource, CHAR *szDest);
    
    #include "LoadImage.h"
    
    
    PIMAGE_IMPORT_DESCRIPTOR g_OldImportDesc;
    KIRQL Irql;
    PEPROCESS g_TargetProcess;
    HANDLE    g_TargetProcessId;
    
    NTSTATUS DriverEntry(IN PDRIVER_OBJECT DriverObject, IN PUNICODE_STRING RegisterPath)
    {
    
        DbgPrint("驱动加载
    ");
        DriverObject->DriverUnload = UnloadDriver;
        PsSetLoadImageNotifyRoutine((PLOAD_IMAGE_NOTIFY_ROUTINE)LoadImageNotifyRoutine);
        return STATUS_SUCCESS;
    }
    
    VOID UnloadDriver(PDRIVER_OBJECT DriverObject)
    {
        PsRemoveLoadImageNotifyRoutine((PLOAD_IMAGE_NOTIFY_ROUTINE)LoadImageNotifyRoutine);
        DbgPrint("驱动卸载
    ");
    }
    
    
    
    VOID LoadImageNotifyRoutine(PUNICODE_STRING FullImageName,HANDLE  ProcessId,PIMAGE_INFO  ImageInfor)
    {
        NTSTATUS Status;
        PVOID DriverEntryAddress = NULL;
        char szFullImageName[260]={0};
        PEPROCESS TatgetProcess = NULL;
        KAPC_STATE apcState;
        BOOLEAN       bAttached =FALSE;
        HANDLE    hProcess;
        Status  = PsLookupProcessByProcessId(ProcessId,&TatgetProcess);
        if (!NT_SUCCESS(Status))
        {
            return ;
        }
        if (strstr(PsGetProcessImageFileName(TatgetProcess),"cc.exe")) //当前进程是cc.exe
        {
            UnicodeToChar(FullImageName,szFullImageName);
    
            if (strstr(szFullImageName,"cc.exe"))  //加载的是cc.exe
            {
                g_TargetProcessId = ProcessId;
                Status = ObOpenObjectByPointer(TatgetProcess, 
                    OBJ_KERNEL_HANDLE | OBJ_CASE_INSENSITIVE, 
                    NULL, 
                    GENERIC_ALL, 
                    *PsProcessType, 
                    KernelMode, 
                    &hProcess
                    );
                if (!NT_SUCCESS(Status))
                {
                    ObDereferenceObject(TatgetProcess);
                    return; 
                }
                g_TargetProcess = TatgetProcess;
                __try
                {
                    //KeStackAttachProcess(TatgetProcess,&apcState);
                    if (MmIsAddressValid(ImageInfor->ImageBase))
                    {
                        PIMAGE_DOS_HEADER pDos;
                        PIMAGE_NT_HEADERS pHeader = NULL;
                        PIMAGE_IMPORT_DESCRIPTOR  pImportDesc;
                        //ZwUnmapViewOfSection(hProcess,ImageInfor->ImageBase);
                        ULONG nImportDllCount;
                        PVOID ulImageBase = ImageInfor->ImageBase;
                        ULONG nNewImportSize;
                        ULONG nNewDllNameSize = 0x20;
                        PIMAGE_IMPORT_DESCRIPTOR lpNewImportDesc = NULL;
                        PVOID lpDllName = NULL;
                        IMAGE_IMPORT_DESCRIPTOR Add_ImportDesc;
                        PIMAGE_THUNK_DATA        lpNewThunkData = NULL;
                        ULONG nNewThunkDataSize = 0x20;
                        PIMAGE_IMPORT_BY_NAME lpImportApi = NULL;
                        ULONG nNewImportApiSize  = 0x20;
                        pDos =(PIMAGE_DOS_HEADER) ulImageBase;
    
                        pHeader = (PIMAGE_NT_HEADERS)((ULONG)ulImageBase+(ULONG)pDos->e_lfanew);
                        pImportDesc  = (PIMAGE_IMPORT_DESCRIPTOR)((ULONG)pHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress 
                            + (ULONG)ulImageBase);
                        //导入表项个数
                        nImportDllCount = pHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].Size / sizeof(IMAGE_IMPORT_DESCRIPTOR);
    
                        g_OldImportDesc = pImportDesc;//原始的导入表
    
                        nNewImportSize = sizeof(IMAGE_IMPORT_DESCRIPTOR)*(nImportDllCount+1);//加上自己的
    
                        Status = ZwAllocateVirtualMemory(NtCurrentProcess(), &lpNewImportDesc, 0, &nNewImportSize,
                            MEM_COMMIT, PAGE_EXECUTE_READWRITE);
                        if (!NT_SUCCESS(Status))
                        {
                            ObDereferenceObject(TatgetProcess);
                            ObDereferenceObject(TatgetProcess);
                            return;
                        }
                        RtlZeroMemory(lpNewImportDesc,nNewImportSize);
    
                        Status = ZwAllocateVirtualMemory(hProcess, &lpDllName, 0, &nNewDllNameSize,
                            MEM_COMMIT, PAGE_EXECUTE_READWRITE);
                        if (!NT_SUCCESS(Status))
                        {
                            ZwFreeVirtualMemory(hProcess,&lpNewImportDesc,0,MEM_RELEASE);
                            ObDereferenceObject(TatgetProcess);
                            ObDereferenceObject(TatgetProcess);
                            return;
                        }
    
                        RtlZeroMemory(lpDllName,nNewDllNameSize);
    
                        //ThunkData
                        Status = ZwAllocateVirtualMemory(hProcess, &lpNewThunkData, 0, &nNewThunkDataSize,
                            MEM_COMMIT, PAGE_EXECUTE_READWRITE);
                        if (!NT_SUCCESS(Status))
                        {
                            ZwFreeVirtualMemory(hProcess,&lpNewImportDesc,0,MEM_RELEASE);
                            ZwFreeVirtualMemory(hProcess,&lpDllName,0,MEM_RELEASE);
                            ObDereferenceObject(TatgetProcess);
                            ObDereferenceObject(TatgetProcess);
                            return;
                        }
                        RtlZeroMemory(lpNewThunkData,nNewThunkDataSize);                    
                        //IMAGE_IMPORT_BY_NAME
                        Status = ZwAllocateVirtualMemory(hProcess, &lpImportApi, 0, &nNewImportApiSize,
                            MEM_COMMIT|MEM_TOP_DOWN, PAGE_EXECUTE_READWRITE);
                        if (!NT_SUCCESS(Status))
                        {
                            ZwFreeVirtualMemory(hProcess,&lpNewImportDesc,0,MEM_RELEASE);
                            ZwFreeVirtualMemory(hProcess,&lpDllName,0,MEM_RELEASE);
                            ZwFreeVirtualMemory(hProcess,&lpNewThunkData,0,MEM_RELEASE);
                            ObDereferenceObject(TatgetProcess);
                            ObDereferenceObject(TatgetProcess);
                            return;
                        }
                        RtlZeroMemory(lpImportApi,nNewImportApiSize);
                        //原始的导入表,留出一个表项
                        RtlCopyMemory(lpNewImportDesc+1,pImportDesc,sizeof(IMAGE_IMPORT_DESCRIPTOR)*nImportDllCount);
                        lpImportApi->Hint = 0;
                        RtlCopyMemory(lpImportApi->Name,"DllMain",0x20);
                        lpNewThunkData->u1.AddressOfData = (ULONG)lpImportApi-(ULONG)ulImageBase;                
                        Add_ImportDesc.OriginalFirstThunk = (ULONG)lpNewThunkData-(ULONG)ulImageBase;
                        Add_ImportDesc.TimeDateStamp = 0;
                        Add_ImportDesc.ForwarderChain = 0;
                        RtlCopyMemory(lpDllName,"test.dll",0x20);
                        Add_ImportDesc.Name = (ULONG)lpDllName-(ULONG)ulImageBase;
                        Add_ImportDesc.FirstThunk = Add_ImportDesc.OriginalFirstThunk;                    
                        RtlCopyMemory(lpNewImportDesc,&Add_ImportDesc,sizeof(IMAGE_IMPORT_DESCRIPTOR));
                        WPOFF(); //修改Descriptor
                        pHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].Size += sizeof(IMAGE_IMPORT_DESCRIPTOR);
                        pHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress = (ULONG_PTR)lpNewImportDesc - (ULONG_PTR)ulImageBase;
                        WPON();
    
                    }
                    //KeUnstackDetachProcess(&apcState);
                }__except(EXCEPTION_EXECUTE_HANDLER){
                }
                ObDereferenceObject(TatgetProcess);
            }
        }
    
        ObDereferenceObject(TatgetProcess);
    }
    
    VOID WPOFF()
    {
        ULONG_PTR cr0 = 0;
        Irql = KeRaiseIrqlToDpcLevel();
        cr0 =__readcr0();
        cr0 &= 0xfffffffffffeffff;
        __writecr0(cr0);
    
    }
    
    
    VOID WPON()
    {
    
        ULONG_PTR cr0=__readcr0();
        cr0 |= 0x10000;
        __writecr0(cr0);
        KeLowerIrql(Irql);
    }
    
    VOID UnicodeToChar(PUNICODE_STRING uniSource, CHAR *szDest)
    {                                                  
        ANSI_STRING ansiTemp;                                
        RtlUnicodeStringToAnsiString(&ansiTemp,uniSource,TRUE);   
    
        strcpy(szDest,ansiTemp.Buffer);
        RtlFreeAnsiString(&ansiTemp);
    }
  • 相关阅读:
    RocketMQ(十):数据存储模型的设计与实现
    常用sql语句
    配色方案
    WPF界面MahApps.Metro之应用
    使用 Zendesk maxwell 对接 kinesis (include producer and consumer)
    oracle报错【ORA-01017:用户名/口令无效;登录被拒绝】问题处理
    oracle报错【ORA-28000:帐户已被锁定】问题处理
    $(window).load(function(){})和$(document).ready(function(){})的区别
    HttpClientFactory 结合 Polly 轻松实现重试机制
    ocelot 中间件的变化
  • 原文地址:https://www.cnblogs.com/lanrenxinxin/p/4731544.html
Copyright © 2011-2022 走看看