hadsky部分用户任意登录
漏洞利用过程
在注册页面
注册用户 密码为password 其他信息随便填
在登陆框以用户名0e10(万能用户名) 密码password登录
成功登陆
漏洞产生原因
该cms有三种登陆方式
用户UID 邮箱 用户名 代码如下
\upload\phpscript\checklogin.php 第6行
1 | if (Cnum($_POST['username'])) { |
这里会首先进入Cnum()函数检查
1 | function Cnum($str, $return = 0, $int = true, $min = FALSE, $max = FALSE) { |
这个函数的功能是检验是否位数字,0e10的用户名经过is_numberic()判断returu,最后int()后,以 return 0返回
问题就出在这里 if (Cnum($_POST[‘username’])) 看到返回值是0会认为他不是数字(实际上是的嘛只是科学记数法而已),于是绕过UID登录方式,0e10显然也不符合邮箱格式,于是进入else被当成了用户名来验证。0e10符合用户名的格式,于是接下来进入用户存在性检验。
\upload\phpscript\checklogin.php 第25行
1 | if (!$username || !$password) |
如果开始直接输入0,会在这里报错,但是0e10不会目测PHP弱类型的原因~
\upload\phpscript\checklogin.php 第34行
1 | //检验数据库中是否有相应用户名 |
跟进getData()
1 | public function getData($field = NULL, $str = NULL) { |
跟进getSql()
1 | public function getSql($field, $str = NULL) { |
这里mysqlstr($value)没有引号保护直接拼接进去,最终执行SQL语句如下
1 | if ($trylogindata) { |
由于MYSQL的弱类型的关系(0=任何字符串)因为username
字段是是字符串,所以只要数据库里有一条数据,那么getData(array('username' => $username));
就会返回数据给$trylogindata
\upload\phpscript\checklogin.php 第52行
1 | if ($trylogindata) { |
由于$trylogindata
存在,所以进入if语句
\upload\phpscript\checklogin.php 第52行
1 | //检验密码是否正确 |
跟进UserLogin()
1 | function UserLogin($chkuserloginarray, $chkloginqx = true) { |
这里检验用户名,密码依然是getData()函数
最后执行SQL语句就是
1 | select * from `pk_user` where `username`=0e10 and password = 'xxxxxxxxx' |
所以只要数据库中存在密码,就能登陆拥有相应密码的第一个用户(万能用户名)。
一句话总结:未加引号保护时,MYSQL+PHP弱类型引起的登陆逻辑漏洞
最后
1、厂商原话:系统开源的,也希望大家多多支持,能把发现的问题发给我
2、个人能力有限,如有错误还请师傅们多多指教
hadsky部分用户任意登录