欢迎来到 嗅灵易学

零基础也能上手的脚本技术课,一对一答疑带你入门

[原创]今天写了个apc注入dll代码,可以当工具使用

[原创]今天写了个apc注入dll代码,可以当工具使用

ring0和ring3都有,像我这样菜鸟写这么个代码真累啊
typedef struct _INJECT_INFO
{
        HANDLE ProcessId;
        wchar_t DllName[1024];
}INJECT_INFO,*PINJECT_INFO;
BOOLEAN InjectDll(PINJECT_INFO InjectInfo)
{
        PEPROCESS Process;
        PETHREAD Thread;
        PKINJECT mem;
        ULONG size;
        PKAPC_STATE ApcState;
        PKAPC apc;
        PVOID buffer;
        PSYSTEM_PROCESS_INFO pSpi;
        LARGE_INTEGER delay;
        buffer=ExAllocatePool(NonPagedPool,1024*1024); // Allocate memory for the system information
        if(!buffer)
        {
                DbgPrint("Error: Unable to allocate memory for the process thread list.");
                return FALSE;
        }
        // Get the process thread list
        if(!NT_SUCCESS(ZwQuerySystemInformation(5,buffer,1024*1024,NULL)))
        {
                DbgPrint("Error: Unable to query process thread list.");
               
                ExFreePool(buffer);
                return FALSE;
        }
        pSpi=(PSYSTEM_PROCESS_INFO)buffer;
        // Find a target thread
        while(pSpi->NextEntryOffset)
        {
                if(pSpi->UniqueProcessId==InjectInfo->ProcessId)
                {
                        DbgPrint("Target thread found. TID: %d",pSpi->Threads[0].ClientId.UniqueThread);
                        break;
                }
                pSpi=(PSYSTEM_PROCESS_INFO)((PUCHAR)pSpi+pSpi->NextEntryOffset);
        }
        // Reference the target process
        if(!NT_SUCCESS(PsLookupProcessByProcessId(InjectInfo->ProcessId,&Process)))
        {
                DbgPrint("Error: Unable to reference the target process.");
               
                ExFreePool(buffer);
                return FALSE;
        }
        DbgPrint("Process name: %s",PsGetProcessImageFileName(Process));
        DbgPrint("EPROCESS address: %#x",Process);
        // Reference the target thread
        if(!NT_SUCCESS(PsLookupThreadByThreadId(pSpi->Threads[0].ClientId.UniqueThread,&Thread)))
        {
                DbgPrint("Error: Unable to reference the target thread.");
                ObDereferenceObject(Process); // Dereference the target process
                ExFreePool(buffer); // Free the allocated memory
                return FALSE;
        }
        DbgPrint("ETHREAD address: %#x",Thread);
        ExFreePool(buffer); // Free the allocated memory
        KeAttachProcess(Process); // Attach to target process's address space
        mem=NULL;
        size=4096;
        // Allocate memory in the target process
        if(!NT_SUCCESS(ZwAllocateVirtualMemory(NtCurrentProcess(),(PVOID*)&mem,0,&size,MEM_COMMIT|MEM_RESERVE,PAGE_EXECUTE_READWRITE)))
        {
            DbgPrint("Error: Unable to allocate memory in the target process.");
                KeDetachProcess(); // Detach from target process's address space
                ObDereferenceObject(Process); // Dereference the target process
                ObDereferenceObject(Thread); // Dereference the target thread
                return FALSE;
        }
        DbgPrint("Memory allocated at %#x",mem);
        mem->LdrLoadDll=LdrLoadDll; // Write the address of LdrLoadDll to target process
        wcscpy(mem->Buffer,InjectInfo->DllName); // Write the DLL name to target process
        RtlInitUnicodeString(&mem->DllName,mem->Buffer); // Initialize the UNICODE_STRING structure
        ApcState=(PKAPC_STATE)((PUCHAR)Thread+ApcStateOffset); // Calculate the address of the ApcState structure
        ApcState->UserApcPending=TRUE; // Force the target thread to execute APC
        memcpy((PKINJECT)(mem+1),InjectDllApc,(ULONG)KernelRoutine-(ULONG)InjectDllApc); // Copy the APC code to target process
        DbgPrint("APC code address: %#x",(PKINJECT)(mem+1));
        apc=(PKAPC)ExAllocatePool(NonPagedPool,sizeof(KAPC)); // Allocate the APC object
        if(!apc)
        {
                DbgPrint("Error: Unable to allocate the APC object.");
                size=0;
                ZwFreeVirtualMemory(NtCurrentProcess(),(PVOID*)&mem,&size,MEM_RELEASE);  // Free the allocated memory
                KeDetachProcess(); // Detach from target process's address space
                ObDereferenceObject(Process); // Dereference the target process
                ObDereferenceObject(Thread); // Dereference the target thread
                return FALSE;
        }
        KeInitializeApc(apc,Thread,OriginalApcEnvironment,KernelRoutine,NULL,(PKNORMAL_ROUTINE)((PKINJECT)mem+1),UserMode,mem); // Initialize the APC
        DbgPrint("Inserting APC to target thread");
        // Insert the APC to the target thread
        if(!KeInsertQueueApc(apc,NULL,NULL,IO_NO_INCREMENT))
        {
                DbgPrint("Error: Unable to insert APC to target thread.");
                size=0;
               
                ZwFreeVirtualMemory(NtCurrentProcess(),(PVOID*)&mem,&size,MEM_RELEASE); // Free the allocated memory
                KeDetachProcess(); // Detach from target process's address space
                ObDereferenceObject(Process); // Dereference the target process
                ObDereferenceObject(Thread); // Dereference the target thread
                ExFreePool(apc); // Free the APC object
                return FALSE;
        }
        delay.QuadPart=-100*10000;
        while(!mem->Executed)
        {
                KeDelayExecutionThread(KernelMode,FALSE,&delay); // Wait for the injection to complete
        }
        if(!mem->DllBase)
        {
                DbgPrint("Error: Unable to inject DLL into target process.");
                size=0;
                ZwFreeVirtualMemory(NtCurrentProcess(),(PVOID*)&mem,&size,MEM_RELEASE);
                KeDetachProcess();
                ObDereferenceObject(Process);
                ObDereferenceObject(Thread);
               
                return FALSE;
        }
        DbgPrint("DLL injected at %#x",mem->DllBase);
        size=0;
        ZwFreeVirtualMemory(NtCurrentProcess(),(PVOID*)&mem,&size,MEM_RELEASE); // Free the allocated memory
        KeDetachProcess(); // Detach from target process's address space
        ObDereferenceObject(Process); // Dereference the target process
        ObDereferenceObject(Thread);  // Dereference the target thread
        return TRUE;
}

上传的附件 KeInject.rar

注意:上传附件及图片大小不得大于30M。

⚠️ 版权声明:
本博客所有内容(含教程、源码、工具)仅供个人技术学习与研究交流使用,严禁商用、倒卖、二次分发及非法用途
未经作者书面授权,任何组织或个人不得转载、复制或用于其他平台,违者将追究相关责任。

0 0 0 举报
复制成功