CC注入Tomcat Upgrade/Executor/WebSocket内存马
字数 3096 2025-08-29 22:41:02
Tomcat内存马注入技术详解:Upgrade/Executor/WebSocket
1. Upgrade内存马技术
1.1 原理分析
Upgrade内存马利用了Tomcat的HTTP协议升级机制,通过注入恶意的UpgradeProtocol实现持久化后门:
-
处理流程:
- Http11Processor.service()调用isConnectionToken检查Connection:upgrade请求头
- 存在时取出Upgrade请求头对应的对象名
- 通过getUpgradeProtocol获取UpgradeProtocol实例
- 调用该对象的accept方法
-
关键点:
- httpUpgradeProtocols在Tomcat启动时通过AbstractHttp11Protocol.init初始化
- 初始upgradeProtocols为空,为注入提供了稳定空间
1.2 注入实现
-
恶意代码位置:
- 写入恶意UpgradeProtocol,在accept方法中实现恶意功能
- accept方法的request参数是org.apache.coyote.Request
-
获取httpUpgradeProtocols:
RequestFacade.request.connector.protocolHandler.httpUpgradeProtocols -
Payload示例:
// 通过全局global获取request姿势拼接的Upgrade内存马 // 注意执行命令需要带上Connection: Upgrade和Upgrade请求头
1.3 特点
- 作用于connector内的Http11Processor
- 需要特殊请求头触发:Connection: Upgrade和Upgrade
- 在反向代理环境下仍可工作
2. Executor内存马技术
2.1 Tomcat请求处理架构
-
核心组件:
- Endpoint:监听端口、接收连接、分发socket给Processor
- NioEndpoint:基于Java NIO
- AprEndpoint:基于APR
- JIoEndpoint:基于BIO
- Processor:真正处理请求的逻辑(Http11Processor)
- Executor:线程池管理
- Endpoint:监听端口、接收连接、分发socket给Processor
-
请求处理流程:
- Connector初始化ProtocolHandler
- ProtocolHandler持有Endpoint
- Endpoint启动监听端口
- 连接到来:
- Endpoint分配线程
- 调用Processor处理请求
2.2 Executor注入点
-
调用链:
- NioEndpoint$Poller.run()
- processKey()
- processSocket()
- getExecutor().execute()
-
注入方法:
- 通过NioEndpoint.setExecutor()设置自定义Executor
- 将内置executor置空
-
查找NioEndpoint:
- 使用java-object-searcher工具
- 通过线程名"ClientPoller-*"定位
2.3 回显问题与局限
-
问题:
- Executor阶段request未完全解析,内容为空
- 修改Executor可能导致正常业务崩溃
- 稳定性差,复现困难
-
不稳定回显方案:
- 尝试从channel读取:command.socketWrapper.socket.appReadBufHandler.byteBuffer.hb
- 自定义Header匹配(如cmd:whoami\r)
-
局限:
- 需要继承ThreadPoolExecutor,限制利用方式
- 业务影响大,易导致服务不可用
3. WebSocket内存马技术
3.1 WebSocket实现机制
-
注解实现:
- @ServerEndpoint创建WebSocket端点
- 生命周期注解:
- @OnOpen
- @OnMessage
- @OnClose
- @OnError
-
手动实现:
- 继承Endpoint类
- 实现MessageHandler.Whole
-
注册流程:
- WsSci.onStartup()初始化
- 扫描@ServerEndpoint和Endpoint子类
- WsServerContainer.addEndpoint注册
3.2 内存马实现
-
获取WsServerContainer:
- 从StandardContext属性获取:"javax.websocket.server.ServerContainer"
- 反射路径:StandardContext→ApplicationContext→attributes
-
注入步骤:
- 获取StandardContext
- 获取WsServerContainer
- 创建ServerEndpointConfig
- 调用addEndpoint注册恶意Endpoint
-
恶意Endpoint示例:
public class EvilServerWebSocket extends Endpoint implements MessageHandler.Whole<String> { @Override public void onOpen(Session session, EndpointConfig config) { session.addMessageHandler(this); } @Override public void onMessage(String message) { // 恶意代码逻辑 } }
3.3 特点与工具
- 建立独立ws TCP通道,绕过部分检测
- 已有开源利用工具:wsMemShell
- 需要配套客户端连接
4. 综合对比与防御
4.1 技术对比
| 类型 | 注入点 | 触发条件 | 稳定性 | 隐蔽性 | 适用场景 |
|---|---|---|---|---|---|
| Upgrade | Http11Processor | 特殊HTTP头 | 高 | 中 | 常规Web环境 |
| Executor | NioEndpoint | 所有请求 | 低 | 高 | 无防护设备环境 |
| WebSocket | WsServerContainer | WebSocket连接 | 高 | 高 | 长期控制通道 |
4.2 防御建议
-
检测:
- 监控非常规协议升级请求
- 检查WebSocket端点注册
- 线程池实现类验证
-
防护:
- 限制协议升级功能
- WebSocket端点白名单
- RASP防护关键API调用
-
加固:
- 禁用不必要的SCI
- 定期内存马扫描
- 更新Tomcat版本
5. 参考资源
-
测试环境与代码:
https://github.com/godownio/TomcatMemshell -
WebSocket内存马工具:
https://github.com/veo/wsMemShell -
相关技术文章:
- https://mp.weixin.qq.com/s/RuP8cfjUXnLVJezBBBqsYw
- https://xz.aliyun.com/news/11012
- https://wileysec.github.io/fee784a451d7.html
-
Java对象搜索技术:
https://godownio.github.io/2025/04/09/li-yong-java-object-searcher-gou-jian-tomcat-xian-cheng-hui-xian/ -
StandardContext获取方法:
https://godownio.github.io/2025/02/26/tomcat-xia-huo-qu-standardcontext-de-fang-fa-jsp-zhuan-java-nei-cun-ma/ -
SPI机制解析:
https://godownio.github.io/2024/10/28/snakeyaml/#SPI-%E6%9C%BA%E5%88%B6