Web 攻防之业务安全:不安全验证码 测试.
验证码安全 也可以叫《全自动区分计算机和人类的图灵测试》,是一种区分用户是计算机还是人的共全自动程序。可以防止:恶意破解密码、刷票、论坛灌水。可以有效防止黑客对某一个特定用户用特定程序暴力破解方式进行不断的登陆尝试。由于计算机无法解答CAPTCHA的问题,所以回答出问题的用产就可以被认为是人类.
目录:
验证码安全 概括:
验证码的认证流程:
验证码 作用:
验证码 分类:
验证码安全 问题:
不安全验证码测试 步骤:
不安全验证码( 服务器端 )
第一步:随便输入一个 账号 和 密码,验证码也随便 进行测试(用 Burp 进行抓包.)
第二步:在 Burp 里,将数据包发送给重发器.(进行 验证码 测试.)
第三步:知道是 服务端的验证码 没有被及时销毁了.(然后 用 Burp 进行密码爆破.)
第四步:使用爆破的 账号 和 密码 进行测试(测试成功.)
不安全验证码( 客户端 )
第一步:随便输入一个 账号 和 密码,验证码也随便 进行测试(用 Burp 进行抓包.)
第二步:在 Burp 里,将数据包发送给重发器.(进行 验证码 测试.)
第三步:知道是 客户端的验证码验证了 (然后 用 Burp 进行密码爆破.)
第四步:使用爆破的 账号 和 密码 进行测试(测试成功.)
修改建议:
验证码的认证流程:
客户端请求登录页面,后台生成验证码:
(1)后台使用算法生成图片,并将图片发送给客户端.
(2)同时将算法生成的值全局赋值存到SESSION中.
校验验证码∶
(1)客户端将认证信息和验证码一同提交.
(2)后台对提交的验证码与SESSION里面的进行比较.
客户端重新刷新页面,再次生成新的验证码:
(1)验证码算法中一般包含随机函数,所以每次刷新都会改变.
验证码 作用:
(1)防止 恶意破解密码、刷票、论坛灌水,刷页.
(2)可以有效防止黑客对某一个特定用户用特定程序暴力破解方式进行不断的登陆尝试.
验证码 分类:
(1)动画验证码 (2)手机短信验证码 (3)手机语言验证码
(4)视频验证码
验证码安全 问题:
1.客户端问题:(1)使用前端JS代码实现验证码 (2)验证码输出在 html 中.(3)验证码输出在 cookie 中
2.服务端问题:(1)验证码不过期,没有及时销毁会话导致验证码复用这个验证码.(2)没有进行非空判断.
3.其他类型验证码绕过(" 调试功能 " 还是设计缺陷 ?)
4.验证码太简单,容易被机器识别.
5.爆破验证码.
靶场:
本地自己搭建的Pikachu(皮卡丘)靶场:安装在win XP(IP地址:192.168.1.104)
Pikachu(皮卡丘)靶场搭建链接:Web安全 Pikachu(皮卡丘)靶场搭建._半个西瓜.的博客-CSDN博客
不安全验证码测试 步骤:
不安全验证码( 服务器端 )
测试的是:后台对验证码没有及时销毁.(可以多次使用)
后台进行验证的代码:
$html="";if(isset($_POST['submit'])) {if (empty($_POST['username'])) {$html .= "<p class='notice'>用户名不能为空</p>";} else {if (empty($_POST['password'])) {$html .= "<p class='notice'>密码不能为空</p>";} else {if (empty($_POST['vcode'])) {$html .= "<p class='notice'>验证码不能为空哦!</p>";} else {//验证验证码是否正确if (strtolower($_POST['vcode']) != strtolower($_SESSION['vcode'])) {$html .= "<p class='notice'>验证码输入错误哦!</p>";//应该在验证完成后,销毁该$_SESSION['vcode']}else{$username = $_POST['username'];$password = $_POST['password'];$vcode = $_POST['vcode'];$sql = "select * from users where username=? and password=md5(?)";$line_pre = $link->prepare($sql);$line_pre->bind_param('ss',$username,$password);if($line_pre->execute()){$line_pre->store_result();//虽然前面做了为空判断,但最后,却没有验证验证码!!!if($line_pre->num_rows()==1){$html.='<p> login success</p>';}else{$html.= '<p> username or password is not exists~</p>';}}else{$html.= '<p>执行错误:'.$line_pre->errno.'错误信息:'.$line_pre->error.'</p>';}}}}}}
第一步:随便输入一个 账号 和 密码,验证码也随便 进行测试(用 Burp 进行抓包.)
Burp的数据包数据.
第二步:在 Burp 里,将数据包发送给重发器.(进行 验证码 测试.)
第三步:知道是 服务端的验证码 没有被及时销毁了.(然后 用 Burp 进行密码爆破.)
第四步:使用爆破的 账号 和 密码 进行测试(测试成功.)
不安全验证码( 客户端 )
测试的是:使用前端JS代码实现验证码
查看前端代码(发现验证码是在前端进行验证的):
<script language="javascript" type="text/javascript">var code; //在全局 定义验证码function createCode() {code = "";var codeLength = 5;//验证码的长度var checkCode = document.getElementById("checkCode");var selectChar = new Array(0, 1, 2, 3, 4, 5, 6, 7, 8, 9,'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z');//所有候选组成验证码的字符,当然也可以用中文的for (var i = 0; i < codeLength; i++) {var charIndex = Math.floor(Math.random() * 36);code += selectChar[charIndex];}//alert(code);if (checkCode) {checkCode.className = "code";checkCode.value = code;}}function validate() {var inputCode = document.querySelector('#bf_client .vcode').value;if (inputCode.length <= 0) {alert("请输入验证码!");return false;} else if (inputCode != code) {alert("验证码输入错误!");createCode();//刷新验证码return false;}else {return true;}}
第一步:随便输入一个 账号 和 密码,验证码也随便 进行测试(用 Burp 进行抓包.)
Burp的数据包数据.
第二步:在 Burp 里,将数据包发送给重发器.(进行 验证码 测试.)
第三步:知道是 客户端的验证码验证了 (然后 用 Burp 进行密码爆破.)
第四步:使用爆破的 账号 和 密码 进行测试(测试成功.)
修改建议:
(1)强制要求输入验证码,否则 必须实施IP策略(注意不要被 X-Forwarded-For 绕过了!)
(2)验证码只能用一次,用完立即过期!不能再次使用了.
(3)验证码不要太弱(要使用 扭曲、变形、干扰线条、干扰背景色、变换字体等.)
(4)大网站最好统一安全验证码,各处使用同一个验证码接口.
参考链接:Web安全 验证码绕过_哔哩哔哩_bilibili