当前位置: 首页 > news >正文

mq3.8.9版本有什么不同_【SEACMS 8.9版本】从变量覆盖到变量覆盖的SQL注入漏洞

0x01

最近审计了一波seacms,官网:https://www.seacms.net 。版本是最新版本的(审计时),和那些单入口框架不同,这个cms审计起来很圆润,但是过滤的就很干干巴巴,印象中好像看到了3个过滤拦截页面,360webscan(cmseasy也有)一个,好像自带还有两个,丧心病狂。但还是盘出来一个可以绕过的注入。

0x02

首先了解了下参数传递方式。核心文件是/include/common.php,很多文件都包含了这个文件。看下这个文件,114-117行:

foreach(Array('_GET','_POST','_COOKIE') as $_request)
{
    foreach($$_request as $_k => $_v) ${$_k} = _RunMagicQuotes($_v);
}

GET、POST和Cookie的参数会经过一次变量覆盖,然后把值$_v赋给对应的变量$$_k,这里会对$_v进行处理,单引号啥的都会被转义。这里既然可以进行变量覆盖,也就是说像一些全局变量我都可以控制!!!感觉这里问题很大。

接下来看20-26行:

foreach($_REQUEST as $_k=>$_v)
{
    if( strlen($_k)>0 && m_eregi('^(cfg_|GLOBALS)',$_k) && !isset($_COOKIE[$_k]) )
    {
        exit('Request var not allow!');
    }
}

这里的代码在上一步进行变量覆盖之前进行了一次过滤,不能覆盖全局变量$GLOBALS和一些配置变量(以$cfg_开头)。但是过滤的是$_REQUEST,也就是说只能过滤$_POST和$_GET。这里把想覆盖的变量放到在Cookie里面就可以绕过。比如下图,cfg_runmode,cfg_paramset两个配置变量的值都被赋值为1。

15284d35a8ec61aeb2efb881387ffc90.png

0x03

上一步确定了思路,接下来找一波包含common.php的文件。大概有这么多,忽略掉后台的。

c100e1615fdce2b5dceebe618361a1c9.png

这些文件在进行变量覆盖后都会做一些整数化处理,比如

ac9c6fcd9a7c877b20000f9e9e00ee4f.png

be96a9ce3c92b0c5191cb1d1568d86d3.png

类似这种处理的地方特别多。

0x04

第二处变量覆盖。

在/detail/index.php文件中。echoContent($vId)方法中,第38行进行了sql语句拼接,$row=$dsql->GetOne("Select d.*,p.body as v_playdata,p.body1 as v_downdata,c.body as v_content From `sea_data` d left join `sea_playdata` p on p.v_id=d.v_id left join `sea_content` c on c.v_id=d.v_id where d.v_id='$vId'"),这里把$vId拼接了进去,并且需要单引号闭合才可以注入。

if($GLOBALS['cfg_runmode']==2||$GLOBALS['cfg_paramset']==0){
    $paras=str_replace(getfileSuffix(),'',$_SERVER['QUERY_STRING']);
    $id=intval($paras);
    $id = (isset($id) && is_numeric($id) ? $id : 0);
}else{
    $id=$$GLOBALS['cfg_paramid'];
}
if($id==0){
    showmsg('参数丢失,请返回!', -1);
    exit;
}

echoContent($id);

function echoContent($vId)
{
    global $dsql,$cfg_iscache,$mainClassObj,$t1,$cfg_user;
    $row=$dsql->GetOne("Select d.*,p.body as v_playdata,p.body1 as v_downdata,c.body as v_content From `sea_data` d left join `sea_playdata` p on p.v_id=d.v_id left join `sea_content` c on c.v_id=d.v_id where d.v_id='$vId'");
    if(!is_array($row)){ShowMsg("该内容已被删除或者隐藏","../index.php",0,10000);exit();}
    $vType=$row['tid'];

在第23行,调用了echoContent($id)方法。看下传进去的$id如何取值。

第16行可以看到,$id=$$GLOBALS['cfg_paramid'],这里进行了第二次变量覆盖。

897e26109baa07a37950bc286ece6412.png

这里有一个条件,if($GLOBALS['cfg_runmode']==2||$GLOBALS['cfg_paramset']==0),需要$cfg_runmode的值不为2并且$cfg_paramset的值不为0。这里很好绕过,在0x02中说过,把想覆盖的变量放到在Cookie里面就可以绕过。

接下来考虑把什么变量的值赋给$id。在最后一步想了很多方法,把注入代码放入参数里面都会被转义处理。然后考虑把注入代码放到$_SERVER变量传进去,这样可以绕过360webscan和自带的过滤。

这样又出现了一个问题。$_SERVER是数组,$id=$$GLOBALS['cfg_paramid']无法根据key取数组中的值,包括$_GET,$_POST,$GLOBALS等。并且在GET,POST中加注入代码会触发360webscan。

1477ba8547d080709dce7418a7542d53.png

在这一步卡了很久,最后想到一个方法。

0x05

回到最开始,/include/common.php,114-117行:

foreach(Array('_GET','_POST','_COOKIE') as $_request)
{
    foreach($$_request as $_k => $_v) ${$_k} = _RunMagicQuotes($_v);
}

这里在循环完成后没有把$_k这个变量销毁,可以借用这个变量。在Cookie中加上cfg_paramid=_k,$$GLOBALS['cfg_paramid']的值即为$_k的值,然后在Cookie最后一个参数名加上注入代码,比如:1'and(updatexm l(1,concat(1,user(),1),1))and'1=123,$_k的值就被赋值为1'and(updatexm l(1,concat(1,user(),1),1))and'1,$id就被赋值为1'and(updatexm l(1,concat(1,user(),1),1))and'1。并且不会被拦截,也不会被转义。最后POC如下:

d779a872ddb75f3f3a562e9faae9ed0c.png

0x06

该漏洞已通报厂商和cnnvd,1月31号更新最新版本9.0已修复该漏洞。

有骚思路欢迎一起讨论,大佬勿喷!

相关文章:

  • matlab中k-means算法_OpenCV图像处理-KMeans 图像处理
  • python中的转义字符是什么意思_python 转义字符、运算符、列表。。。。
  • python发微信公众号消息_个人微信公众号搭建Python实现 -接收和发送消息-基本说明与实现(14.2.1)...
  • python爬虫代写价格_python爬取京东价格
  • lua get reused time_利用redis-lua+python实现接口限流
  • server2008网卡驱动包_网卡工作原理详解
  • svpwm的原理及法则推导和控制算法详解_电机控制要点解疑:SPWM,SVPWM和矢量控制...
  • python删除文件指定字符串,从Python中的字符串中删除特定字符
  • python基础读后感_《python基础教程 》第一章 读书笔记
  • 二叉树的字符图形显示程序_(CSPJ)入门级C++语言试题A卷答案解析阅读程序
  • 服务器显示地址正在使用_用Windows Storage Server 2008做iSCSI存储服务器
  • 权限设计表结构超详细_超详细!!五金模具组件及工程结构设计
  • flex 下对齐_开启 flex 与 grid 布局方式之旅
  • python中的and or的区别_Python 中 (,|)和(and,or)之间的区别
  • python csv模块dictwrite_Pythoncsv.DictWriterwriterow()返回
  • 10个最佳ES6特性 ES7与ES8的特性
  • canvas实际项目操作,包含:线条,圆形,扇形,图片绘制,图片圆角遮罩,矩形,弧形文字...
  • CentOS从零开始部署Nodejs项目
  • ES6系统学习----从Apollo Client看解构赋值
  • httpie使用详解
  • Java 23种设计模式 之单例模式 7种实现方式
  • JavaScript对象详解
  • Java程序员幽默爆笑锦集
  • mysql常用命令汇总
  • MySQL用户中的%到底包不包括localhost?
  • PAT A1017 优先队列
  • python3 使用 asyncio 代替线程
  • vue 个人积累(使用工具,组件)
  • Vue官网教程学习过程中值得记录的一些事情
  • 个人博客开发系列:评论功能之GitHub账号OAuth授权
  • 记录一下第一次使用npm
  • 你不可错过的前端面试题(一)
  • 前端 CSS : 5# 纯 CSS 实现24小时超市
  • 前端面试题总结
  • 让你的分享飞起来——极光推出社会化分享组件
  • 学习HTTP相关知识笔记
  • 一加3T解锁OEM、刷入TWRP、第三方ROM以及ROOT
  • 移动端唤起键盘时取消position:fixed定位
  • ​软考-高级-系统架构设计师教程(清华第2版)【第20章 系统架构设计师论文写作要点(P717~728)-思维导图】​
  • ${ }的特别功能
  • (二)学习JVM —— 垃圾回收机制
  • (四)七种元启发算法(DBO、LO、SWO、COA、LSO、KOA、GRO)求解无人机路径规划MATLAB
  • (五)IO流之ByteArrayInput/OutputStream
  • (续)使用Django搭建一个完整的项目(Centos7+Nginx)
  • (学习日记)2024.04.10:UCOSIII第三十八节:事件实验
  • (转)Mysql的优化设置
  • (转)总结使用Unity 3D优化游戏运行性能的经验
  • .net php 通信,flash与asp/php/asp.net通信的方法
  • .Net Web窗口页属性
  • .NET 命令行参数包含应用程序路径吗?
  • .NET 使用配置文件
  • .NET面试题解析(11)-SQL语言基础及数据库基本原理
  • @KafkaListener注解详解(一)| 常用参数详解
  • @transactional 方法执行完再commit_当@Transactional遇到@CacheEvict,你的代码是不是有bug!...
  • [ 代码审计篇 ] 代码审计案例详解(一) SQL注入代码审计案例