浅谈.Net Profiling在红队中的使用

admin 2024年6月20日09:45:06评论5 views字数 3360阅读11分12秒阅读模式
前言

.NET Profiling 是一组用于开发性能分析工具的接口,用于监控和分析 .NET 应用程序的各种行为。近日,有研究员将该项技术用于横向移动,本文主要对此技术在红队中的使用做介绍。

01 .Net Profiling

.NET Profiling 用于监控和分析 .NET 应用程序的各种行为。通过调用这些接口,开发人员可以创建自定义的性能分析器,深入了解应用程序的性能瓶颈、内存使用、线程行为等,从而进行优化和改进。

.Net Profiling API分为.Net Framework和.Net Core两个版本,Framework中大部分的API都适用于.Net Core。主要的API接口有两个:

  • ICorProfilerCallback: 定义了所有分析事件的回调接口,例如方法调用、垃圾回收等。
  • ICorProfilerInfo: 提供了查询和控制被分析应用程序的信息,例如获取模块信息、设置分析标志等。
下面列举几个有意思的API:

  • ICorProfilerCallback2::GarbageCollectionFinished GC(垃圾回收)完成时,该回调函数被调用
  • ICorProfilerCallback::JITCompilationStarted 通过该回调函数,我们可以知道哪个函数开始JIT(即时编译)
  • ICorProfilerCallback::AssemblyLoadStarted 通过该回调函数,我们可以知道哪些程序集被加载
  • ICorProfilerInfo4::RequestReJIT 通过该方法,我们可以强制重新JIT某个方法,这意味着可以动态修改IL代码
02 .Net Profiler

.Net Profiler是调用.Net Profiling接口编写的分析器,本身以dll形式出现。这个dll和Java中的agent类似,需要注入到CLR或者CoreCLR中。注入方式也有两种,一种是任意.Net进程启动时由CLR或CoreCLR自动加载,另一种是在任意.Net程序运行中执行Attach。这两种方式类似于Java Agent的premain和agentmain,但实际上比Java要复杂和重型。

第一种方式是通过设置环境变量实现的,适用于.Net Core和.Net Framework 如下所示。

CORECLR_ENABLE_PROFILING为1,代表允许分析器加载到.Net进程

CORECLR_PROFILER 分析器dll将检查传递的CLSID是否正确

CORECLR_PROFILER_PATH 代表分析器dll的路径

setx CORECLR_ENABLE_PROFILING=1 setx CORECLR_PROFILER={805A308B-061C-47F3-9B30-F785C3186E71}setx CORECLR_PROFILER_PATH=C:DotNextMoscow2019-masterDebugDotNext.Profiler.Windows.dll
设置好上述变量后,任意.Net进程启动都会自动加载分析器Dll

第二种方式,用到了ICLRProfiling::AttachProfile 接口。.Net FrameWork的主要步骤如下:

  1. 获取ICLRMetaHost
  2. 枚举加载到目标进程中的 CLR
  3. 获取目标进程中特定 CLR 的 ICLRRuntimeInfo
  4. 获取ICLRProfiling接口
  5. 调用 ICLRProfiling::AttachProfiler 方法,附加成功

可以看到,整个流程前三步和Execute-Assembly技术实现的前三步完全一致

.Net Core则提供了相应库Microsoft.Diagnostics.NETCore.Client,相关代码如下。

using Microsoft.Diagnostics.NETCore.Client;class profiler_injector{    static void Main(string[] args){        int pid = Int32.Parse(args[0]);        string profilerPath = args[1];        DiagnosticsClient dia = new DiagnosticsClient(pid);        Guid guid = new Guid("{805A308B-061C-47F3-9B30-F785C3186E71}");        dia.AttachProfiler(TimeSpan.FromSeconds(30),guid, path );    }}
浅谈.Net Profiling在红队中的使用

谈完注入方式后,咱们来谈一下分析器Dll本身。分析器dll的工作原理大致如下图所示:

浅谈.Net Profiling在红队中的使用
1. CoreCLR 首先Load Profiler这个dll,每个分析器Dll都会有DllGetClassobject这个导出函数。

2. CoreCLR然后调用DllGetClassobject导出函数,该函数通常判断CLSID的正确性,然后返回IClassFactory接口实例对象指针。

浅谈.Net Profiling在红队中的使用

3. CoreCLR然后调用IClassFactory::CreateInstance方法,获取ICorCallback接口实例对象指针。

浅谈.Net Profiling在红队中的使用

4. CoreCLR调用ICorCallback::Initialize方法,传入指向自己的指针,profiler会保存下来,然后调用SetEventMask通知coreclr 收集什么类的信息。

浅谈.Net Profiling在红队中的使用
5. 双方进入正常通信。一旦有事件发生,ICorCallback接口的回调函数会被调用。

详细代码见参考链接3,建议观看 Pavel Yosifovich 的演讲视频"Writing a .NET Core cross platform profiler in an hour"

03 应用

持久化

上文提到,当3个环境变量被设置时,任意.Net进程启动会自动加载环境变量指定路径下的Dll,这意味着可以用来做持久化。需要注意的是,Dll不一定要是分析器Dll,普通的Dll也会被加载,即DllMain函数会被执行,可以把恶意代码放在DllMain中。

横向移动

如果可以通过UNC路径远程加载分析器Dll,并设置环境变量,那么便可以用.Net Profiler来横向移动。利用Win32_Process Create创建进程是一种常见的横向方式。而Win32_ProcessStartup可以为指定进程创建环境变量,这意味着我们可以利用上面两个函数远程执行任意.Net进程并加载分析器Dll。

研究员Daniel Mayer在WMI bof项目的基础上,添加了设置环境变量的功能,并将分析器Dll的路径设置为远程UNC路径,但由于使用了WMI,会有双跳(Double Hop)问题,因此失败。然而,他又发现了一种新方式,即分析器Dll可以从远程WebDAV服务器加载,从而实现了横向移动。

04 总结

.Net Profiling API是一组功能较为强大的接口,本文主要介绍了该技术在红队横向移动和持久化中的使用。由于该组接口的参考文档不多,且使用较为复杂,因此相关研究较少,但该组接口有着不少强大的功能,比如运行时修改.Net程序中的某个方法、挂钩.Net程序的指定方法等,这些技术有待进一步研究。

附录 参考链接

[1] https://learn.microsoft.com/en-us/dotnet/framework/unmanaged-api/profiling/profiling-interfaces

[2] https://github.com/dotnet/coreclr/blob/master/Documentation/Profiling/davbr-blog-archive/Attach.md

[3] https://github.com/zodiacon/DotNextMoscow2019

[4] https://www.youtube.com/watch?v=TqS4OEWn6hQ

[5] https://posts.specterops.io/lateral-movement-with-the-net-profiler-8772c86f9523

 

原文始发于微信公众号(M01N Team):浅谈.Net Profiling在红队中的使用

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2024年6月20日09:45:06
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   浅谈.Net Profiling在红队中的使用http://cn-sec.com/archives/2857808.html

发表评论

匿名网友 填写信息