
SystemInformer 中 DLL 注入到底怎么实现2 个原语、1 条调用链与 3 层排查指南【免费下载链接】systeminformerA free, powerful, multi-purpose tool that helps you monitor system resources, debug software and detect malware. Brought to you by Winsider Seminars Solutions, Inc. https://windows-internals.com项目地址: https://gitcode.com/GitHub_Trending/sy/systeminformerSystemInformer 是 Winsider 出品的系统监控与调试工具内置了跨进程加载模块的能力。本文直接带你定位SystemInformer DLL 注入在当前代码里的真实落点用户态注入原语在phlib/nativethread.c内核通信层在phlib/kph.c反向防护在phlib/nativejob.c。读完后你能说清注入走的是哪条路径、需要哪些进程权限、失败时该从哪一步开始查。快速结论真正干活的只有两个函数phlib/nativethread.c里的PhLoadDllProcess远程线程 LoadLibraryW和PhLoadDllProcessApcThreadAPC 线程变体。它们是可复用的用户态原语不是 GUI 菜单按钮。它不在kphmsg.c网传注入结构定义在kphlib/kphmsg.c的KPH_CREATE_THREAD_REQUEST是误认kphmsg.h里是KPHM_THREAD_CREATE等消息枚举属于内核通信而非注入。内核通信层在phlib/kph.cKphConnect/KphOpenProcess/KphReadVirtualMemory等kphlib/提供跨进程打开、读内存等底层能力。反向能力phlib/nativejob.c用JOB_OBJECT_UILIMIT_INJECTION阻止从 Job 外部向其中进程注入 DLL用于阻止注入。没有plugins/ExtendedTools/inject.c该插件文件在当前仓库不存在请勿按此路径查找。一、背景为什么注入在这里是分散的概念SystemInformer 前身是 Process Hacker跨进程加载模块的能力最初用于把扩展 DLL 装进目标进程。随着 Windows 内核防护演进团队把在别的进程里跑一段代码这件事拆成了用户态原语 内核通信层 反向限制三块。因此当你按旧版本经验去找一个统一的注入入口时会扑空——它在不同层各占一角。二、功能地图注入能力落在哪一层用户态注入层核心phlib/nativethread.c提供两个互不依赖的原语思路一致在目标进程里写一段 DLL 路径 → 以目标进程内的LoadLibraryW为起点拉起线程 → 等待其返回。NTSTATUS PhLoadDllProcess( _In_ HANDLE ProcessHandle, _In_ PPH_STRINGREF FileName, // 待注入的 DLL 路径 _In_opt_ ULONG Timeout // 加载超时毫秒 );内部关键一步是创建远程线程入口与参数都指向目标进程自身status PhCreateUserThread( ProcessHandle, ..., loadLibraryW, // 起点目标进程内的 LoadLibraryW fileNameBaseAddress, // 参数已写入的 DLL 路径 threadHandle, NULL );PhLoadDllProcessApcThread是 APC 变体用RtlExitUserThread收尾适用于需要以 APC 方式投递的场景。两者开头都有一次KphProcessLevel级别校验权限不足直接返回STATUS_ACCESS_DENIED。内核通信层phlib/kph.c封装了与内核驱动的通信KphConnect、KphOpenProcess、KphOpenProcessToken、KphReadVirtualMemory、KphOpenThread等。消息类型定义在kphlib/include/kphmsg.h如KPHM_THREAD_CREATE、KPHM_THREAD_EXECUTE。这一层给注入原语提供以更高上下文打开/操作进程的底座。反向防护层phlib/nativejob.c配置 Job 对象 UI 限制从外部阻止注入uiRestrictions.UIRestrictionsClass JOB_OBJECT_UILIMIT_INJECTION; // 禁止 Job 外进程向其内注入 DLL历史遗留SystemInformer/heapinfo.c第 1225 行残留一行被注释的//if (!(threadHandle CreateRemoteThread(属于早期销毁堆功能的旧技术路线现已停用仅作考古痕迹保留。三、路径索引目录 / 文件关键函数 / 常量作用phlib/nativethread.cPhLoadDllProcess远程线程 LoadLibraryW注入原语phlib/nativethread.cPhLoadDllProcessApcThreadAPC 线程注入变体phlib/nativejob.cJOB_OBJECT_UILIMIT_INJECTION阻止 Job 外部进程注入 DLLphlib/kph.cKphConnect/KphOpenProcess/KphReadVirtualMemory内核驱动通信层kphlib/include/kphmsg.hKPHM_THREAD_CREATE/KPHM_THREAD_EXECUTE内核-用户消息定义KSystemInformer/ksidll.defKsiInsertQueueApc/KsiQueueWorkItem内核导出APC/WorkItem非内存读写接口SystemInformer/heapinfo.c//CreateRemoteThread(...)历史遗留已注释说明ksidll.def的真实导出围绕 APC、DPC、WorkItem、线程生命周期等内核原语并不包含KsiReadVirtualMemory/KsiSendMessage这类远程内存读写导出——跨进程读写由phlib/kph.c的用户态封装承担。四、最小使用步骤围绕原语的前置条件取得目标进程句柄权限需覆盖PROCESS_QUERY_LIMITED_INFORMATION、PROCESS_CREATE_THREAD、PROCESS_VM_OPERATION、PROCESS_VM_READ、PROCESS_VM_WRITE。调用PhLoadDllProcess(ProcessHandle, DllPath, Timeout)Timeout设得过短可能导致目标进程来不及加载而崩溃请按 DLL 复杂度取值。函数内部会解析目标进程运行库地址 → 定位LoadLibraryW→ 分配并写入路径 →PhCreateUserThread拉线程 →PhWaitForSingleObject等待返回 → 清理句柄与内存。需要在 Job 环境里禁止外部注入时改为配置JOB_OBJECT_UILIMIT_INJECTION。五、调用链六、验证与排查确认注入是否发生在目标进程内查模块列表是否出现该 DLL或在调用后检查NTSTATUS是否为成功值。返回STATUS_ACCESS_DENIED优先检查KphProcessLevel级别校验与句柄访问位是否齐全而非先怀疑 DLL 本身。超时/进程无响应调大TimeoutPhLoadDllProcess的文档明确提示超时未加载可能使进程崩溃。找不到旧路径若按kphmsg.c结构体或plugins/ExtendedTools/inject.c查找失败属正常——真实原语在phlib/nativethread.c。需要阻止注入核对 Job 是否设置了JOB_OBJECT_UILIMIT_INJECTION可参考 phlib/nativejob.c。七、相关资源用户态注入原语phlib/nativethread.c内核通信封装phlib/kph.c、消息定义 kphlib/反向防护phlib/nativejob.c内核组件与导出KSystemInformer/构建与贡献说明README.md、CONTRIBUTING.md获取代码git clone https://gitcode.com/GitHub_Trending/sy/systeminformer【免费下载链接】systeminformerA free, powerful, multi-purpose tool that helps you monitor system resources, debug software and detect malware. Brought to you by Winsider Seminars Solutions, Inc. https://windows-internals.com项目地址: https://gitcode.com/GitHub_Trending/sy/systeminformer创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考