1*9a0e4156SSadaf Ebrahimiimport os 2*9a0e4156SSadaf Ebrahimiimport sys 3*9a0e4156SSadaf Ebrahimiimport shutil 4*9a0e4156SSadaf Ebrahimi 5*9a0e4156SSadaf Ebrahimifrom distutils import log 6*9a0e4156SSadaf Ebrahimifrom distutils.core import setup 7*9a0e4156SSadaf Ebrahimifrom distutils.extension import Extension 8*9a0e4156SSadaf Ebrahimifrom distutils.command.build import build 9*9a0e4156SSadaf Ebrahimifrom Cython.Distutils import build_ext 10*9a0e4156SSadaf Ebrahimi 11*9a0e4156SSadaf EbrahimiSYSTEM = sys.platform 12*9a0e4156SSadaf EbrahimiVERSION = '4.0.0' 13*9a0e4156SSadaf Ebrahimi 14*9a0e4156SSadaf Ebrahimi# adapted from commit e504b81 of Nguyen Tan Cong 15*9a0e4156SSadaf Ebrahimi# Reference: https://docs.python.org/2/library/platform.html#cross-platform 16*9a0e4156SSadaf EbrahimiIS_64BITS = sys.maxsize > 2**32 17*9a0e4156SSadaf Ebrahimi 18*9a0e4156SSadaf Ebrahimi# are we building from the repository or from a source distribution? 19*9a0e4156SSadaf EbrahimiROOT_DIR = os.path.dirname(os.path.realpath(__file__)) 20*9a0e4156SSadaf EbrahimiLIBS_DIR = os.path.join(ROOT_DIR, 'pyx', 'lib') 21*9a0e4156SSadaf EbrahimiHEADERS_DIR = os.path.join(ROOT_DIR, 'pyx', 'include') 22*9a0e4156SSadaf EbrahimiSRC_DIR = os.path.join(ROOT_DIR, 'src') 23*9a0e4156SSadaf EbrahimiBUILD_DIR = SRC_DIR if os.path.exists(SRC_DIR) else os.path.join(ROOT_DIR, '../..') 24*9a0e4156SSadaf EbrahimiPYPACKAGE_DIR = os.path.join(ROOT_DIR, 'capstone') 25*9a0e4156SSadaf EbrahimiCYPACKAGE_DIR = os.path.join(ROOT_DIR, 'pyx') 26*9a0e4156SSadaf Ebrahimi 27*9a0e4156SSadaf Ebrahimiif SYSTEM == 'darwin': 28*9a0e4156SSadaf Ebrahimi VERSIONED_LIBRARY_FILE = "libcapstone.4.dylib" 29*9a0e4156SSadaf Ebrahimi LIBRARY_FILE = "libcapstone.dylib" 30*9a0e4156SSadaf Ebrahimi STATIC_LIBRARY_FILE = 'libcapstone.a' 31*9a0e4156SSadaf Ebrahimielif SYSTEM in ('win32', 'cygwin'): 32*9a0e4156SSadaf Ebrahimi VERSIONED_LIBRARY_FILE = "capstone.dll" 33*9a0e4156SSadaf Ebrahimi LIBRARY_FILE = "capstone.dll" 34*9a0e4156SSadaf Ebrahimi STATIC_LIBRARY_FILE = None 35*9a0e4156SSadaf Ebrahimielse: 36*9a0e4156SSadaf Ebrahimi VERSIONED_LIBRARY_FILE = "libcapstone.so.4" 37*9a0e4156SSadaf Ebrahimi LIBRARY_FILE = "libcapstone.so" 38*9a0e4156SSadaf Ebrahimi STATIC_LIBRARY_FILE = 'libcapstone.a' 39*9a0e4156SSadaf Ebrahimi 40*9a0e4156SSadaf Ebrahimicompile_args = ['-O3', '-fomit-frame-pointer', '-I' + HEADERS_DIR] 41*9a0e4156SSadaf Ebrahimilink_args = ['-L' + LIBS_DIR] 42*9a0e4156SSadaf Ebrahimi 43*9a0e4156SSadaf Ebrahimiext_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' ] 44*9a0e4156SSadaf Ebrahimi 45*9a0e4156SSadaf Ebrahimiext_modules = [Extension("capstone.ccapstone", 46*9a0e4156SSadaf Ebrahimi ["pyx/ccapstone.pyx"], 47*9a0e4156SSadaf Ebrahimi libraries=["capstone"], 48*9a0e4156SSadaf Ebrahimi extra_compile_args=compile_args, 49*9a0e4156SSadaf Ebrahimi extra_link_args=link_args)] 50*9a0e4156SSadaf Ebrahimiext_modules += [Extension("capstone.%s" % name, 51*9a0e4156SSadaf Ebrahimi ["pyx/%s.pyx" % name], 52*9a0e4156SSadaf Ebrahimi extra_compile_args=compile_args, 53*9a0e4156SSadaf Ebrahimi extra_link_args=link_args) 54*9a0e4156SSadaf Ebrahimi for name in ext_module_names] 55*9a0e4156SSadaf Ebrahimi 56*9a0e4156SSadaf Ebrahimidef clean_bins(): 57*9a0e4156SSadaf Ebrahimi shutil.rmtree(LIBS_DIR, ignore_errors=True) 58*9a0e4156SSadaf Ebrahimi shutil.rmtree(HEADERS_DIR, ignore_errors=True) 59*9a0e4156SSadaf Ebrahimi 60*9a0e4156SSadaf Ebrahimidef copy_pysources(): 61*9a0e4156SSadaf Ebrahimi for fname in os.listdir(PYPACKAGE_DIR): 62*9a0e4156SSadaf Ebrahimi if not fname.endswith('.py'): 63*9a0e4156SSadaf Ebrahimi continue 64*9a0e4156SSadaf Ebrahimi 65*9a0e4156SSadaf Ebrahimi if fname == '__init__.py': 66*9a0e4156SSadaf Ebrahimi shutil.copy(os.path.join(PYPACKAGE_DIR, fname), os.path.join(CYPACKAGE_DIR, fname)) 67*9a0e4156SSadaf Ebrahimi else: 68*9a0e4156SSadaf Ebrahimi shutil.copy(os.path.join(PYPACKAGE_DIR, fname), os.path.join(CYPACKAGE_DIR, fname + 'x')) 69*9a0e4156SSadaf Ebrahimi 70*9a0e4156SSadaf Ebrahimidef build_libraries(): 71*9a0e4156SSadaf Ebrahimi """ 72*9a0e4156SSadaf Ebrahimi Prepare the capstone directory for a binary distribution or installation. 73*9a0e4156SSadaf Ebrahimi Builds shared libraries and copies header files. 74*9a0e4156SSadaf Ebrahimi 75*9a0e4156SSadaf Ebrahimi Will use a src/ dir if one exists in the current directory, otherwise assumes it's in the repo 76*9a0e4156SSadaf Ebrahimi """ 77*9a0e4156SSadaf Ebrahimi cwd = os.getcwd() 78*9a0e4156SSadaf Ebrahimi clean_bins() 79*9a0e4156SSadaf Ebrahimi os.mkdir(HEADERS_DIR) 80*9a0e4156SSadaf Ebrahimi os.mkdir(LIBS_DIR) 81*9a0e4156SSadaf Ebrahimi 82*9a0e4156SSadaf Ebrahimi # copy public headers 83*9a0e4156SSadaf Ebrahimi shutil.copytree(os.path.join(BUILD_DIR, 'include', 'capstone'), os.path.join(HEADERS_DIR, 'capstone')) 84*9a0e4156SSadaf Ebrahimi 85*9a0e4156SSadaf Ebrahimi os.chdir(BUILD_DIR) 86*9a0e4156SSadaf Ebrahimi 87*9a0e4156SSadaf Ebrahimi # platform description refers at https://docs.python.org/2/library/sys.html#sys.platform 88*9a0e4156SSadaf Ebrahimi if SYSTEM == "win32": 89*9a0e4156SSadaf Ebrahimi # Windows build: this process requires few things: 90*9a0e4156SSadaf Ebrahimi # - CMake + MSVC installed 91*9a0e4156SSadaf Ebrahimi # - Run this command in an environment setup for MSVC 92*9a0e4156SSadaf Ebrahimi if not os.path.exists("build"): os.mkdir("build") 93*9a0e4156SSadaf Ebrahimi os.chdir("build") 94*9a0e4156SSadaf Ebrahimi # Do not build tests & static library 95*9a0e4156SSadaf Ebrahimi os.system('cmake -DCMAKE_BUILD_TYPE=RELEASE -DCAPSTONE_BUILD_TESTS=0 -DCAPSTONE_BUILD_STATIC=0 -G "NMake Makefiles" ..') 96*9a0e4156SSadaf Ebrahimi os.system("nmake") 97*9a0e4156SSadaf Ebrahimi else: # Unix incl. cygwin 98*9a0e4156SSadaf Ebrahimi os.system("CAPSTONE_BUILD_CORE_ONLY=yes bash ./make.sh") 99*9a0e4156SSadaf Ebrahimi 100*9a0e4156SSadaf Ebrahimi shutil.copy(VERSIONED_LIBRARY_FILE, os.path.join(LIBS_DIR, LIBRARY_FILE)) 101*9a0e4156SSadaf Ebrahimi if STATIC_LIBRARY_FILE: shutil.copy(STATIC_LIBRARY_FILE, LIBS_DIR) 102*9a0e4156SSadaf Ebrahimi os.chdir(cwd) 103*9a0e4156SSadaf Ebrahimi 104*9a0e4156SSadaf Ebrahimi 105*9a0e4156SSadaf Ebrahimiclass custom_build(build): 106*9a0e4156SSadaf Ebrahimi def run(self): 107*9a0e4156SSadaf Ebrahimi log.info('Copying python sources') 108*9a0e4156SSadaf Ebrahimi copy_pysources() 109*9a0e4156SSadaf Ebrahimi log.info('Building C extensions') 110*9a0e4156SSadaf Ebrahimi build_libraries() 111*9a0e4156SSadaf Ebrahimi return build.run(self) 112*9a0e4156SSadaf Ebrahimi 113*9a0e4156SSadaf Ebrahimi# clean package directory first 114*9a0e4156SSadaf Ebrahimi#import os.path, shutil, sys 115*9a0e4156SSadaf Ebrahimi#for f in sys.path: 116*9a0e4156SSadaf Ebrahimi# if f.endswith('packages'): 117*9a0e4156SSadaf Ebrahimi# pkgdir = os.path.join(f, 'capstone') 118*9a0e4156SSadaf Ebrahimi# #print(pkgdir) 119*9a0e4156SSadaf Ebrahimi# try: 120*9a0e4156SSadaf Ebrahimi# shutil.rmtree(pkgdir) 121*9a0e4156SSadaf Ebrahimi# except: 122*9a0e4156SSadaf Ebrahimi# pass 123*9a0e4156SSadaf Ebrahimi 124*9a0e4156SSadaf Ebrahimisetup( 125*9a0e4156SSadaf Ebrahimi provides = ['capstone'], 126*9a0e4156SSadaf Ebrahimi package_dir = {'capstone' : 'pyx'}, 127*9a0e4156SSadaf Ebrahimi packages = ['capstone'], 128*9a0e4156SSadaf Ebrahimi name = 'capstone', 129*9a0e4156SSadaf Ebrahimi version = VERSION, 130*9a0e4156SSadaf Ebrahimi cmdclass = {'build_ext': build_ext, 'build': custom_build}, 131*9a0e4156SSadaf Ebrahimi ext_modules = ext_modules, 132*9a0e4156SSadaf Ebrahimi author = 'Nguyen Anh Quynh', 133*9a0e4156SSadaf Ebrahimi author_email = '[email protected]', 134*9a0e4156SSadaf Ebrahimi description = 'Capstone disassembly engine', 135*9a0e4156SSadaf Ebrahimi url = 'http://www.capstone-engine.org', 136*9a0e4156SSadaf Ebrahimi classifiers = [ 137*9a0e4156SSadaf Ebrahimi 'License :: OSI Approved :: BSD License', 138*9a0e4156SSadaf Ebrahimi 'Programming Language :: Python :: 2', 139*9a0e4156SSadaf Ebrahimi ], 140*9a0e4156SSadaf Ebrahimi include_package_data=True, 141*9a0e4156SSadaf Ebrahimi package_data={ 142*9a0e4156SSadaf Ebrahimi "capstone": ["lib/*", "include/capstone/*"], 143*9a0e4156SSadaf Ebrahimi } 144*9a0e4156SSadaf Ebrahimi) 145