phpshe最新1.7版本的后台sql注入分析。
官网:http://www.phpshe.com/
实验环境
在后台批量上下架操作中存在注入。
我们先根据路由查看源码,抓包拿到操作的路径
POST /phpshe/admin.php?mod=product&act=state&state=1&token=c04c2e7a55d84759c0e09eb54b16fccf
定位admin.php:86
if (in_array("{$mod}.php", pe_dirlist("{$pe['path_root']}module/{$module}/*.php"))) {
include("{$pe['path_root']}module/{$module}/{$mod}.php");
}
pe_result();
?>
此时引入了admin模型中的product.php
在switch中找到state分支
case 'state':
pe_token_match();
$product_id = is_array($_p_product_id) ? $_p_product_id : $_g_id;
if ($db->pe_update('product', array('product_id'=>$product_id), array('product_state'=>$_g_state))) {
pe_success("操作成功!");
}
else {
pe_error("操作失败...");
}
break;
如果提交的pproductid是一个数组的话会直接进入db->peupdate操作中。没有任何过滤防护措施。
继续跟进db->pe_update,在db.class.php:226
public function pe_update($table, $where, $set)
{
//处理设置语句
$sqlset = $this->_doset($set);
//处理条件语句
$sqlwhere = $this->_dowhere($where);
return $this->sql_update("update `".dbpre."{$table}` {$sqlset} {$sqlwhere}");
}
peupdate会将参数抛向sqlupdate,继续跟进一下,
public function sql_update($sql)
{
if ($this->query($sql) == true) {
$result = $this->affected_rows();//affected_rows()是获取insert/update/delete结果集条数。
return $result == 0 ? true : $result;
}
return 0;
}
此时我们从product_id传上的数据会被直接拼接在语句中执行。
构造一个POST包进行测试,由于没有回显,我们进行延时
成功延时,网站对传入的product_id没有过滤处理造成了时间盲注。
之后继续审计发现
case 'tuijian':
pe_token_match();
foreach ($_p_product_id as $v) {
$result = $db->pe_update('product', array('product_id'=>$v), array('product_istuijian'=>$_g_tuijian));
}
if ($result) {
pe_success("操作成功!");
}
else {
pe_error("操作失败...");
}
不仅 state 分支,tuijian order move分支均没有对$product_id进行处理。
均存在注入点
在管理页面订单处
定位到order.php
这里依旧采取了一个语句的拼接
然后sqlwhere进入peselectall方法
继续跟进pe_selectall方法
public function pe_selectall($table, $where = '', $field = '*', $limit_page = array())
{
//处理条件语句
$sqlwhere = $this->_dowhere($where);
return $this->sql_selectall("select {$field} from `".dbpre."{$table}` {$sqlwhere}", $limit_page);
}
看到此方法依然没有对语句的过滤处理就直接执行。
回到后台页面,进入订单页面。
之后进入wsend分支
http://127.0.0.1/phpshe/admin.php?mod=order&state=wsend
在state处进行注入
成功延时。可进行时间盲注。
如果wsend分支中有订单存在,同样可以进行bool盲注。
见下面两图
我们对比user.php和admin.php中对订单查询的处理
user.php多了一层对gstate的过滤,admin.php则没有这个操作。
继续审计发现在orderpay页面中,同样没有对g_state进行过滤就直接拼接。
同样存在注入,payload如下
http://127.0.0.1/phpshe/admin.php?mod=order_pay&state=wpay%27and%201=1%20--%201