RIFF¤ WEBPVP8 ˜ ðÑ *ôô>‘HŸK¥¤"§£±¨àð �PNG  ��� IHDR���0���0����`n���� cHRM��z&��������������u0���`��:���p��Q<���bKGD�������������tIME� 6���� AIDATX��]pU����{��{�G�n$$@ -�-jВAک��P��1O���j��:cU|hg�}�C�ʋU�:�A A�����|$$$������}�^}8i *�د�?w�9gݵ��:{��F"��&��4� �@��@q_����Ow��9<<|�ԩ�;w���"�#GV�^}Ճ7�|s˖-{��|��G�-[��R�Q�aőTR)� �2!�e�63��X�U������{��Z�m۶�^}�5����}����v�퟇R��J�J,�$� B�$Ф")�i��D�9+䜆B.�qf�үÇoذaժU�i>��so����a^���۷����3�<�ꫯnݺ��"���\���gn0�h��B�i� hR��,W*�e�65��LS�ر�0ēO>���755���ι@O?��ҥK������:::����1��X�9S�%�'�I���$��Sg�ڥ3'zF/� ��Z�8ES6WZ#�. �\��P�R�2����-[�,_�|�`�j�Xl6M���b�Z�* �jҟ0��҉B""� y22r�ܹ�CG�;���{7nn��ma���������2S���� <��x�⡡�|p.Pw��x��y�C�=��O� ��CB}�ӵ����?�wq`8�e����{+Չɱ�\{&� LL������vww��]��?q��Y�������P(���vuu9���S?w���ݻ�v<���mш ��D�DR&�j�X�����y񪂬�>���dyg�7��b��s�p��E���BDR� t����������=w�\�[;:[&._�Dlڸv�]�� u�驚�/Y�a�����d�%��*)1� �V\G���[F]����X���i����J:z�N�9�?xϭ+X�V|���U�n� �g���hҜ�b�aҢ ^��j�f�ZV�K��w.�ؾp�}{� �/e��{O�o�����R�8���i� !jB`�3n;Mw.=7�S�'��F�y W��x�}LXNfz���� �b�p�b�bq~�����s�4�H�2��q^�r�� n���\aFf4�����n�c��Q�n�X�,����ӑҤd5DDDd 9'd��,�l��.���)?��������#}C�k����ܖq����m�a��y��8D���,K)�I�$I�8NE�aH)�|�VCDƘ��DF0D@M �"3�+�����Kcú��+n}��-�k:W�K������3ƄRʌ��m۞��q�9WJ���d�0�, �8��ٶ�⦈B�h���䩡�eDCj&$ �1�Y��\�>{~`�M����ͷt�#?VZ'@D²l"�,+�ɤc0�r��R*��X��n�_kMD�1"""ι�:%X��� $�b:i�b4 �X<�/"r�����[Vo��T��0V�i���sΓ$IG���4M�c �R�eq��QS�+5{�{�,��a"� �D�2�CҐ(I`CS�s�ʥ�R&�p�����۴(�N���e�sq�Ғ|%�����k�=�0S3@�`�i9�K��Պ�0T�Y��ؼD*��DE��2�gO�bŷrY����z�T��R�҉҆SX�Tϑ����/�Zi�eL��X��jdx䏿�eَ ���7��П"?�����0y����<��R�N8�\X9ӥx ��^�L�l�ކ��u����/���Q�B�^p�f��\3��]�INƑ�L�"--�r�! 8?���Rp~����v��|�M��$����_M �����GgF�/U�^�^p�Dk�ٲ�vM� ����L$�eGʓ01*���Two��f��#���ޱ��7��!5rdy"D��V���\ט�� [y�f ���@���Um����2w\�fg_򯯃z�y���v|`$_ow402�|���c��Zt��J��Yw��݌�b8+L����R�t߉O�xS���'�L��`/lY�� ���Z;f�nX���f��$�<���Ϩ�J��z"�y��%�qzz��(B��Y�@D�)�uS���<�\.[�����*T(�8v�̗����rrr2I�� N5w����^k=�}�:�S�yӌ��ً+�����NY碧f����0)��h. �R����4�Ա�>�X,:����c�0�0 �Rn6���mii�MW*�j��i�I�0�,ˊ��� È�8���j�$I �hkk �`||�B!b��l6�8Ncc��U��<���1f�&"FQdYV�B�b���j3�>� !��j>���g���g��RD����8���r�08�׵u�7��]3������~�,b�P���%tEXtdate:create�2025-02-07T10:02:54+00:00� t����%tEXtdate:modify�2025-02-07T10:02:54+00:00�P�6���(tEXtdate:timestamp�2025-02-07T10:02:54+00:00�E������IEND�B`� 403WebShell
403Webshell
Server IP : 128.227.220.250  /  Your IP : 216.73.216.35
Web Server : Apache/2.4.64 (Unix) OpenSSL/1.0.2k-fips PHP/7.4.33
System : Linux dumont.ece.ufl.edu 3.10.0-1160.95.1.el7.x86_64 #1 SMP Mon Jul 24 13:59:37 UTC 2023 x86_64
User : daemon ( 2)
PHP Version : 7.4.33
Disable Function : NONE
MySQL : OFF  |  cURL : ON  |  WGET : ON  |  Perl : ON  |  Python : ON  |  Sudo : ON  |  Pkexec : ON
Directory :  /opt/source/BWASP/ManualAPI/modules/

Upload File :
current_dir [ Writeable ] document_root [ Writeable ]

 

Command :


[ Back ]     

Current File : /opt/source/BWASP/ManualAPI/modules/attack_vector.py
from bs4 import BeautifulSoup
import requests, json, re, base64, sys, os
from modules.keywordList import keywordCmp
from urllib.parse import urlparse
from modules import func
#sys.path.append(os.path.dirname(os.path.abspath(os.path.dirname(__file__))))


def attackHeader(target_url):
    dict_data = requests.get(target_url, verify=False).headers
    infor_data = ""
    infor_vector = ""
    try:
        http_method = requests.options(target_url, verify=False).headers['Allow'].replace(",", "").split(" ")
    except: #KeyError or ConnectionError
        http_method = "private"

    try:
        tmp_data = dict_data['Set-Cookie']
        i = len(tmp_data.split())
        if "HttpOnly" in tmp_data:
            for j in range(0, i):
                infor_data += tmp_data.split()[j] + "\n"
        elif "Secure" in tmp_data:
            for j in range(0, i):
                infor_data += tmp_data.split()[j] + "\n"
        else:
            infor_data = tmp_data
            infor_vector += "Not_HttpOnly\n"

    except:
        infor_vector += "Not_HttpOnly\n"

    try:
        tmp_data = dict_data['X-Frame-Options']
        i = len(tmp_data.split())
        for j in range(0, i):
            infor_data += tmp_data.split()[j] + "\n"

    except:
        infor_vector += "Not_X-Frame-Options\n"

    return http_method, infor_vector


def inputTag(response_body, http_method, infor_vector):
    # form tag action and input tag and input name parse
    try:
        soup = BeautifulSoup(response_body, 'html.parser')
    except:
        soup = BeautifulSoup("", 'html.parser')

    tag_list = list()
    tag_name_list = list()
    action_page = list()
    action_type = list()
    attack_vector = dict()  # list()
    data = dict()
    impactRate = 0
    check = 0
    cmp_sql_check = False
    cmp_sql_xss_check = False
    cmp_logic_check = False

    text = soup.find_all('input')
    form = soup.find_all('form')
    with open("./ManualAPI/modules/attack_vector.json", 'r', encoding='UTF8') as f:
        data = json.load(f)

    # ~~~~~~~~~~~~Allow Method
    if "private" not in http_method:
        data["info"]["allowMethod"] = http_method
    else:
        data["info"].pop("allowMethod")

    if len(text) != 0:
        for tag in text:
            try:
                if tag.attrs['type']:
                    pass
            except: #KeyError
                continue
            if tag.attrs['type'] != "submit" and len(text) != 0 and tag.attrs['type'] != "checkbox":
                tag_list.append(base64.b64encode(str(tag).encode('utf-8')).decode('utf-8'))  # input tag 값 ex) <input ~
                try:
                    tag_name_list.append(tag.attrs['name'].replace("'", "").replace("+", "").replace("\"", ""))
                except:
                    pass

                # ~~~~~~~~~~~~SQL Injection and XSS

                # th tag check (board) and type="password" check (login)
                if "<th" in response_body:
                    if "None" in data["doubt"]["SQL injection"]["type"] or "None" in data["doubt"]["XSS"]["type"]:
                        index_sql = data["doubt"]["SQL injection"]["type"].index("None")
                        index_xss = data["doubt"]["XSS"]["type"].index("None")
                        del (data["doubt"]["SQL injection"]["type"][index_sql])
                        del (data["doubt"]["XSS"]["type"][index_xss])

                    if "board" in data["doubt"]["SQL injection"]["type"] or "board" in data["doubt"]["XSS"]["type"]:
                        pass
                    else:
                        data["doubt"]["SQL injection"]["type"].append("board")
                        data["doubt"]["XSS"]["type"].append("board")

                        impactRate = 2

                try:
                    if tag.attrs['type'] == "password":
                        if "None" in data["doubt"]["SQL injection"]["type"] or "None" in data["doubt"]["XSS"]["type"]:
                            index_sql = data["doubt"]["SQL injection"]["type"].index("None")
                            index_xss = data["doubt"]["XSS"]["type"].index("None")
                            del (data["doubt"]["SQL injection"]["type"][index_sql])
                            del (data["doubt"]["XSS"]["type"][index_xss])

                        if "account" in data["doubt"]["SQL injection"]["type"] or "account" in data["doubt"]["XSS"]["type"]:
                            pass
                        else:
                            data["doubt"]["SQL injection"]["type"].append("account")
                            data["doubt"]["XSS"]["type"].append("account")

                            impactRate = 2
                except:
                    pass

                cmp_sql_check = keywordCmp().keywordCmp_SQL(tag_name_list, cmp_sql_check)
                cmp_sql_xss_check = keywordCmp().keywordCmp_SQL_XSS(tag_name_list, cmp_sql_xss_check)
                cmp_logic_check = keywordCmp().keywordCmp_Logic(tag_name_list, cmp_logic_check)

                if "board" in data["doubt"]["SQL injection"]["type"] or "board" in data["doubt"]["XSS"]["type"] \
                        or "account" in data["doubt"]["SQL injection"]["type"] or "account" in data["doubt"]["XSS"][
                    "type"] \
                        or "None" in data["doubt"]["SQL injection"]["type"] or "None" in data["doubt"]["XSS"]["type"]:
                    pass
                elif cmp_sql_check:
                    data["doubt"]["SQL injection"]["type"].append("None")

                    impactRate = 1
                elif cmp_sql_xss_check:
                    data["doubt"]["SQL injection"]["type"].append("None")
                    data["doubt"]["XSS"]["type"].append("None")

                    impactRate = 1
                elif cmp_logic_check:
                    data["doubt"]["Logic Flaw"] = True

                    impactRate = 1
                else:
                    if "SQL injection" in data["doubt"]:
                        pass
                    else:
                        data["doubt"]["Parameter"] = True

                        impactRate = 0

                if "Not_HttpOnly" in infor_vector:
                    if "HttpOnly" not in data["doubt"]["XSS"]["required"]:
                        data["doubt"]["XSS"]["required"].append("HttpOnly")

                    if impactRate != 2:
                        impactRate = 1

                if "Not_X-Frame-Options" in infor_vector:
                    if "X-Frame-Options" not in data["doubt"]["XSS"]["required"]:
                        data["doubt"]["XSS"]["required"].append("X-Frame-Options")

                    if impactRate != 2:
                        impactRate = 1

                try:
                    # ~~~~~~~~~~~~File Upload
                    if tag.attrs['type'] == "file":
                        data["doubt"]["File Upload"] = True
                        check = 2

                        impactRate = 2
                    else:
                        if check == 2:
                            pass
                        else:
                            check = 1
                except:
                    if "File Upload" in data["doubt"]:
                        data["doubt"].pop("File Upload")

        if check == 1:
            data["doubt"].pop("File Upload")

        attack_vector = data

    else:
        attack_vector = data
        try:
            attack_vector["doubt"].pop("SQL injection")
        except:
            pass
        try:
            attack_vector["doubt"].pop("XSS")
        except:
            pass
        try:
            attack_vector["doubt"].pop("File Upload")
        except:
            pass

    if form:
        for tag in form:
            try:
                action_page.append(base64.b64encode(tag.attrs['action'].encode('utf-8')).decode('utf-8'))
            except:
                pass
            try:
                action_type.append(base64.b64encode(tag.attrs['method'].encode('utf-8')).decode('utf-8'))
            except:
                pass

    return tag_list, tag_name_list, attack_vector, action_page, action_type, impactRate


def corsCheck(packet):
    cors_check = "None"

    response_header = packet["response"]["headers"]

    try:
        if response_header['access-control-allow-origin'] == "*":
            cors_check = "CORS Misconfiguration: *"
    except:
        pass

    return cors_check


def openRedirectionCheck(packet):
    try:
        if packet["open_redirect"]:
            return packet["request"]["full_url"]
    except:
        return ""


def s3BucketCheck(packet):
    return_s3_url = []
    patterns = ["s3\.[a-zA-Z0-9.-]+\.com",
                "[a-zA-Z0-9.-]+\.s3\.amazonaws\.com[\/]?[a-zA-Z0-9\-\/]*",
                "[a-zA-Z0-9.-]+\.amazonaws\.com[\/]?[a-zA-Z0-9\-\/]*"
                "[a-zA-Z0-9.-]+\.s3-[a-zA-Z0-9-]\.amazonaws\.com[\/]?[a-zA-Z0-9\-\/]*",
                "[a-zA-Z0-9.-]+\.s3-website[.-](?: eu|ap|us|ca|sa|cn)",
                "[\/\/]?s3\.amazonaws\.com\/[a-zA-Z0-9\-\/]*",
                "[\/\/]?s3-[a-z0-9-]+\.amazonaws\.com/[a-zA-Z0-9\-\/]*",
                "[a-zA-Z0-9-]+\.s3-[a-zA-Z0-9-]+\.amazonaws\.com/[a-zA-Z0-9\-\/]*",
                "[a-zA-Z0-9-]+\.s3-[a-zA-Z0-9-]+\.amazonaws\.com[\/]?[a-zA-Z0-9\-\/]*",
                "[a-zA-Z0-9\.\-]{3,63}\.s3[\.-](?: eu|ap|us|ca|sa)-\w{2,14}-\d{1,2}\.amazonaws.com[\/]?[a-zA-Z0-9\-\/]*",
                "[a-zA-Z0-9\.\-]{0,63}\.?s3.amazonaws\.com[\/]?[a-zA-Z0-9\-\/]*",
                "[a-zA-Z0-9\.\-]{3,63}\.s3-website[\.-](?: eu|ap|us|ca|sa|cn)-\w{2,14}-\d{1,2}\.amazonaws.com[\/]?[a-zA-Z0-9\-\/]*"]

    for pattern in patterns:
        regex = re.compile(pattern)
        res_body = regex.findall(packet["request"]["body"])
        req_body = regex.findall(packet["response"]["body"])

        if res_body:
            return_s3_url += res_body
        if req_body:
            return_s3_url += req_body

    return list(set(return_s3_url))


def jwtCheck(packet):
    return_jwt = []
    patterns = ["([a-zA-Z0-9_=]+)\.([a-zA-Z0-9_=]+)\.([a-zA-Z0-9_\-\+\/=]*)"]

    for pattern in patterns:
        regex = re.compile(pattern)
        req_header = []
        req_body = []
        res_header = []
        res_body = []

        for header_key in packet["request"]["headers"].keys():
            req_header += regex.findall(packet["request"]["headers"][header_key])
        for header_key in packet["response"]["headers"].keys():
            res_header += regex.findall(packet["response"]["headers"][header_key])
        req_body = regex.findall(packet["request"]["body"])
        res_body = regex.findall(packet["response"]["body"])

        return_jwt += req_header + req_body + res_header + res_body
    return list(set(return_jwt))


def robotsTxt(current_url):
    # 주요정보통신기반시설_기술적_취약점_분석_평가_방법_상세가이드.pdf [page 726] robots.txt not set
    return True if "user-agent" not in requests.get(current_url, verify=False).text.lower() or 404 == requests.get(current_url, verify=False).status_code else False


def errorPage(current_url):
    # 주요정보통신기반시설_기술적_취약점_뿐석_평가_방법_상세가이드.pdf [page 678] Error Page not set
    return True if 404 == requests.get(current_url, verify=False).status_code and "not found" in requests.get(current_url, verify=False).text.lower() else False

def ReflectedXSSCheck(packet: dict, target_url: str) -> bool:
    if not func.isSameDomain(packet["request"]["full_url"], target_url):
        return False

    queries = urlparse(packet["request"]["full_url"]).query

    if queries:
        queries = queries.split("&")
        try:
            soup = BeautifulSoup(packet["response"]["body"], "html.parser")
        except:
            return False

        for query in queries:
            datas = query.split("=")

            if len(datas) != 2:
                break

            input_tag = soup.find("input", {"name": datas[0]})
            if input_tag and datas[1] == input_tag.get("value"):
                return True

    return False


def SSRFCheck(packet: dict) -> bool:
    if "open_redirect" in packet.keys():
        return False

    if packet["request"]["method"] == "GET":
        queries = urlparse(packet["request"]["full_url"]).query.split("&")
        for data in queries:
            datas = data.split("=")

            if len(datas) != 2:
                continue

            if func.isStringAnUrl(datas[1]):
                return True

    elif packet["request"]["method"] == "POST":
        body = packet["request"]["body"]
        pattern = "((?:http|ftp|https)(?:://)([\w_-]+((\.[\w_-]+)+))([\w.,@?^=%&:/~+#-]*[\w@?^=%&/~+#-])?)"
        result = re.findall(pattern, body)

        if len(result) != 0:
            return True

    return False

# input tag 함수, Packets에서 불러오는 Cookie 값 + QueryString(Parameter) JSON 형태 예시 -> domain 테이블 Details 컬럼
"""
{
  "tag": [
    "tag A",
    "tag B"
  ],
  "cookie": {
    "PHPSESSID": "8a7s6f89sd6fg98f6s98d",
    "JSESSIONID": "abcdefghijklmnop"
  },
  "queryString": {
    "hello": "world"
  }
}

?hello=world
"""

Youez - 2016 - github.com/yon3zu
LinuXploit