利用rundll32执行程序的技术分析与利用方法
0x00 前言
本文详细分析通过rundll32.exe加载特定DLL并利用其导出函数执行程序的技术原理和实现方法。该技术可以用于渗透测试中的命令执行和横向移动,具有较高的实用价值。
0x01 技术原理概述
rundll32基本用法
rundll32是Windows系统自带的工具,用于加载DLL并调用其导出函数。官方文档描述其用法为:
rundll32 <dllname>,<entrypoint> <optional arguments>
其中:
<entrypoint>:DLL的导出函数名<optional arguments>:传递给导出函数的参数
导出函数的定义如下:
void CALLBACK EntryPoint(
HWND hwnd,
HINSTANCE hinst,
LPSTR lpszCmdLine,
int nCmdShow
);
<optional arguments>对应导出函数中的LPSTR lpszCmdLine参数。
OpenURL函数分析
在url.dll中,导出函数OpenURL调用了ShellExecute API:
HINSTANCE ShellExecute(
_In_opt_ HWND hwnd,
_In_opt_ LPCTSTR lpOperation,
_In_ LPCTSTR lpFile,
_In_opt_ LPCTSTR lpParameters,
_In_opt_ LPCTSTR lpDirectory,
_In_ INT nShowCmd
);
关键点:
- 当第二个参数为NULL时,表示执行默认操作"open"
- 第三个参数lpFile指定要打开的程序或文件路径
因此,执行:
rundll32.exe url.dll,OpenURL calc.exe
实际上相当于:
ShellExecuteA(hwnd, NULL, "calc.exe", NULL, NULL, nShowCmd);
0x02 技术细节深入
动态调试验证
使用Immunity Debugger动态调试可以验证:
- 执行
rundll32.exe url.dll,OpenURL calc.exe - 跟踪到
ShellExecuteA调用 - 确认传入参数确实为"calc.exe"
其他可利用的导出函数
在url.dll中,除了OpenURL外,FileProtocolHandler函数同样调用了ShellExecute:
rundll32.exe url.dll,FileProtocolHandler calc.exe
支持的文件类型
通过ShellExecute执行不仅支持exe,还支持多种脚本文件:
-
JS文件:
WScript.Echo("1");执行:
rundll32.exe url.dll,OpenURL C:\test\echo.js -
HTA文件:
<HTML> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <HEAD> <script language="VBScript"> Window.ReSizeTo 0, 0 Window.moveTo -2000,-2000 Set objShell = CreateObject("Wscript.Shell") objShell.Run "calc.exe" self.close </script> <body>demo</body> </HEAD> </HTML>执行:
rundll32.exe url.dll,OpenURLA C:\test\calc.hta -
URL快捷方式:
[InternetShortcut] URL=c:\windows\system32\calc.exe执行:
rundll32.exe ieframe.dll,OpenURL C:\test\calc.url
0x03 扩展利用方法
查找其他可利用的DLL
通过PowerShell脚本批量扫描%windir%\system32下的DLL,查找包含OpenURL导出函数的DLL:
$DllSearchPath = dir c:\windows\system32\*.dll
foreach($DllName in $DllSearchPath){
$DllName.Name
}
扫描结果发现以下DLL也包含OpenURL函数:
- ieframe.dll
- shdocvw.dll
ieframe.dll分析:
其OpenURL函数要求执行.url文件,内容需为InternetShortcut格式。
其他已知可利用的DLL
hexacorn发现的另一个可利用DLL:
rundll32 zipfldr.dll, RouteTheCall calc.exe
0x04 批量扫描脚本
改进的PowerShell脚本要点:
-
处理异常DLL(如auditpolmsg.dll):
try { $OffsetPtr = New-Object System.Intptr -ArgumentList $($HModule.ToInt64() + $ExportRVA) } catch { Write-Warning "Error processing $DllName" continue } -
处理内存读取错误(如avicap.dll):
try { $EXPORT_DIRECTORY_FLAGS = [system.runtime.interopservices.marshal]::PtrToStructure($OffsetPtr, [type]$IMAGE_EXPORT_DIRECTORY) } catch { Write-Warning "Memory read error for $DllName" continue }
完整脚本参考:
https://raw.githubusercontent.com/3gstudent/Writeup/master/Find-OpenURL.ps1
0x05 防御建议
-
监控rundll32异常调用:
- 监控rundll32加载非常见DLL的行为
- 特别关注带有命令行参数的调用
-
限制脚本执行:
- 控制JS、HTA等脚本文件的执行权限
- 监控异常脚本文件创建和执行
-
应用白名单:
- 实施应用白名单策略,限制未授权程序执行
-
日志分析:
- 收集和分析进程创建日志(如Sysmon事件ID 1)
- 关注rundll32的父进程和命令行参数
0x06 总结
本文详细分析了利用rundll32执行程序的技术原理,包括:
- rundll32加载DLL的基本机制
- OpenURL等导出函数如何调用ShellExecute
- 支持执行的多种文件类型
- 批量扫描可利用DLL的方法
- 其他已知的可利用DLL
这种技术具有较高的隐蔽性,可用于渗透测试的多个阶段,防御方需要有针对性地加强监控和防护。