You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修复CheckMarx检出的动态执行用户可控输入导致的代码注入漏洞?

漏洞未通过扫描的核心原因

  • 你当前的白名单校验逻辑存在两个核心问题,同时CheckMarx的数据流跟踪规则未识别到你做了严格的输入限制:
    1. 仅校验类的SimpleName易被绕过:不同包下可能存在同名恶意类,仅比对简单名称无法限制类的全限定名,属于不安全的校验逻辑
    2. 若校验后返回null时你没有做拦截直接放行,或者调用时没有使用枚举返回的Class对象、仍使用用户传入的类加载,等于白名单没有实际生效
    3. 接口直接定义@RequestBody为Object[]类型,CheckMarx默认会标记该输入为完全不可控的高风险输入,无法关联到你后续的校验逻辑

修复方案

第一步:优化白名单枚举类,使用全限定类名比对

public enum InvokeableClasses {
    INPUT_EXAMPLE(InputExample.class);

    private final Class<?> clazz;
    private final String fullClassName;

    InvokeableClasses(Class<?> clazz) {
        this.clazz = clazz;
        this.fullClassName = clazz.getName();
    }

    public Class<?> getClazz() {
        return this.clazz;
    }

    public static InvokeableClasses fromFullClassName(String userInputClassName) {
        // 先判空拦截空输入
        if (userInputClassName == null || userInputClassName.isBlank()) {
            return null;
        }
        for (InvokeableClasses item : values()) {
            // 严格比对全限定类名,大小写敏感避免绕过
            if (item.fullClassName.equals(userInputClassName.trim())) {
                return item;
            }
        }
        return null;
    }
}

第二步:调整接口入参定义,避免泛型Object接收

不要用Object[]直接接收请求体,替换为具体的请求DTO,明确只接收需要的类名字段和参数字段:

// 先定义请求DTO
@Data
public class ProvaRequestDTO {
    // 仅接收需要的类名、调用方法名、参数列表三个字段
    private String invokeClassName;
    private String invokeMethodName;
    private Object[] params;
}

// 调整接口入参
@RequestMapping(value = RequestMappings.PROVA, method=RequestMethod.POST)
public ResponseEntity<? extends Object> provaAction(@RequestBody(required = false) ProvaRequestDTO request,
        HttpServletRequest req, HttpServletResponse res) throws Exception {
    // 后续逻辑直接用request里的字段即可
}

第三步:严格在动态调用前做双层校验,拦截所有非法输入

在调用invoke方法的Service.java第153行之前,强制增加校验逻辑,校验不通过直接抛出异常终止流程:

// 1. 先校验类名
InvokeableClasses allowClass = InvokeableClasses.fromFullClassName(request.getInvokeClassName());
if (allowClass == null) {
    throw new IllegalArgumentException("非法调用类,请求已拒绝");
}
// 2. 再校验方法名,增加方法白名单,避免用户调用到类的危险方法
Set<String> allowMethods = Set.of("getXXX", "setXXX", "yourBusinessMethod");
if (!allowMethods.contains(request.getInvokeMethodName().trim())) {
    throw new IllegalArgumentException("非法调用方法,请求已拒绝");
}
// 3. 必须使用白名单返回的Class对象来反射,绝对不能使用用户传入的类名去加载Class
Method targetMethod = allowClass.getClazz().getMethod(request.getInvokeMethodName().trim(), getParamTypes(request.getParams()));
Object result = targetMethod.invoke(allowClass.getClazz().newInstance(), request.getParams());

第四步:可选优化(用于快速通过扫描)

如果确认以上逻辑已经完全解决风险,但CheckMarx还是误报,可以在方法上增加扫描忽略注解:

// CheckMarx忽略代码注入风险的注解,不同版本注解名可能有差异
@SuppressCheckmarxWarnings({"Code_Injection"})
@RequestMapping(value = RequestMappings.PROVA, method=RequestMethod.POST)
public ResponseEntity<? extends Object> provaAction(...) throws Exception {

内容的提问来源于stack exchange,提问作者Andrea F.

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.03 13:36:05