BaRMIe 是一款用于枚举和攻击 Java RMI(远程方法调用)服务的工具。
RMI 服务常常在缺乏适当安全控制的情况下暴露危险功能,然而由于缺乏有效的测试工具,RMI 服务在安全评估中往往被忽视。2008 年,Adam Boulton 在 AppSec USA 上发表了演讲(YouTube)并发布了一些 RMI 攻击工具,但这些工具很快消失了。不过,即使有了这些工具,成功的零知识攻击仍需通过网络进行大规模暴力破解(约 64 位/90 亿亿种可能性)。
BaRMIe 的目标是让安全专业人员能够识别、攻击和保护不安全的 RMI 服务。通过利用现有软件中的部分 RMI 接口,BaRMIe 可以直接与这些服务交互,而无需首先通过网络暴力破解 64 位数据。
在此处下载最新版本并可直接运行: https://github.com/NickstaDB/BaRMIe/releases/latest
BaRMIe 旨在帮助安全专业人员识别用户已获得事先许可进行攻击的系统上不安全的 RMI 服务。未经授权访问计算机系统是违法的,BaRMIe 必须遵守所有相关法律使用。否则可能导致您被起诉。BaRMIe 的开发人员不承担任何责任,也不对因使用本程序造成的任何滥用或损害负责。
BaRMIe 的使用方法十分简单。不带参数运行 BaRMIe 可获取使用信息。
$ java -jar BaRMIe.jar
▄▄▄▄ ▄▄▄ ██▀███ ███▄ ▄███▓ ██▓▓█████
▓█████▄ ▒████▄ ▓██ ▒ ██▒▓██▒▀█▀ ██▒▓██▒▓█ ▀
▒██▒ ▄██▒██ ▀█▄ ▓██ ░▄█ ▒▓██ ▓██░▒██▒▒███
▒██░█▀ ░██▄▄▄▄██ ▒██▀▀█▄ ▒██ ▒██ ░██░▒▓█ ▄
░▓█ ▀█▓ ▓█ ▓██▒░██▓ ▒██▒▒██▒ ░██▒░██░░▒████▒
░▒▓███▀▒ ▒▒ ▓▒█░░ ▒▓ ░▒▓░░ ▒░ ░ ░░▓ ░░ ▒░ ░
▒░▒ ░ ▒ ▒▒ ░ ░▒ ░ ▒░░ ░ ░ ▒ ░ ░ ░ ░
░ ░ ░ ▒ ░░ ░ ░ ░ ▒ ░ ░
░ ░ ░ ░ ░ ░ ░ ░
░ v1.0
Java RMI 枚举工具。
作者:Nicky Bloor (@NickstaDB)
警告:BaRMIe 旨在帮助安全专业人员识别用户已获得事先许可进行攻击的系统上不安全的 RMI 服务。BaRMIe 必须遵守所有相关法律使用。否则可能导致您被起诉。开发人员不承担任何责任,也不对因使用本程序造成的任何滥用或损害负责。
用法:
BaRMIe -enum [选项] [主机] [端口]
枚举给定端点上的 RMI 服务。
注意:如果未指定 -enum,则此为默认模式。
BaRMIe -attack [选项] [主机] [端口]
枚举并攻击给定的目标。
选项:
--threads 用于枚举的线程数(默认为 10)。
--timeout 阻塞套接字操作的超时时间(默认为 5000 毫秒)。
--targets 包含要扫描目标的文件。
文件每行应包含单个主机或空格分隔的主机和端口对。
或者,支持所有 nmap 输出格式,BaRMIe 将解析 nmap 输出以定位端口 1099、'rmiregistry' 或 'Java RMI' 服务作为目标。
注意:使用 --targets 时不支持 [主机] [端口]。
可靠性:
使用 +/- 系统指示攻击可靠性,如下所示:
[+ ]:表示特定应用攻击
[- ]:表示 JRE 攻击
[ + ]:攻击不安全方法(例如无认证的 'writeFile')
[ - ]:攻击 Java 反序列化(即 Object 参数)
[ +]:无需非默认依赖
[ -]:需要非默认依赖
枚举模式(-enum)提取通过 RMI 注册表服务暴露的对象详细信息,并列出影响该端点的已知攻击。
攻击模式(-attack)首先枚举给定目标,然后提供一个菜单系统,用于对 RMI 服务发起已知攻击。
可以在命令行中指定单个目标。或者,BaRMIe 可以从简单的文本文件或 nmap 输出中提取目标。
很好!这是您帮助改进 BaRMIe 的机会!BaRMIe 依赖对 RMI 暴露的类有一定了解,因此贡献将大大有助于改进 BaRMIe 及 RMI 服务的安全性。
如果您有权访问目标应用程序的 JAR 文件或源代码,则只需针对相关 JAR 文件编译代码即可生成攻击。使用 LocateRegistry 和 Registry 类检索相关远程对象,并调用所需方法。或者,查找接受任意对象或其他非原始参数的远程方法,因为这些方法可用于传递反序列化载荷。未来将提供更多关于攻击 RMI 和为 BaRMIe 生成攻击的文档。
或者,联系我们,并提供尽可能详细的信息,包括 BaRMIe -enum 的输出,以及理想情况下相关的 JAR 文件。
BaRMIe 能够对 RMI 服务执行三种类型的攻击。以下是对每种攻击的简要说明。更多技术细节将于近期在 https://nickbloor.co.uk/ 上发布。此外,我在 44CON 2017 上展示了我研究的结果,相关幻灯片可在此处找到: BaRMIe - Poking Java's Back Door。
攻击不安全 RMI 服务的第一种也是最直接的方法就是直接调用不安全的远程方法。通常,危险功能通过 RMI 暴露出来,只需检索远程对象引用并调用危险方法即可触发。以下代码是一个示例:
//获取远程 RMI 注册表服务的引用
Registry reg = LocateRegistry.getRegistry(targetHost, targetPort);
//获取目标 RMI 对象的引用
Foo bar = (Foo)reg.lookup(objectName);
//调用远程的 executeCommand() 方法
bar.executeCommand(cmd);
某些 RMI 服务并不暴露危险功能,或者实现了诸如身份验证和会话管理等安全控制。如果 RMI 服务暴露了一个接受任意 Object 作为参数的方法,那么该方法可以用作反序列化攻击的入口点。以下是一些此类方法的示例:
public void setOption(String name, Object value);
public void addAll(List values);
由于序列化的使用以及服务器上对方法参数的不安全处理,可以使用任何具有非原始参数类型的方法作为反序列化攻击的入口点。BaRMIe 通过使用 TCP 代理在网络层面修改方法参数来实现这一点,本质上触发了非法方法调用。以下是一些易受攻击方法的示例:
public void setName(String name);
public Long add(Integer i1, Integer i2);
public void sum(int[] values);
每个方法的参数都可以在方法调用通过代理时被替换为反序列化载荷。这种攻击之所以可能,是因为 Java 在反序列化远程方法参数之前,并不会尝试验证通过网络接收到的参数与实际参数类型是否兼容。