### 简要描述:
phpmps设计缺陷导致CSRF(全站功能通杀)
### 详细说明:
phpmps防御xss和sql还是很好的,但是却忽略了csrf
请求没有token,没有验证referer。可以请求伪造。
所以是全站通杀!
还是给几个案例吧
案例1:修改管理员密码
```
case 'repass':
if(empty($_REQUEST[password]))show("请输入密码");
if(empty($_REQUEST[repassword]))$msg .= "请输入重复密码\n";
if($_REQUEST[password] <> $_REQUEST[repassword])show("两次输入的密码不一致");
$password = md5($_REQUEST[password]);
$sql = "UPDATE {$table}admin SET password = '$password' WHERE userid = '$_SESSION[adminid]'";
$res = $db->query($sql);
admin_log("$_SESSION[adminid]修改密码成功");
show('资料修改成功', 'admin.php');
break;
```
[<img src="https://images.seebug.org/upload/201502/0112030600c349d6446d24a89b0ad6253e0883cc.jpg" alt="360截图20150201115454295.jpg" width="600" onerror="javascript:errimg(this);">](https://images.seebug.org/upload/201502/0112030600c349d6446d24a89b0ad6253e0883cc.jpg)
案例2:刷钱
```
case 'add':
if($_POST['dosubmit'])
{
extract($_REQUEST);
$amount = floatval($amount);
$r = $db->getOne("SELECT userid,email,money FROM {$table}member WHERE username='$username'");
if(!$r) show('不存在此用户');
$balance = $r['money'];
$value = 0;
if($operation == '+')
{
$balance += $amount;
}
elseif($operation == '-')
{
$balance -= $amount;
}
$balance = round($balance, 2);
$time = time();
$year = date('Y', $time);
$month = date('m', $time);
$date = date('Y-m-d', $time);
$note = htmlspecialchars_deep($note);
$note = cut_str($note, 200);
if($operation == '+')
{
money_add($username, $amount, $note);
}
elseif($operation == '-')
{
money_diff($username, $amount, $note);
}
$url = 'pay.php?act=add';
show('操作成功', $url);
```
[<img src="https://images.seebug.org/upload/201502/011206334b610c665e7f769bc177c22b3458f864.jpg" alt="360截图20150201115454295.jpg" width="600" onerror="javascript:errimg(this);">](https://images.seebug.org/upload/201502/011206334b610c665e7f769bc177c22b3458f864.jpg)
-------------------------------------
由于全站都存在,我就不一一指出了
还有一个设计缺陷在这里提提
备份数据生成的文件名是
```
$filename = date('Ymd').'_'.$random.'_'.$fileid.'.sql';
```
而$random是
```
$random = mt_rand(1000, 9999);
```
生成就是时间戳_从1000到9999的任意数字_加上操作者的id(通常都是1).sql
只需针对写个爆破脚本就可以看到了
**-----
还有一个提示,学dz,把下载数据备份的目录为不可访问,只有管理员才可以访问
### 漏洞证明:
phpmps防御xss和sql还是很好的,但是却忽略了csrf
请求没有token,没有验证referer。可以请求伪造。
所以是全站通杀!
还是给几个案例吧
案例1:修改管理员密码
```
case 'repass':
if(empty($_REQUEST[password]))show("请输入密码");
if(empty($_REQUEST[repassword]))$msg .= "请输入重复密码\n";
if($_REQUEST[password] <> $_REQUEST[repassword])show("两次输入的密码不一致");
$password = md5($_REQUEST[password]);
$sql = "UPDATE {$table}admin SET password = '$password' WHERE userid = '$_SESSION[adminid]'";
$res = $db->query($sql);
admin_log("$_SESSION[adminid]修改密码成功");
show('资料修改成功', 'admin.php');
break;
```
[<img src="https://images.seebug.org/upload/201502/0112030600c349d6446d24a89b0ad6253e0883cc.jpg" alt="360截图20150201115454295.jpg" width="600" onerror="javascript:errimg(this);">](https://images.seebug.org/upload/201502/0112030600c349d6446d24a89b0ad6253e0883cc.jpg)
案例2:刷钱
```
case 'add':
if($_POST['dosubmit'])
{
extract($_REQUEST);
$amount = floatval($amount);
$r = $db->getOne("SELECT userid,email,money FROM {$table}member WHERE username='$username'");
if(!$r) show('不存在此用户');
$balance = $r['money'];
$value = 0;
if($operation == '+')
{
$balance += $amount;
}
elseif($operation == '-')
{
$balance -= $amount;
}
$balance = round($balance, 2);
$time = time();
$year = date('Y', $time);
$month = date('m', $time);
$date = date('Y-m-d', $time);
$note = htmlspecialchars_deep($note);
$note = cut_str($note, 200);
if($operation == '+')
{
money_add($username, $amount, $note);
}
elseif($operation == '-')
{
money_diff($username, $amount, $note);
}
$url = 'pay.php?act=add';
show('操作成功', $url);
```
[<img src="https://images.seebug.org/upload/201502/011206334b610c665e7f769bc177c22b3458f864.jpg" alt="360截图20150201115454295.jpg" width="600" onerror="javascript:errimg(this);">](https://images.seebug.org/upload/201502/011206334b610c665e7f769bc177c22b3458f864.jpg)
-------------------------------------
由于全站都存在,我就不一一指出了
还有一个设计缺陷在这里提提
备份数据生成的文件名是
```
$filename = date('Ymd').'_'.$random.'_'.$fileid.'.sql';
```
而$random是
```
$random = mt_rand(1000, 9999);
```
生成就是时间戳_从1000到9999的任意数字_加上操作者的id(通常都是1).sql
只需针对写个爆破脚本就可以看到了
**-----
还有一个提示,学dz,把下载数据备份的目录为不可访问,只有管理员才可以访问
暂无评论