Windows RPC服务漏洞挖掘之旅

admin 2025年3月5日16:29:27评论46 views字数 5401阅读18分0秒阅读模式
一、Windows RPC介绍

二、Windows RPC Demo

三、FAX服务

四、StorSvc服务

五、总  结

在当今的网络安全领域,Windows操作系统的漏洞挖掘一直是研究者们关注的焦点之一。其中,RPC(Remote Procedure Call,远程方法调用)服务作为Windows系统的核心组件,因其广泛的使用和潜在的安全风险,成为了漏洞挖掘的重要目标,历史上出了非常多的漏洞。

Windows RPC介绍
01
RPC是什么

RPC是Windows系统里最基础的组件之一,很多服务都是基于此开发。RPC是Remote Procedure Call的缩写,即远程方法调用。简单来说,客户端可以通过RPC远程调用服务端已注册的接口内的方法并取得执行结果,而无需关心具体实现。这种机制使得不同进程之间的通信变得高效且透明。

Windows RPC服务漏洞挖掘之旅

02
RPC工作原理

RPC的工作过程可以分为以下几个步骤,参考微软官方文档:<a ""="" class="weapp_text_link js_weapp_entry" href="">微软官方文档

  1. 客户端将参数和要调用的方法按约定序列化成NDR(Network Data Representation)格式。
  2. 通过网络或管道将数据发送给服务端。
  3. 服务端接收数据后将数据反序列化,并调用对应的接口中的方法,反序列化的数据按约定作为各参数。
  4. 服务端方法执行结束后,将返回结果序列化。
  5. 再次通过网络或管道将数据发送给客户端。
  6. 客户端接收数据后将数据反序列化,从而获得服务端执行结果。
Windows RPC服务漏洞挖掘之旅

03
为什么关注RPC

RPC作为Windows系统的核心组件,具有以下特点使其成为漏洞挖掘的重要目标,并且历史上也出现了非常多的漏洞:

  1. 丰富的攻击面:由于RPC是许多服务的基础,因此它提供了大量的潜在攻击点。
  2. 高权限运行:RPC服务通常以高权限(如SYSTEM权限)运行,或者至少具备SeImpersonatePrivilege权限。这意味着一旦被利用,攻击者可以利用RPC服务进行提权操作。
Windows RPC Demo
为了更好地理解RPC的工作机制,我们可以通过一个简单的Demo来展示RPC的基本操作。以下是<a ""="" class="weapp_text_link js_weapp_entry" href="">Windows官方教程的Windows RPC服务端和客户端代码示例:

01
服务端代码

Windows RPC服务漏洞挖掘之旅

Windows RPC服务漏洞挖掘之旅

  1. 初始化 RPC 服务
    • 通过 RpcServerUseProtseqEp 指定通信协议和端点。
    • 通过 RpcServerRegisterIf 注册 RPC 接口(hello_ServerIfHandle 是由 MIDL 编译器对interface hello生成的接口句柄,表示服务端的 RPC 接口)。
  2. 进入监听状态
    • 调用 RpcServerListen,服务端开始监听客户端的 RPC 调用请求。
  3. 处理客户端请求
    • 当客户端通过 RPC 调用服务器端的远程过程时,RPC 运行时会调用相应的服务器存根代码,进而执行实际的远程方法(HelloProcShutdown)。
02
客户端代码

Windows RPC服务漏洞挖掘之旅

  1. 构造字符串信息
    • pszEndpoint:端点名称,指定为 pipehello,与服务端的端点一致。
    • 通过RpcStringBindingCompose将协议序列、端点等信息合并为一个字符串信息。
  2. 创建绑定句柄
    • 通过RpcBindingFromStringBinding从上述字符串信息创建一个 RPC 绑定句柄,用于与服务端进行通信。
  3. 调用远程方法
    • RpcTryExcept 异常处理块中,客户端调用服务端的远程方法(HelloProcShutdown)。
FAX服务
Windows Fax ServerWindows Server中的一个服务器角色,可被用来远程发送和接收传真。

Windows RPC服务漏洞挖掘之旅

微软为传真服务定义了一套基于RPC的交互协议,提供多种传真相关功能,并提供了详细的<a ""="" class="weapp_text_link js_weapp_entry" href="">说明文档。

Windows RPC服务漏洞挖掘之旅

01
Fax Server Interface

<a ""="" class="weapp_text_link js_weapp_entry" href="">Fax服务端接口存在105个方法可被远程调用

Windows RPC服务漏洞挖掘之旅

CVE-2023-21694 Windows 传真服务远程代码执行漏洞

通过查看微软文档,FAX_CreateAccount似乎是个有趣的方法,该方法会验证客户端用户是否有权限创建账户,若验证成功,则会根据传入的参数Buffer创建对应账户。如下是该方法声明:

Windows RPC服务漏洞挖掘之旅

可以看到BufferLPBYTE类型,大小由BufferSize决定,而<a ""="" class="weapp_text_link js_weapp_entry" href="">文档上说Buffer应该是FAX_ACCOUNT_INFO_0指针类型,那么意味着在FAX_CreateAccount内部肯定会有类型转换。

Buffer: A pointer to a FAX_ACCOUNT_INFO_0 that contains fax account information. The lpcwstrAccountName member of the FAX_ACCOUNT_INFO_0 MUST be set to the name of the operating system user account for which the new fax user account is to be created, using the same account name. The format of the user account name string is described in section 2.2.24 (FAX_ACCOUNT_INFO_0).

BufferSize: A DWORD value that indicates the return size, in bytes, of the buffer that is pointed to by the Buffer parameter. The maximum size is FAX_MAX_RPC_BUFFER(section 2.2.82).

FAX_ACCOUNT_INFO_0类型由Fixed_PortionVariable_Data两部分组成。

Windows RPC服务漏洞挖掘之旅

Fixed_PortiondwSizeOfStruct字段(当前Fixed_Portion结构大小,固定为8)和lpcwstrAccountNameOffset字段(Variable_Data相对FAX_ACCOUNT_INFO_0的偏移)组成。这里需要注意的是lpcwstrAccountNameOffset字段后续会被转换为存放指向Variable_Data指针,64位下指针类型占用8字节,加上dwSizeOfStruct字段的4字节,一共是12字节,对齐后Fixed_Portion的大小为16字节,后续也是按16字节进行处理。

Windows RPC服务漏洞挖掘之旅

Variable_Data只有lpcwstrAccountName字段,以0结尾的字符串。

Windows RPC服务漏洞挖掘之旅

分析FAX_CreateAccount里将Buffer转换为FAX_ACCOUNT_INFO_0的逻辑,根据BufferSize分配一段内存,并拷贝Buffer内容,接着调用MarshallUpStructure。此时只检查BufferSize不为0。

Windows RPC服务漏洞挖掘之旅

MarshallUpStructure调用IsBufferSizeEnough来判断原有的Buffer大小是否足够,值得注意的是,整个过程并没有对BufferSize进行检查,调用IsBufferSizeEnough也不带BufferSize

Windows RPC服务漏洞挖掘之旅

分析IsBufferSizeEnough,发现只要lpcwstrAccountNameOffset等于0x10即可满足要求,使IsBufferSizeEnough返回True

Windows RPC服务漏洞挖掘之旅

那漏洞就很明显了,当BufferSize为8,lpcwstrAccountNameOffset0x10时,即可在后续AjustPointersInStructuresArray中将lpcwstrAccountNameOffset转换成指针时触发越界写。

Windows RPC服务漏洞挖掘之旅

type_strict_context_handle

通过查看数据类型idl文件<a ""="" class="weapp_text_link js_weapp_entry" href="">faxdatatypes.idl,发现定义了多种context_handle类型:

Windows RPC服务漏洞挖掘之旅

不同方法间混用不一样的context_handle,会不会存在类型混淆问题呢?实际上微软早就考虑到了这种问题,并在一开始就规定了必须使用<a ""="" class="weapp_text_link js_weapp_entry" href="">type_strict_context_handle。

This protocol MUST specify to the RPC runtime via the type_strict_context_handle attribute, which rejects the use of context handles created by a method that creates a different type of context handle  ([MS-RPCE] section 3).

Windows RPC服务漏洞挖掘之旅

但类型混淆问题在Fax服务协议中就真的不存在吗?

02
Fax Client Interface

<a ""="" class="weapp_text_link js_weapp_entry" href="">Fax客户端接口存在4个方法可被远程调用

Windows RPC服务漏洞挖掘之旅

客户端连接服务端后,为了获取服务端主动发送的事件消息,也会注册对应的RPC接口,等待服务端回连传送消息。

Windows RPC服务漏洞挖掘之旅

客户端在调用FAX_StartServerNotification之后会监听1024端口等待服务端调用FAX_OpenConnection回连。值得注意的是此时1024端口是监听在0.0.0.0上,所有人都可以访问该端口。

Windows RPC服务漏洞挖掘之旅

CVE-2024-38104 Windows 传真客户端远程代码执行漏洞

根据<a ""="" class="weapp_text_link js_weapp_entry" href="">文档说明,Context 参数是一个 ULONG64 类型的句柄,其值应与通过 FAX_StartServerNotification 发送的值保持一致。

Windows RPC服务漏洞挖掘之旅

Context: A ULONG64 ([MS-DTYP] section 2.2.51) containing a context information handle. This handle SHOULD match the one supplied to the server when using the FAX_StartServerNotification family of calls. For more information, see the following topics:

§ FAX_StartServerNotification

  • FAX_StartServerNotificationEx
  • FAX_StartServerNotificationEx2
但逆向分析FAX_OpenConnection发现并没有对Context做任何检查,就直接作为指针使用。

Windows RPC服务漏洞挖掘之旅

并且在注册RPC接口时虽然调用RpcServerRegisterAuthInfoW提供了认证选项,但实际上RpcServerRegisterAuthInfoW并不拒绝未认证的连接。

Windows RPC服务漏洞挖掘之旅

所以任何人通过1024端口连接,发送FAX_OpenConnection,都可以触发任意地址解引用。

Windows RPC服务漏洞挖掘之旅

StorSvc服务
01
CVE-2024-38248 Windows 存储特权提升漏洞

StorSvc服务并不像传真服务一样具有完整而详细的文档说明。此时可以通过借助RpcView来反编译其接口方法说明。

Windows RPC服务漏洞挖掘之旅

逆向其RPC接口注册过程,可以看到通过RpcServerRegisterIf3注册了两个接口。

Windows RPC服务漏洞挖掘之旅

分别具有如下方法:

Windows RPC服务漏洞挖掘之旅

Windows RPC服务漏洞挖掘之旅

RPC接口方法具有高度的规范化特点,那么是否可以使用静态工具自动化扫描这些接口方法呢?

考虑最简单的条件竞争漏洞模式:在未加锁的情况下,存在一条路径对全局变量执行释放操作。

Windows RPC服务漏洞挖掘之旅

首先通过破壳平台查找会被free释放的全局变量。

Windows RPC服务漏洞挖掘之旅

增加约束条件,仅考虑那些可通过RPC接口方法调用的路径。

Windows RPC服务漏洞挖掘之旅

Windows RPC服务漏洞挖掘之旅

当两个线程同时进入StorageService::GetLastFailedSaveLocationPath会导致条件竞争,全局变量Block会被释放两次。

Windows RPC服务漏洞挖掘之旅

Windows RPC服务漏洞挖掘之旅

总  结
本文重点探讨了RPC服务的工作原理、漏洞挖掘方法以及具体案例分析。RPC服务作为Windows系统的核心组件,其安全性和稳定性对于整个系统的安全至关重要。在实际的漏洞挖掘过程中,我们需要关注RPC服务的以下特点:

  1. 丰富的攻击面:RPC服务提供了大量的潜在攻击点,需要仔细分析每个接口方法的实现和调用过程。
  2. 高权限运行:RPC服务通常以高权限运行,一旦被利用,攻击者可以实现提权等恶意操作。
  3. 复杂的通信机制:RPC的通信机制涉及参数的序列化与反序列化、网络传输等多个环节,容易出现安全漏洞。
【版权说明】

本作品著作权归lm0963所有

原文始发于微信公众号(奇安信天工实验室):Windows RPC服务漏洞挖掘之旅

免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉。
  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2025年3月5日16:29:27
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   Windows RPC服务漏洞挖掘之旅https://cn-sec.com/archives/3798637.html
                  免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉.

发表评论

匿名网友 填写信息