aboutsummaryrefslogtreecommitdiffstats
path: root/capstone/bindings/python/setup_cython.py
diff options
context:
space:
mode:
Diffstat (limited to 'capstone/bindings/python/setup_cython.py')
-rw-r--r--capstone/bindings/python/setup_cython.py144
1 files changed, 144 insertions, 0 deletions
diff --git a/capstone/bindings/python/setup_cython.py b/capstone/bindings/python/setup_cython.py
new file mode 100644
index 000000000..d36769a02
--- /dev/null
+++ b/capstone/bindings/python/setup_cython.py
@@ -0,0 +1,144 @@
+import os
+import sys
+import shutil
+
+from distutils import log
+from distutils.core import setup
+from distutils.extension import Extension
+from distutils.command.build import build
+from Cython.Distutils import build_ext
+
+SYSTEM = sys.platform
+VERSION = '4.0.0'
+
+# adapted from commit e504b81 of Nguyen Tan Cong
+# Reference: https://docs.python.org/2/library/platform.html#cross-platform
+IS_64BITS = sys.maxsize > 2**32
+
+# are we building from the repository or from a source distribution?
+ROOT_DIR = os.path.dirname(os.path.realpath(__file__))
+LIBS_DIR = os.path.join(ROOT_DIR, 'pyx', 'lib')
+HEADERS_DIR = os.path.join(ROOT_DIR, 'pyx', 'include')
+SRC_DIR = os.path.join(ROOT_DIR, 'src')
+BUILD_DIR = SRC_DIR if os.path.exists(SRC_DIR) else os.path.join(ROOT_DIR, '../..')
+PYPACKAGE_DIR = os.path.join(ROOT_DIR, 'capstone')
+CYPACKAGE_DIR = os.path.join(ROOT_DIR, 'pyx')
+
+if SYSTEM == 'darwin':
+ VERSIONED_LIBRARY_FILE = "libcapstone.4.dylib"
+ LIBRARY_FILE = "libcapstone.dylib"
+ STATIC_LIBRARY_FILE = 'libcapstone.a'
+elif SYSTEM in ('win32', 'cygwin'):
+ VERSIONED_LIBRARY_FILE = "capstone.dll"
+ LIBRARY_FILE = "capstone.dll"
+ STATIC_LIBRARY_FILE = None
+else:
+ VERSIONED_LIBRARY_FILE = "libcapstone.so.4"
+ LIBRARY_FILE = "libcapstone.so"
+ STATIC_LIBRARY_FILE = 'libcapstone.a'
+
+compile_args = ['-O3', '-fomit-frame-pointer', '-I' + HEADERS_DIR]
+link_args = ['-L' + LIBS_DIR]
+
+ext_module_names = ['arm', 'arm_const', 'arm64', 'arm64_const', 'm68k', 'm68k_const', 'm680x', 'm680x_const', 'mips', 'mips_const', 'ppc', 'ppc_const', 'x86', 'x86_const', 'sparc', 'sparc_const', 'systemz', 'sysz_const', 'xcore', 'xcore_const', 'tms320c64x', 'tms320c64x_const', 'evm', 'evm_const' ]
+
+ext_modules = [Extension("capstone.ccapstone",
+ ["pyx/ccapstone.pyx"],
+ libraries=["capstone"],
+ extra_compile_args=compile_args,
+ extra_link_args=link_args)]
+ext_modules += [Extension("capstone.%s" % name,
+ ["pyx/%s.pyx" % name],
+ extra_compile_args=compile_args,
+ extra_link_args=link_args)
+ for name in ext_module_names]
+
+def clean_bins():
+ shutil.rmtree(LIBS_DIR, ignore_errors=True)
+ shutil.rmtree(HEADERS_DIR, ignore_errors=True)
+
+def copy_pysources():
+ for fname in os.listdir(PYPACKAGE_DIR):
+ if not fname.endswith('.py'):
+ continue
+
+ if fname == '__init__.py':
+ shutil.copy(os.path.join(PYPACKAGE_DIR, fname), os.path.join(CYPACKAGE_DIR, fname))
+ else:
+ shutil.copy(os.path.join(PYPACKAGE_DIR, fname), os.path.join(CYPACKAGE_DIR, fname + 'x'))
+
+def build_libraries():
+ """
+ Prepare the capstone directory for a binary distribution or installation.
+ Builds shared libraries and copies header files.
+
+ Will use a src/ dir if one exists in the current directory, otherwise assumes it's in the repo
+ """
+ cwd = os.getcwd()
+ clean_bins()
+ os.mkdir(HEADERS_DIR)
+ os.mkdir(LIBS_DIR)
+
+ # copy public headers
+ shutil.copytree(os.path.join(BUILD_DIR, 'include', 'capstone'), os.path.join(HEADERS_DIR, 'capstone'))
+
+ os.chdir(BUILD_DIR)
+
+ # platform description refers at https://docs.python.org/2/library/sys.html#sys.platform
+ if SYSTEM == "win32":
+ # Windows build: this process requires few things:
+ # - CMake + MSVC installed
+ # - Run this command in an environment setup for MSVC
+ if not os.path.exists("build"): os.mkdir("build")
+ os.chdir("build")
+ # Do not build tests & static library
+ os.system('cmake -DCMAKE_BUILD_TYPE=RELEASE -DCAPSTONE_BUILD_TESTS=0 -DCAPSTONE_BUILD_STATIC=0 -G "NMake Makefiles" ..')
+ os.system("nmake")
+ else: # Unix incl. cygwin
+ os.system("CAPSTONE_BUILD_CORE_ONLY=yes bash ./make.sh")
+
+ shutil.copy(VERSIONED_LIBRARY_FILE, os.path.join(LIBS_DIR, LIBRARY_FILE))
+ if STATIC_LIBRARY_FILE: shutil.copy(STATIC_LIBRARY_FILE, LIBS_DIR)
+ os.chdir(cwd)
+
+
+class custom_build(build):
+ def run(self):
+ log.info('Copying python sources')
+ copy_pysources()
+ log.info('Building C extensions')
+ build_libraries()
+ return build.run(self)
+
+# clean package directory first
+#import os.path, shutil, sys
+#for f in sys.path:
+# if f.endswith('packages'):
+# pkgdir = os.path.join(f, 'capstone')
+# #print(pkgdir)
+# try:
+# shutil.rmtree(pkgdir)
+# except:
+# pass
+
+setup(
+ provides = ['capstone'],
+ package_dir = {'capstone' : 'pyx'},
+ packages = ['capstone'],
+ name = 'capstone',
+ version = VERSION,
+ cmdclass = {'build_ext': build_ext, 'build': custom_build},
+ ext_modules = ext_modules,
+ author = 'Nguyen Anh Quynh',
+ author_email = 'aquynh@gmail.com',
+ description = 'Capstone disassembly engine',
+ url = 'http://www.capstone-engine.org',
+ classifiers = [
+ 'License :: OSI Approved :: BSD License',
+ 'Programming Language :: Python :: 2',
+ ],
+ include_package_data=True,
+ package_data={
+ "capstone": ["lib/*", "include/capstone/*"],
+ }
+)