今天不是来打游戏的,我们的重点是了解一些针对web登陆界面的爆破手法。
就是在很多场合中上不了台面的一类攻击手法。简单的通过正常请求的发送,不断尝试用户名密码,最终登陆上去的方法。我们可以称之为爆破、穷举攻击。
1.概述
穷举就是枚举的意思,在互联网的今天,需要使用某种的服务,大多数都需要口令登录,这个口令就是密码,密码的强度分为,弱口令 、中度口令、强度口令。如果登录的服务为弱口令,那会存在很大的安全隐患,黑客通过穷举弱口令对服务进行攻击,很容易就得到登录密码。得到密码之后就能登录服务,进行其他危害较大得操作。黑客也能通过对用户的信息整理,组合密码进行穷举攻击。例如根据用户的生日号码,出身年月日和姓名进行口令组合,再对其服务进行穷举。
2. 环境搭建
两台windows2012的虚拟机需要部署在本地虚拟化环境内部,我们需要对其上部署的网站进行域名访问。那么我们就需要修改本地也就是本机的host文件指向对应的主机IP地址即可使用域名访问到目标主机。
2.1 解压文件到当前目录
2.2 导入虚拟机
获取所有权:
网卡模式NAT:
开机后配置自动获取IP地址:
获取当前虚拟机IP地址:
我们攻击机由本地宿主机扮演,则在攻击机上将对应的域名解析到此地址上,用于维持域名访问对应的web服务。
C:\Windows\System32\drivers\etc\hosts
192.168.2.175 www.c1moon.com
192.168.2.175 www.c3moon.com
192.168.2.175 www.c4moon.com
测试访问情况:
三个网站均可以正常通过域名访问即可。
至于环境更加详细的信息大家可以在文档中自行查阅,核心的思想就是我们要通过域名访问到我们的测试网站。
3. burpsuite 穷举后台密码
burp真是安全人员的小帮手,它提供的穷举功能也是十分的强大。
3.1 无验证码穷举
测试站点:www.c1moon.com
3.1.1 找到登陆点
从这里点击可以进入网站后面的登陆框,如果没有明显的登陆位置则可以使用dirsearch等工具进行路径探测。
3.1.2 抓包爆破
提示我们密码输错则意味着用户名是存在的,开启burp进行抓包分析:ctrl + r送到重放模块,查看放行后的状态:
这里显示密码错误,我们继续ctrl+i
将数据包发送到爆破模块,在这个模块中被$
包裹的就是变量,可以在后续的测试中进行多次遍历。整理(点击clear后选中可变字段,再次点击add)之后就是下面的效果:
在payload里面添加进入我们的字典
开始攻击:点击右上角start attack
到这里我们可以看到,根据相应包大小排序或者状态码来看,有那么一个不一样的,极有可能是正确的密码。正常的页面请求在登陆成功的时候通常是302处理的,我们回到原页面进行登陆尝试即可。
无验证码的状态爆破成功。
tips:在数据包界面中看不见汉字的时候就可以尝试修改burp的编码格式,调整为汉字即可。
3.2 burp针对webshell的穷举
灰帽子对网站攻破后,一般会留后门方便对其网站进行非法管理。后门的程序语言包括 asp
、php
、.net
这些脚本文件放在网站某些目录底下, 一般都采用单密码进行登录。
通过目录扫描获取 webshell 的后门的网址。得到网址后可以对其进行密码穷举以此获取登入对方后台的机会。
测试环境:我们已经通过扫描手段获取了两个藏在根目录底下的webshell,尝试对其进行穷举。
http://www.c1moon.com/webshell.asp
http://www.c1moon.com/webshell.aspx
抓包,将数据包放到爆破模块:
直接开始进行爆破:
登陆尝试:
有一说一这样的大马功能还是十分完善的,另一个的爆破过程不在做演示。
因为没有做任何安全限制,所以突破这样的登陆界面对于我们来说是十分简单的。理论上只要我们的字典足够大,很容易爆破进去。
3.3 有token防御的网站后台
有的网站后台存在 token 值,这个 token 通俗的名字叫令牌,每次刷新页面都会随机变化。提交请求时必须携带这个 token 值,可以利用这点避免后台进行直接穷举和防止 csrf 攻击。
测试环境:
http://www.c3moon.com/login.php
第一次进行请求提交:
尝试跟进跳转页面可以看到登陆失败的字样:
当我们尝试再次重放这一数据包时:
可以看到跟进的响应数据报文已经变成了csrf token increat
字样。这就意味着服务端通过token对我们的访问做了限制。其实也可以通过不断刷新页面在当前页面查看token的数值变化:
其大致的访问逻辑如下:
1.客户端向服务器发起请求
2.服务端在返回页面内部插入一次性token字符串,要求客户端下一次请求提交数据时必须携带该token作为令牌。以此实现安全访问。
3.当我们提交post请求时同时将token附在页面内部,和账号密码一起提交
4.服务器拿到请求先检查token是不是自己先前发出去的内一个,用过之后就将使用过的token标记起来,如果下一次在收到相同的token则视为重放攻击。拒绝登陆请求。
3.3.1 burpsuite绕过token
那么,梳理了以上的防御方式之后我们也该有一个应对思路了。先前的burp在发起大量爆破请求时,无法做到每一个请求都提前获取token,因此导致burp在这个环境中无法使用。
也就是说,我们只要让burp的请求可以在每一次请求之前提前获取一次性的token,就可以绕过这一防御机制。这就要仰仗于burp自带的宏定义功能,在模块执行前辅助执行一些动作。
进入project options
选项卡,选择添加新的宏
点击添加
选择run a macro
添加任务:
添加监控页面:
选则页面内部提取的内容:
设置抓取字段:
设置成功后应该在这个页面内有如下现象;
点击ok去设置更新内容,此选项对每一个请求进行如下字段的更新
设置作用范围:这里的作用URL局限在了目标站点内部
完成后点击OK即可完成宏的设置。回到最开始的那一步,继续抓包,扔到破解模块开始下一步的爆破,要注意的一点是这个页面每一个请求都会进行跳转,那么我们就需要在爆破模块的这里开启跟踪模式:
实施爆破:
可以看到在宏的帮助下我们很快就完成了绕过token限制的爆破。
3.3.2 python脚本绕过token
除了上述的burp工具模块的使用,我们还可以采用python脚本完成这一操作。
#coding:utf-8
import requests
import re
#定义目标URL
url = "http://www.c3moon.com/login.php"
#以密码为参数的请求函数
def login(password):
session = requests.session()
req=session.get(url)
#print(req) 获取session对象,下面则从session对象中获取实时的token数值
user_token=re.search("[a-z0-9]{32}",req.text).group(0) #32md5
#print(user_token) 获取当前页面的user_token
data={"username":"admin","password":password,"Login":"Login",'user_token':user_token}
req=session.post(url=url,data=data,allow_redirects=True)
html = req.text
return html
#注意在当前的页面文件夹内部存放字典文件
with open('toppasswd.txt') as p:
passlist =p.readlines()
p.close()
for line in passlist:
line = line.strip("\n")
print(line)
if 'File Upload' in login(line):
print( "[* 密码 is %s *]" % line )
break
运行结果:
原理剖析:
1.客户端在于服务器进行通信时,服务器端会生成session文件用于存储客户端校验用的token信息。
2.客户端拿到响应报文时会生成名称为phpsessionid的cookie其内部存储的就是服务器上对应的sessionid,用于找到对应的文件
3.当客户端再次发起post请求提交文件时,会携带cookie上去,服务器跟着cookie中的sessionid找到存储了的session文件,取出其中的token数值于报文中携带的token进行对比,如果不一致则直接拒绝此请求。返回token失效的信息。
那么,我们的脚本实现的功能就是从返回报文中读取session内的token信息用于本次的web请求发送。循环往复,以此绕开了token的验证机制。
4. 验证码绕过
网站后台或者有登录的地方都可能存在验证码验证,验证码的作用 不少网站为了防止用户利用机器人自动注册、登录、灌水,都会采用验证码技术,所谓的验证码,就是将一串随机产生的数字和符号,生成一幅图片,在图像上加上干扰像素(防止 orc),要用户用肉眼识别其中的验证码信息,输入表单提交网站验证。
针对验证码后台的处理方案我们通常有两种思路,一种就是利用验证码逻辑上的漏洞绕过验证过程。另一种则是直接使用自动化图像识别工具,进行验证码的识别。
4.1 逻辑绕过
4.1.1 cookie失效引发的验证失效
测试站点:登陆框
http://www.c4moon.com/index.php?case=user&act=login
注意这里第一次登陆是没有这个验证码的,是看不见的。需要我们尝试过一次之后才能显示输入验证码的地方。
抓包分析结果:连续提交会提示我们验证码错误,这里说明每一次请求都刷新了后端验证码的数值。
尝试绕过,我们删除这里的sessionid再次尝试提交请求,发现响应报文的结果发生了变化:
套入爆破模块测试效果:
成功爆破成功,这里推测的原因就是应用程序在处理登陆逻辑的时候出现失误,当客户端不存在cookie的时候不进行验证。这一点在我们第一次登陆的时候其实已经有了迹象,因此我们删除了请求报文中对应的cookie字段之后就直接跳过了执行流程。由此使得我们不用进行验证码的校验就可以进行登陆,从而可以进一步进行爆破攻击。
4.1.2 后台验证码不及时跟新引发的验证码绕过
在登录提交的时候进行验证码验证 不管密码是否正确,都要销毁验证码。
测试站点:
http://emlog.redteam.com/admin/
我们直接进行抓包分析,可以看出来无论我们重复提交多少次返回的数据报文仍旧是密码错误,并非验证码失效。故,验证码并未在输错密码后进行刷新,因此会引发我们可以进行爆破的bug
进入repeat模块尝试重放:
爆破模块测试:
4.2 识别绕过
这一步其实就没有什么技术含量了,找一个趁手的工具,想办法完成验证码识别+爆破一把梭即可
图片的干扰像素太少就会被一些工具识别出来,从而造成验证码失效被绕过的危害。
测试环境:这时候我们假装源站不存在cookie验证的逻辑问题即可
http://www.c4moon.com/index.php?case=user&act=login
我们需要拿到具有验证码识别的工具,首先再输入验证码的地方,我们进行验证码可用性测试。右击验证码,在新页面中打开,复制对应的url即可:
将其放置到工具中进行处理:
测试识别无误之后我们就可以进行爆破了,我们先从burp中拿到完整的请求报文。
将其复制到工具中:
进入爆破界面:注意这里的特征需要从burp中进行提取,放到框内即可
到这里,就可以使用此软件进行带验证码识别的爆破了。
5. 防御思路
当然,从上面一系列例子中大家可以发现,爆破的核心有两个,一个是拥有趁手的工具,还有一个就是准确的字典。
那么我们的防御思路也有两个,首先是针对字典的防御,我们在日常设置密码的时候可以强制用户必须用什么样的字符,比如大小写字母、数字8位混合密码。让用户的密码变成真正意义上的强密码。以此降低用户密码出现在黑客字典中的概率。
其次,我们可以在其工具上下功夫,也就是在人机识别上想办法。如果说传统的验证码会被绕过,那我们就用更加难以被机器识别的验证码,或者干脆添加单用户登陆手机验证、邮箱验证。如此一来便可以提高工具使用者的门槛。
当然,面对这样的自动化威胁,如果作为大型企业,其已经危害到我们的营业安全时。我们就应该考虑进行相应安全设备的使用,比如可以在自动化威胁防御方面做出强对抗的某些WAF,或者某厂商的动态应用防护系统等。都可以有效的抵抗暴力破解和撞库带来的危害。