动态库注入--APC注入
- APC(异步过程调用)
1)当EXE里某个线程执行到SleepEx()或者WaitForSingleObjectEx()时(此时该线程处于可警惕状态),系统就会产生一个软中断。
2)当线程再次被唤醒时,此线程会首先执行APC队列中的被注册的函数。
3)利用QueueUserAPC()这个API可以在软中断时向线程的APC队列插入一个函数指针,如果我b们插入的是Loadlirary()执行函数的话,就能达到注入DLL的目的。
- APC注入DLL流程
a根据进程ID得到进程句柄
b枚举进程的线程
c在目标进程中申请内存(用来储存动态库的绝对地址)
d调用WriteProcessMemory在申请的内存处写入动态库地址
e调用QueueUserAPC为每个线程提交APC到APC队列
- 代码实现
// InjectByAPC.cpp : 定义控制台应用程序的入口点。 // #include "stdafx.h"#define _WIN32_WINNT 0x0400 #define WIN32_LEAN_AND_MEAN // 从 Windows 头中排除极少使用的资料 #include<Windows.h> #include <iostream> #include <Tlhelp32.h> using namespace std;typedef struct _THREADID_LIST_ {DWORD ThreadID;_THREADID_LIST_ *pNext; }THREADIDLIST,*PTHREADIDLIST; DWORD GetProcessID(const TCHAR* szProcessName); PTHREADIDLIST InsertTid(PTHREADIDLIST ThreadIDList, DWORD ThreadId); int EnumThreadID(DWORD ProcessID, PTHREADIDLIST ThreadIDList); DWORD EnumThread(HANDLE ProcessHandle, PTHREADIDLIST ThreadIDList);int main() {PTHREADIDLIST ThreadIDList = (PTHREADIDLIST)malloc(sizeof(THREADIDLIST));if (ThreadIDList == NULL){return 0;}RtlZeroMemory(ThreadIDList, sizeof(THREADIDLIST));DWORD ProcessID = 0;if ((ProcessID = GetProcessID("explorer.exe")) == 0xFFFFFFFF){printf("进程ID获取失败!\n");return 0;}EnumThreadID(ProcessID, ThreadIDList);HANDLE ProcessHandle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, ProcessID);if (ProcessHandle == NULL){return 0;}EnumThread(ProcessHandle, ThreadIDList);getchar();getchar();return 0; }DWORD GetProcessID(const TCHAR* szProcessName) {PROCESSENTRY32 pe32 = { 0 };pe32.dwSize = sizeof(PROCESSENTRY32);HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);if (hSnapshot == INVALID_HANDLE_VALUE){return -1;}if (!Process32First(hSnapshot, &pe32)){return -1;}do{if (!_strnicmp(szProcessName, pe32.szExeFile, strlen(szProcessName))){printf("%s的PID是:%d\n", pe32.szExeFile, pe32.th32ProcessID);return pe32.th32ProcessID;}} while (Process32Next(hSnapshot, &pe32));return -1; } // 枚举线程ID int EnumThreadID(DWORD ProcessID, PTHREADIDLIST ThreadIDList) {int i = 0;THREADENTRY32 te32 = { 0 };te32.dwSize = sizeof(THREADENTRY32);HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, ProcessID);if (hSnapshot != INVALID_HANDLE_VALUE){if (Thread32First(hSnapshot, &te32)){do{if (te32.th32OwnerProcessID == ProcessID){if (ThreadIDList->ThreadID == 0){ThreadIDList->ThreadID = te32.th32ThreadID;}else{if (NULL == InsertTid(ThreadIDList, te32.th32ThreadID)){printf("插入失败!\n");return 0;}}}} while (Thread32Next(hSnapshot, &te32));}}return 1; } PTHREADIDLIST InsertTid(PTHREADIDLIST ThreadIDList, DWORD ThreadId) {PTHREADIDLIST pCurrent = NULL;PTHREADIDLIST pNewMember = NULL;if (ThreadIDList == NULL){return NULL;}pCurrent = ThreadIDList;while (pCurrent != NULL){if (pCurrent->pNext == NULL){//// 定位到链表最后一个元素// pNewMember = (PTHREADIDLIST )malloc(sizeof(THREADIDLIST));if (pNewMember != NULL){pNewMember->ThreadID = ThreadId;pNewMember->pNext = NULL;pCurrent->pNext = pNewMember;return pNewMember;}else{return NULL;}}pCurrent = pCurrent->pNext;}return NULL; }DWORD EnumThread(HANDLE ProcessHandle, PTHREADIDLIST ThreadIDList) {//默认第一个?PTHREADIDLIST CurrentThreadID = ThreadIDList;const char szInjectModName[] = "J:\\注入\\InjectByAPC\\x64\\Debug\\DLL.dll";DWORD Length = strlen(szInjectModName);PVOID Address = VirtualAllocEx(ProcessHandle,NULL, Length, MEM_COMMIT | MEM_TOP_DOWN, PAGE_EXECUTE_READWRITE);if (Address != NULL){SIZE_T ReturnLength;////将动态库的地址写进去// if (WriteProcessMemory(ProcessHandle, Address, (LPVOID)szInjectModName, Length, &ReturnLength)){while (CurrentThreadID){HANDLE ThreadHandle = OpenThread(THREAD_ALL_ACCESS, FALSE, CurrentThreadID->ThreadID);if (ThreadHandle != NULL){//// 注入DLL到指定进程//Address LoadLibraryA 参数// QueueUserAPC((PAPCFUNC)LoadLibraryA, ThreadHandle, (ULONG_PTR)Address);}printf("TID:%d\n", CurrentThreadID->ThreadID);CurrentThreadID = CurrentThreadID->pNext;}}}return 0; }
转载于:https://www.cnblogs.com/banchen/p/6682804.html
动态库注入--APC注入相关推荐
- DLL注入-APC注入
APC注入 APC注入的原理是利用当线程被唤醒时APC中的注册函数会被执行的机制,并以此去执行我们的DLL加载代码,进而完成DLL注入的目的,其具体流程如下: 1)当EXE里某个线程执行到Sl ...
- 【Android 逆向】Android 进程注入工具开发 ( 远程进程注入动态库文件操作 | 注入动态库 加载 业务动态库 | 业务动态库启动 | pthread_create 线程开发 )
文章目录 前言 一.加载 libnattive.so 动态库 二. libnattive.so 动态库启动 三. pthread_create 线程开发 四. 线程执行函数 前言 libbridge. ...
- 【Android 逆向】Android 进程代码注入原理 ( 注入本质 | 静态注入和动态注入 | 静态注入两种方式 | 修改动态库重打包 | 修改 /data/app/xx/libs 动态库 )
文章目录 一.注入本质 二.静态注入和动态注入 三.静态注入两种方式 ( 修改动态库重打包 | 修改 /data/app/packageName/libs/ 下的动态库 ) 一.注入本质 进程注入本质 ...
- 【Android 逆向】函数拦截实例 ( 函数拦截流程 | ① 定位动态库及函数位置 )
文章目录 一.函数拦截流程 二.定位动态库及函数位置 一.函数拦截流程 函数拦截流程 : 定位动态库及函数位置 : 获取该动态库在内存中的位置 , 以便于 查找函数位置 ; 插桩 : 在函数的入口处插 ...
- 【Android 逆向】Android 进程注入工具开发 ( 远程进程 注入动态库 文件操作 | Android 进程读取文件所需的权限 | fopen 打开文件标志位 | 验证文件权限 )
文章目录 前言 一.Android 进程读取文件所需的权限 二.fopen 打开文件标志位 三.验证文件权限 前言 一.Android 进程读取文件所需的权限 通过 注入工具 , 将 libbridg ...
- 【Android 逆向】Android 进程注入工具开发 ( 注入代码分析 | 注入工具收尾操作 | 关闭注入的动态库 | 恢复寄存器 | 脱离远程调试附着 )
文章目录 一.dlclose 函数简介 二.关闭注入的 libbridge.so 动态库 三.恢复寄存器 四.脱离远程调试附着 一.dlclose 函数简介 dlclose 函数的作用是 卸载一个 指 ...
- 【Android 逆向】Android 进程注入工具开发 ( 注入代码分析 | 获取注入的 libbridge.so 动态库中的 load 函数地址 并 通过 远程调用 执行该函数 )
文章目录 一.dlsym 函数简介 二.获取 目标进程 linker 中的 dlsym 函数地址 三.远程调用 目标进程 linker 中的 dlsym 函数 获取 注入的 libbridge.so ...
- 【Android 逆向】Android 进程注入工具开发 ( 注入代码分析 | 远程调用 目标进程中 libc.so 动态库中的 mmap 函数 三 | 等待远程函数执行完毕 | 寄存器获取返回值 )
文章目录 前言 一.等待远程进程 mmap 函数执行完毕 二.从寄存器中获取进程返回值 三.博客资源 前言 前置博客 : [Android 逆向]Android 进程注入工具开发 ( 注入代码分析 | ...
- 【Android 逆向】Android 进程注入工具开发 ( 注入代码分析 | 远程调用 目标进程中 libc.so 动态库中的 mmap 函数 二 | 准备参数 | 远程调用 mmap 函数 )
文章目录 一.准备 mmap 函数的参数 二.mmap 函数远程调用 一.准备 mmap 函数的参数 上一篇博客 [Android 逆向]Android 进程注入工具开发 ( 注入代码分析 | 远程调 ...
最新文章
- ob_start ob_end_clean的用法 fetch
- 恢复mysql数据库详细图解_binlog恢复mysql数据库超详细步骤
- c语言订餐管理系统报告,用c语言编程小型的订餐管理系统,谁会啊?
- 高性能mysql整理
- 【spring boot】新建项目,实现HelloWorld
- 分页offset格式_Thinkphp5 原生sql分页操作
- 记一次TCP连接异常故障解决
- vsphere6.0实验拓扑-虚拟机版
- VSCode插件开发全攻略
- 移动通信原理学习笔记之一
- matlab 反复激活无效——许可证到期
- 两万字的CAPL语法基础,一篇文章带你入门
- Rust学习:13.1_返回值和错误处理之panic 深入剖析
- 要闻君说: 百度云喜提信息安全首证;紫光展锐携5G芯片进击2019MWC;OPPO首发5G手机惊艳亮相……...
- 受了点小伤,心情怎么就变坏了呢?
- 使用PHP实现密保卡功能
- 两阶段市场投标策略。 电力市场程序。 日前日内竞价 提出了日前电力市场和实时电力市场下充电站的投标策略
- HR不得不知的Excel技能——模板篇
- 【SSL】2128可可摘苹果
- 利用eda函数对文本数据进行增强
热门文章
- 解析 | 如何从频域的角度解释CNN(卷积神经网络)?
- 腾讯开源最大规模多标签图像数据集,刷新行业数据集基准
- linux中波浪号代表什么_建筑电气施工图纸中BV、ZRBLV和TC、SC符号代表什么?
- 用字典存储学生成绩查询_中考用分数评价学生音体美成绩未尝不是好事
- IDEA Docker 插件安装
- abp mysql .net core_ABP .Net Core Entity Framework迁移使用MySql数据库
- java volatile实例_Java的Volatile实例用法及讲解
- [BZOJ3238][AHOI2013]差异 [后缀数组+单调栈]
- webpack gulp grunt 简单介绍
- Swift - 推送之本地推送(UILocalNotification)添加Button的点击事件