def CHECK_LIB(conf, libs, mandatory=False, empty_decl=True, set_target=True, shlib=False): '''check if a set of libraries exist as system libraries returns the sublist of libs that do exist as a syslib or [] ''' fragment = ''' int foo() { int v = 2; return v*2; } ''' ret = [] liblist = TO_LIST(libs) for lib in liblist[:]: if GET_TARGET_TYPE(conf, lib) == 'SYSLIB': ret.append(lib) continue (ccflags, ldflags, cpppath) = library_flags(conf, lib) if shlib: res = conf.check(features='cc cshlib', fragment=fragment, lib=lib, uselib_store=lib, ccflags=ccflags, ldflags=ldflags, uselib=lib.upper()) else: res = conf.check(lib=lib, uselib_store=lib, ccflags=ccflags, ldflags=ldflags, uselib=lib.upper()) if not res: if mandatory: Logs.error( "Mandatory library '%s' not found for functions '%s'" % (lib, list)) sys.exit(1) if empty_decl: # if it isn't a mandatory library, then remove it from dependency lists if set_target: SET_TARGET_TYPE(conf, lib, 'EMPTY') else: conf.define('HAVE_LIB%s' % lib.upper().replace('-', '_'), 1) conf.env['LIB_' + lib.upper()] = lib if set_target: conf.SET_TARGET_TYPE(lib, 'SYSLIB') ret.append(lib) return ret
def check_ruby_ext_devel(conf): if not conf.env.RUBY: conf.fatal('ruby detection is required first') if not conf.env.CC_NAME and not conf.env.CXX_NAME: conf.fatal('load a c/c++ compiler first') version = tuple(map(int, conf.env.RUBY_VERSION.split("."))) def read_out(cmd): return Utils.to_list(Utils.cmd_output([conf.env.RUBY, '-rrbconfig', '-e', cmd])) def read_config(key): return read_out('puts Config::CONFIG[%r]' % key) ruby = conf.env['RUBY'] archdir = read_config('archdir') cpppath = archdir if version >= (1, 9, 0): ruby_hdrdir = read_config('rubyhdrdir') cpppath += ruby_hdrdir cpppath += [os.path.join(ruby_hdrdir[0], read_config('arch')[0])] conf.check(header_name='ruby.h', includes=cpppath, mandatory=True, errmsg='could not find ruby header file') conf.env.LIBPATH_RUBYEXT = read_config('libdir') conf.env.LIBPATH_RUBYEXT += archdir conf.env.CPPPATH_RUBYEXT = cpppath conf.env.CCFLAGS_RUBYEXT = read_config("CCDLFLAGS") conf.env.rubyext_PATTERN = '%s.' + read_config('DLEXT')[0] # ok this is really stupid, but the command and flags are combined. # so we try to find the first argument... flags = read_config('LDSHARED') while flags and flags[0][0] != '-': flags = flags[1:] # we also want to strip out the deprecated ppc flags if len(flags) > 1 and flags[1] == "ppc": flags = flags[2:] conf.env.LINKFLAGS_RUBYEXT = flags conf.env.LINKFLAGS_RUBYEXT += read_config("LIBS") conf.env.LINKFLAGS_RUBYEXT += read_config("LIBRUBYARG_SHARED") if Options.options.rubyarchdir: conf.env.ARCHDIR_RUBY = Options.options.rubyarchdir else: conf.env.ARCHDIR_RUBY = read_config('sitearchdir')[0] if Options.options.rubylibdir: conf.env.LIBDIR_RUBY = Options.options.rubylibdir else: conf.env.LIBDIR_RUBY = read_config('sitelibdir')[0]
def check_ruby_ext_devel(conf): if not conf.env.RUBY: conf.fatal('ruby detection is required first') if not conf.env.CC_NAME and not conf.env.CXX_NAME: conf.fatal('load a c/c++ compiler first') version = tuple(map(int, conf.env.RUBY_VERSION.split("."))) def read_out(cmd): return Utils.to_list(Utils.cmd_output([conf.env.RUBY, '-rrbconfig', '-e', cmd])) def read_config(key): return read_out('puts Config::CONFIG[%r]' % key) ruby = conf.env['RUBY'] archdir = read_config('archdir') cpppath = archdir if version >= (1, 9, 0): ruby_hdrdir = read_config('rubyhdrdir') cpppath += ruby_hdrdir cpppath += [os.path.join(ruby_hdrdir[0], read_config('arch')[0])] conf.check(header_name='ruby.h', includes=cpppath, mandatory=True, errmsg='could not find ruby header file') conf.env.LIBPATH_RUBYEXT = read_config('libdir') conf.env.LIBPATH_RUBYEXT += archdir conf.env.CPPPATH_RUBYEXT = cpppath conf.env.CCFLAGS_RUBYEXT = read_config("CCDLFLAGS") conf.env.rubyext_PATTERN = '%s.' + read_config('DLEXT')[0] # ok this is really stupid, but the command and flags are combined. # so we try to find the first argument... flags = read_config('LDSHARED') while flags and flags[0][0] != '-': flags = flags[1:] # we also want to strip out the deprecated ppc flags if len(flags) > 1 and flags[1] == "ppc": flags = flags[2:] conf.env.LINKFLAGS_RUBYEXT = flags conf.env.LINKFLAGS_RUBYEXT += read_config("LIBS") conf.env.LINKFLAGS_RUBYEXT += read_config("LIBRUBYARG_SHARED") if Options.options.rubyarchdir: conf.env.ARCHDIR_RUBY = Options.options.rubyarchdir else: conf.env.ARCHDIR_RUBY = read_config('sitearchdir')[0] if Options.options.rubylibdir: conf.env.LIBDIR_RUBY = Options.options.rubylibdir else: conf.env.LIBDIR_RUBY = read_config('sitelibdir')[0]
def CHECK_LIB(conf, libs, mandatory=False, empty_decl=True, set_target=True, shlib=False): """check if a set of libraries exist as system libraries returns the sublist of libs that do exist as a syslib or [] """ fragment = """ int foo() { int v = 2; return v*2; } """ ret = [] liblist = TO_LIST(libs) for lib in liblist[:]: if GET_TARGET_TYPE(conf, lib) == "SYSLIB": ret.append(lib) continue (ccflags, ldflags, cpppath) = library_flags(conf, lib) if shlib: res = conf.check( features="c cshlib", fragment=fragment, lib=lib, uselib_store=lib, ccflags=ccflags, ldflags=ldflags, uselib=lib.upper(), mandatory=False, ) else: res = conf.check( lib=lib, uselib_store=lib, ccflags=ccflags, ldflags=ldflags, uselib=lib.upper(), mandatory=False ) if not res: if mandatory: Logs.error("Mandatory library '%s' not found for functions '%s'" % (lib, list)) sys.exit(1) if empty_decl: # if it isn't a mandatory library, then remove it from dependency lists if set_target: SET_TARGET_TYPE(conf, lib, "EMPTY") else: conf.define("HAVE_LIB%s" % lib.upper().replace("-", "_").replace(".", "_"), 1) conf.env["LIB_" + lib.upper()] = lib if set_target: conf.SET_TARGET_TYPE(lib, "SYSLIB") ret.append(lib) return ret
def check_jni_headers(conf): """ Check for jni headers and libraries On success the environment variable xxx_JAVA is added for uselib """ if not conf.env.CC_NAME and not conf.env.CXX_NAME: conf.fatal('load a compiler first (gcc, g++, ..)') if not conf.env.JAVA_HOME: conf.fatal('set JAVA_HOME in the system environment') # jni requires the jvm javaHome = conf.env['JAVA_HOME'][0] b = Build.BuildContext() b.load_dirs(conf.srcdir, conf.blddir) dir = b.root.find_dir(conf.env.JAVA_HOME[0] + '/include') f = dir.ant_glob('**/(jni|jni_md).h', flat=False) incDirs = [x.parent.abspath() for x in f] dir = b.root.find_dir(conf.env.JAVA_HOME[0]) f = dir.ant_glob('**/*jvm.(so|dll)', flat=False) libDirs = [x.parent.abspath() for x in f] or [javaHome] for i, d in enumerate(libDirs): if conf.check(header_name='jni.h', define_name='HAVE_JNI_H', lib='jvm', libpath=d, includes=incDirs, uselib_store='JAVA', uselib='JAVA'): break else: conf.fatal('could not find lib jvm in %r (see config.log)' % libDirs)
def CHECK_HEADER(conf, h, add_headers=False, lib=None): '''check for a header''' if h in missing_headers and lib is None: return False d = h.upper().replace('/', '_') d = d.replace('.', '_') d = d.replace('-', '_') d = 'HAVE_{0!s}'.format(d) if CONFIG_SET(conf, d): if add_headers: if not h in conf.env.hlist: conf.env.hlist.append(h) return True (ccflags, ldflags, cpppath) = library_flags(conf, lib) hdrs = hlist_to_string(conf, headers=h) if lib is None: lib = "" ret = conf.check(fragment='{0!s}\nint main(void) {{ return 0; }}'.format(hdrs), type='nolink', execute=0, ccflags=ccflags, mandatory=False, includes=cpppath, uselib=lib.upper(), msg="Checking for header {0!s}".format(h)) if not ret: missing_headers.add(h) return False conf.DEFINE(d, 1) if add_headers and not h in conf.env.hlist: conf.env.hlist.append(h) return ret
def check_jni_headers(conf): if not conf.env.CC_NAME and not conf.env.CXX_NAME: conf.fatal('load a compiler first (gcc, g++, ..)') if not conf.env.JAVA_HOME: conf.fatal('set JAVA_HOME in the system environment') javaHome = conf.env['JAVA_HOME'][0] b = Build.BuildContext() b.load_dirs(conf.srcdir, conf.blddir) dir = b.root.find_dir(conf.env.JAVA_HOME[0] + '/include') f = dir.ant_glob('**/(jni|jni_md).h', flat=False) incDirs = [x.parent.abspath() for x in f] dir = b.root.find_dir(conf.env.JAVA_HOME[0]) f = dir.ant_glob('**/*jvm.(so|dll)', flat=False) libDirs = [x.parent.abspath() for x in f] or [javaHome] for i, d in enumerate(libDirs): if conf.check(header_name='jni.h', define_name='HAVE_JNI_H', lib='jvm', libpath=d, includes=incDirs, uselib_store='JAVA', uselib='JAVA'): break else: conf.fatal('could not find lib jvm in %r (see config.log)' % libDirs)
def CHECK_LDFLAGS(conf, ldflags): '''check if the given ldflags are accepted by the linker ''' return conf.check(fragment='int main(void) { return 0; }\n', execute=0, ldflags=ldflags, msg="Checking linker accepts %s" % ldflags)
def CHECK_HEADER(conf, h, add_headers=False, lib=None): '''check for a header''' if h in missing_headers and lib is None: return False d = h.upper().replace('/', '_') d = d.replace('.', '_') d = d.replace('-', '_') d = 'HAVE_%s' % d if CONFIG_SET(conf, d): if add_headers: if not h in conf.env.hlist: conf.env.hlist.append(h) return True (ccflags, ldflags, cpppath) = library_flags(conf, lib) hdrs = hlist_to_string(conf, headers=h) if lib is None: lib = "" ret = conf.check(fragment='%s\nint main(void) { return 0; }' % hdrs, type='nolink', execute=0, ccflags=ccflags, mandatory=False, includes=cpppath, uselib=lib.upper(), msg="Checking for header %s" % h) if not ret: missing_headers.add(h) return False conf.DEFINE(d, 1) if add_headers and not h in conf.env.hlist: conf.env.hlist.append(h) return ret
def CHECK_LDFLAGS(conf, ldflags): '''check if the given ldflags are accepted by the linker ''' return conf.check(fragment='int main(void) { return 0; }\n', execute=0, ldflags=ldflags, msg="Checking linker accepts %s" % ldflags)
def CHECK_HEADER(conf, h, add_headers=False, lib=None): '''check for a header''' if h in missing_headers and lib is None: return False d = h.upper().replace('/', '_') d = d.replace('.', '_') d = d.replace('-', '_') d = 'HAVE_%s' % d if CONFIG_SET(conf, d): if add_headers: if not h in conf.env.hlist: conf.env.hlist.append(h) return True (ccflags, ldflags) = library_flags(conf, lib) hdrs = hlist_to_string(conf, headers=h) if lib is None: lib = "" ret = conf.check(fragment='%s\nint main(void) { return 0; }' % hdrs, type='nolink', execute=0, ccflags=ccflags, uselib=lib.upper(), msg="Checking for header %s" % h) if not ret: missing_headers.add(h) return False conf.DEFINE(d, 1) if add_headers and not h in conf.env.hlist: conf.env.hlist.append(h) return ret
def CHECK_LDFLAGS(conf, ldflags): '''check if the given ldflags are accepted by the linker ''' return conf.check(fragment='int main(void) { return 0; }\n', execute=0, ldflags=ldflags, mandatory=False, msg="Checking linker accepts {0!s}".format(ldflags))
def CHECK_CFLAGS(conf, cflags, fragment='int main(void) { return 0; }\n'): '''check if the given cflags are accepted by the compiler ''' return conf.check(fragment=fragment, execute=0, type='nolink', ccflags=cflags, msg="Checking compiler accepts %s" % cflags)
def CHECK_CFLAGS(conf, cflags): '''check if the given cflags are accepted by the compiler ''' return conf.check(fragment='int main(void) { return 0; }\n', execute=0, type='nolink', ccflags=cflags, msg="Checking compiler accepts %s" % cflags)
def CHECK_LIB(conf, libs, mandatory=False, empty_decl=True, set_target=True, shlib=False): '''check if a set of libraries exist as system libraries returns the sublist of libs that do exist as a syslib or [] ''' fragment= ''' int foo() { int v = 2; return v*2; } ''' ret = [] liblist = TO_LIST(libs) for lib in liblist[:]: if GET_TARGET_TYPE(conf, lib) == 'SYSLIB': ret.append(lib) continue (ccflags, ldflags, cpppath) = library_flags(conf, lib) if lib == 'menu' or lib == 'panel' or lib == 'form': ldflags = '-lncurses' if shlib: res = conf.check(features='cc cshlib', fragment=fragment, lib=lib, uselib_store=lib, ccflags=ccflags, ldflags=ldflags, uselib=lib.upper()) else: res = conf.check(lib=lib, uselib_store=lib, ccflags=ccflags, ldflags=ldflags, uselib=lib.upper()) if not res: if mandatory: Logs.error("Mandatory library '%s' not found for functions '%s'" % (lib, list)) sys.exit(1) if empty_decl: # if it isn't a mandatory library, then remove it from dependency lists if set_target: SET_TARGET_TYPE(conf, lib, 'EMPTY') else: conf.define('HAVE_LIB%s' % lib.upper().replace('-','_').replace('.','_'), 1) conf.env['LIB_' + lib.upper()] = lib if set_target: conf.SET_TARGET_TYPE(lib, 'SYSLIB') ret.append(lib) return ret
def CHECK_LDFLAGS(conf, ldflags): """check if the given ldflags are accepted by the linker """ return conf.check( fragment="int main(void) { return 0; }\n", execute=0, ldflags=ldflags, mandatory=False, msg="Checking linker accepts %s" % ldflags, )
def CHECK_CFLAGS(conf, cflags, fragment='int main(void) { return 0; }\n'): '''check if the given cflags are accepted by the compiler ''' check_cflags = TO_LIST(cflags) if 'WERROR_CFLAGS' in conf.env: check_cflags.extend(conf.env['WERROR_CFLAGS']) return conf.check(fragment=fragment, execute=0, type='nolink', ccflags=check_cflags, msg="Checking compiler accepts %s" % cflags)
def CHECK_SHLIB_INTRASINC_NAME_FLAGS(conf, msg): ''' check if the waf default flags for setting the name of lib are ok ''' snip = ''' int foo(int v) { return v * 2; } ''' return conf.check(features='cc cshlib',vnum="1",fragment=snip,msg=msg)
def CHECK_SHLIB_INTRASINC_NAME_FLAGS(conf, msg): ''' check if the waf default flags for setting the name of lib are ok ''' snip = ''' int foo(int v) { return v * 2; } ''' return conf.check(features='cc cshlib',vnum="1",fragment=snip,msg=msg)
def CHECK_SHLIB_W_PYTHON(conf, msg): '''check if we need -undefined dynamic_lookup''' dir = find_config_dir(conf) snip = ''' #include <Python.h> #include <crt_externs.h> #define environ (*_NSGetEnviron()) static PyObject *ldb_module = NULL; int foo(int v) { extern char **environ; environ[0] = 1; ldb_module = PyImport_ImportModule("ldb"); return v * 2; }''' return conf.check(features='c cshlib',uselib='PYEMBED',fragment=snip,msg=msg, mandatory=False)
def CHECK_SHLIB_W_PYTHON(conf, msg): '''check if we need -undefined dynamic_lookup''' dir = find_config_dir(conf) snip = ''' #include <Python.h> #include <crt_externs.h> #define environ (*_NSGetEnviron()) static PyObject *ldb_module = NULL; int foo(int v) { extern char **environ; environ[0] = 1; ldb_module = PyImport_ImportModule("ldb"); return v * 2; }''' return conf.check(features='c cshlib',uselib='PYEMBED',fragment=snip,msg=msg, mandatory=False)
def CHECK_HEADER(conf, h, add_headers=False, lib=None): """check for a header""" if h in missing_headers and lib is None: return False d = h.upper().replace("/", "_") d = d.replace(".", "_") d = d.replace("-", "_") d = "HAVE_%s" % d if CONFIG_SET(conf, d): if add_headers: if not h in conf.env.hlist: conf.env.hlist.append(h) return True (ccflags, ldflags, cpppath) = library_flags(conf, lib) hdrs = hlist_to_string(conf, headers=h) if lib is None: lib = "" ret = conf.check( fragment="%s\nint main(void) { return 0; }" % hdrs, type="nolink", execute=0, ccflags=ccflags, mandatory=False, includes=cpppath, uselib=lib.upper(), msg="Checking for header %s" % h, ) if not ret: missing_headers.add(h) return False conf.DEFINE(d, 1) if add_headers and not h in conf.env.hlist: conf.env.hlist.append(h) return ret
def SAMBA_CONFIG_H(conf, path=None): '''write out config.h in the right directory''' # we don't want to produce a config.h in places like lib/replace # when we are building projects that depend on lib/replace if not IN_LAUNCH_DIR(conf): return # we need to build real code that can't be optimized away to test if conf.check(fragment=''' #include <stdio.h> int main(void) { char t[100000]; while (fgets(t, sizeof(t), stdin)); return 0; } ''', execute=0, ccflags='-fstack-protector', ldflags='-fstack-protector', msg='Checking if toolchain accepts -fstack-protector'): conf.ADD_CFLAGS('-fstack-protector') conf.ADD_LDFLAGS('-fstack-protector') if Options.options.debug: conf.ADD_CFLAGS('-g', testflags=True) if Options.options.developer: conf.env.DEVELOPER_MODE = True conf.ADD_CFLAGS('-g', testflags=True) conf.ADD_CFLAGS('-Wall', testflags=True) conf.ADD_CFLAGS('-Wshadow', testflags=True) conf.ADD_CFLAGS('-Wmissing-prototypes', testflags=True) conf.ADD_CFLAGS('-Wcast-align -Wcast-qual', testflags=True) conf.ADD_CFLAGS('-fno-common', testflags=True) conf.ADD_CFLAGS('-Werror=address', testflags=True) # we add these here to ensure that -Wstrict-prototypes is not set during configure conf.ADD_CFLAGS('-Werror=strict-prototypes -Wstrict-prototypes', testflags=True) conf.ADD_CFLAGS('-Werror=write-strings -Wwrite-strings', testflags=True) conf.ADD_CFLAGS('-Werror-implicit-function-declaration', testflags=True) conf.ADD_CFLAGS('-Werror=pointer-arith -Wpointer-arith', testflags=True) conf.ADD_CFLAGS('-Werror=declaration-after-statement -Wdeclaration-after-statement', testflags=True) conf.ADD_CFLAGS('-Werror=return-type -Wreturn-type', testflags=True) conf.ADD_CFLAGS('-Werror=uninitialized -Wuninitialized', testflags=True) conf.ADD_CFLAGS('-Wformat=2 -Wno-format-y2k', testflags=True) # This check is because for ldb_search(), a NULL format string # is not an error, but some compilers complain about that. if CHECK_CFLAGS(conf, ["-Werror=format", "-Wformat=2"], ''' int testformat(char *format, ...) __attribute__ ((format (__printf__, 1, 2))); int main(void) { testformat(0); return 0; } '''): if not 'EXTRA_CFLAGS' in conf.env: conf.env['EXTRA_CFLAGS'] = [] conf.env['EXTRA_CFLAGS'].extend(TO_LIST("-Werror=format")) if Options.options.picky_developer: conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Werror -Wno-error=deprecated-declarations', testflags=True) if Options.options.fatal_errors: conf.ADD_CFLAGS('-Wfatal-errors', testflags=True) if Options.options.pedantic: conf.ADD_CFLAGS('-W', testflags=True) if Options.options.address_sanitizer: conf.ADD_CFLAGS('-fno-omit-frame-pointer -O1 -fsanitize=address', testflags=True) conf.ADD_LDFLAGS('-fsanitize=address', testflags=True) conf.env['ADDRESS_SANITIZER'] = True # Let people pass an additional ADDITIONAL_{CFLAGS,LDFLAGS} # environment variables which are only used the for final build. # # The CFLAGS and LDFLAGS environment variables are also # used for the configure checks which might impact their results. conf.add_os_flags('ADDITIONAL_CFLAGS') if conf.env.ADDITIONAL_CFLAGS and conf.CHECK_CFLAGS(conf.env['ADDITIONAL_CFLAGS']): conf.env['EXTRA_CFLAGS'].extend(conf.env['ADDITIONAL_CFLAGS']) conf.add_os_flags('ADDITIONAL_LDFLAGS') if conf.env.ADDITIONAL_LDFLAGS and conf.CHECK_LDFLAGS(conf.env['ADDITIONAL_LDFLAGS']): conf.env['EXTRA_LDFLAGS'].extend(conf.env['ADDITIONAL_LDFLAGS']) if path is None: conf.write_config_header('config.h', top=True) else: conf.write_config_header(path) conf.SAMBA_CROSS_CHECK_COMPLETE()
def CHECK_CODE(conf, code, define, always=False, execute=False, addmain=True, add_headers=True, mandatory=False, headers=None, msg=None, cflags='', includes='# .', local_include=True, lib=None, link=True, define_ret=False, quote=False, on_target=True): '''check if some code compiles and/or runs''' if CONFIG_SET(conf, define): return True if headers is not None: CHECK_HEADERS(conf, headers=headers, lib=lib) if add_headers: hdrs = header_list(conf, headers=headers, lib=lib) else: hdrs = '' if execute: execute = 1 else: execute = 0 defs = conf.get_config_header() if addmain: fragment='%s\n%s\n int main(void) { %s; return 0; }\n' % (defs, hdrs, code) else: fragment='%s\n%s\n%s\n' % (defs, hdrs, code) if msg is None: msg="Checking for %s" % define cflags = TO_LIST(cflags) if local_include: cflags.append('-I%s' % conf.curdir) if not link: type='nolink' else: type='cprogram' uselib = TO_LIST(lib) (ccflags, ldflags) = library_flags(conf, uselib) uselib = [l.upper() for l in uselib] cflags.extend(ccflags) if on_target: exec_args = conf.SAMBA_CROSS_ARGS(msg=msg) else: exec_args = [] conf.COMPOUND_START(msg) ret = conf.check(fragment=fragment, execute=execute, define_name = define, mandatory = mandatory, ccflags=cflags, ldflags=ldflags, includes=includes, uselib=uselib, type=type, msg=msg, quote=quote, exec_args=exec_args, define_ret=define_ret) if not ret and CONFIG_SET(conf, define): # sometimes conf.check() returns false, but it # sets the define. Maybe a waf bug? ret = True if ret: if not define_ret: conf.DEFINE(define, 1) conf.COMPOUND_END(True) else: conf.COMPOUND_END(conf.env[define]) return True if always: conf.DEFINE(define, 0) conf.COMPOUND_END(False) return False
def check_python_headers(conf,mandatory=True): if not conf.env['CC_NAME']and not conf.env['CXX_NAME']: conf.fatal('load a compiler first (gcc, g++, ..)') if not conf.env['PYTHON_VERSION']: conf.check_python_version() env=conf.env python=env['PYTHON'] if not python: conf.fatal('could not find the python executable') if Options.platform=='darwin': conf.check_tool('osx') try: v='prefix SO SYSLIBS LDFLAGS SHLIBS LIBDIR LIBPL INCLUDEPY Py_ENABLE_SHARED MACOSX_DEPLOYMENT_TARGET'.split() (python_prefix,python_SO,python_SYSLIBS,python_LDFLAGS,python_SHLIBS,python_LIBDIR,python_LIBPL,INCLUDEPY,Py_ENABLE_SHARED,python_MACOSX_DEPLOYMENT_TARGET)=_get_python_variables(python,["get_config_var('%s')"%x for x in v],['from distutils.sysconfig import get_config_var']) except RuntimeError: conf.fatal("Python development headers not found (-v for details).") conf.log.write("""Configuration returned from %r: python_prefix = %r python_SO = %r python_SYSLIBS = %r python_LDFLAGS = %r python_SHLIBS = %r python_LIBDIR = %r python_LIBPL = %r INCLUDEPY = %r Py_ENABLE_SHARED = %r MACOSX_DEPLOYMENT_TARGET = %r """%(python,python_prefix,python_SO,python_SYSLIBS,python_LDFLAGS,python_SHLIBS,python_LIBDIR,python_LIBPL,INCLUDEPY,Py_ENABLE_SHARED,python_MACOSX_DEPLOYMENT_TARGET)) if python_MACOSX_DEPLOYMENT_TARGET: conf.env['MACOSX_DEPLOYMENT_TARGET']=python_MACOSX_DEPLOYMENT_TARGET conf.environ['MACOSX_DEPLOYMENT_TARGET']=python_MACOSX_DEPLOYMENT_TARGET env['pyext_PATTERN']='%s'+python_SO if python_SYSLIBS is not None: for lib in python_SYSLIBS.split(): if lib.startswith('-l'): lib=lib[2:] env.append_value('LIB_PYEMBED',lib) if python_SHLIBS is not None: for lib in python_SHLIBS.split(): if lib.startswith('-l'): env.append_value('LIB_PYEMBED',lib[2:]) else: env.append_value('LINKFLAGS_PYEMBED',lib) if Options.platform!='darwin'and python_LDFLAGS: env.append_value('LINKFLAGS_PYEMBED',python_LDFLAGS.split()) result=False name='python'+env['PYTHON_VERSION'] if python_LIBDIR is not None: path=[python_LIBDIR] conf.log.write("\n\n# Trying LIBDIR: %r\n"%path) result=conf.check(lib=name,uselib='PYEMBED',libpath=path) if not result and python_LIBPL is not None: conf.log.write("\n\n# try again with -L$python_LIBPL (some systems don't install the python library in $prefix/lib)\n") path=[python_LIBPL] result=conf.check(lib=name,uselib='PYEMBED',libpath=path) if not result: conf.log.write("\n\n# try again with -L$prefix/libs, and pythonXY name rather than pythonX.Y (win32)\n") path=[os.path.join(python_prefix,"libs")] name='python'+env['PYTHON_VERSION'].replace('.','') result=conf.check(lib=name,uselib='PYEMBED',libpath=path) if result: env['LIBPATH_PYEMBED']=path env.append_value('LIB_PYEMBED',name) else: conf.log.write("\n\n### LIB NOT FOUND\n") if(sys.platform=='win32'or sys.platform.startswith('os2')or sys.platform=='darwin'or Py_ENABLE_SHARED): env['LIBPATH_PYEXT']=env['LIBPATH_PYEMBED'] env['LIB_PYEXT']=env['LIB_PYEMBED'] python_config=conf.find_program('python%s-config'%('.'.join(env['PYTHON_VERSION'].split('.')[:2])),var='PYTHON_CONFIG') if not python_config: python_config=conf.find_program('python-config-%s'%('.'.join(env['PYTHON_VERSION'].split('.')[:2])),var='PYTHON_CONFIG') includes=[] if python_config: for incstr in Utils.cmd_output("%s %s --includes"%(python,python_config)).strip().split(): if(incstr.startswith('-I')or incstr.startswith('/I')): incstr=incstr[2:] if incstr not in includes: includes.append(incstr) conf.log.write("Include path for Python extensions ""(found via python-config --includes): %r\n"%(includes,)) env['CPPPATH_PYEXT']=includes env['CPPPATH_PYEMBED']=includes else: conf.log.write("Include path for Python extensions ""(found via distutils module): %r\n"%(INCLUDEPY,)) env['CPPPATH_PYEXT']=[INCLUDEPY] env['CPPPATH_PYEMBED']=[INCLUDEPY] if env['CC_NAME']=='gcc': env.append_value('CCFLAGS_PYEMBED','-fno-strict-aliasing') env.append_value('CCFLAGS_PYEXT','-fno-strict-aliasing') if env['CXX_NAME']=='gcc': env.append_value('CXXFLAGS_PYEMBED','-fno-strict-aliasing') env.append_value('CXXFLAGS_PYEXT','-fno-strict-aliasing') conf.check(define_name='HAVE_PYTHON_H',uselib='PYEMBED',fragment=FRAG_2,errmsg='Could not find the python development headers',mandatory=mandatory)
def CHECK_CFLAGS(conf, cflags, fragment="int main(void) { return 0; }\n"): """check if the given cflags are accepted by the compiler """ return conf.check( fragment=fragment, execute=0, type="nolink", ccflags=cflags, msg="Checking compiler accepts %s" % cflags )
def SAMBA_CONFIG_H(conf, path=None): '''write out config.h in the right directory''' # we don't want to produce a config.h in places like lib/replace # when we are building projects that depend on lib/replace if not IN_LAUNCH_DIR(conf): return # we need to build real code that can't be optimized away to test if conf.check(fragment=''' #include <stdio.h> int main(void) { char t[100000]; while (fgets(t, sizeof(t), stdin)); return 0; } ''', execute=0, ccflags='-fstack-protector', ldflags='-fstack-protector', mandatory=False, msg='Checking if toolchain accepts -fstack-protector'): conf.ADD_CFLAGS('-fstack-protector') conf.ADD_LDFLAGS('-fstack-protector') if Options.options.debug: conf.ADD_CFLAGS('-g', testflags=True) if Options.options.developer: conf.env.DEVELOPER_MODE = True conf.ADD_CFLAGS('-g', testflags=True) conf.ADD_CFLAGS('-Wall', testflags=True) conf.ADD_CFLAGS('-Wshadow', testflags=True) conf.ADD_CFLAGS('-Wmissing-prototypes', testflags=True) conf.ADD_CFLAGS('-Wcast-align -Wcast-qual', testflags=True) conf.ADD_CFLAGS('-fno-common', testflags=True) conf.ADD_CFLAGS('-Werror=address', testflags=True) # we add these here to ensure that -Wstrict-prototypes is not set during configure conf.ADD_CFLAGS('-Werror=strict-prototypes -Wstrict-prototypes', testflags=True) conf.ADD_CFLAGS('-Werror=write-strings -Wwrite-strings', testflags=True) conf.ADD_CFLAGS('-Werror-implicit-function-declaration', testflags=True) conf.ADD_CFLAGS('-Werror=pointer-arith -Wpointer-arith', testflags=True) conf.ADD_CFLAGS( '-Werror=declaration-after-statement -Wdeclaration-after-statement', testflags=True) conf.ADD_CFLAGS('-Werror=return-type -Wreturn-type', testflags=True) conf.ADD_CFLAGS('-Werror=uninitialized -Wuninitialized', testflags=True) conf.ADD_CFLAGS('-Wformat=2 -Wno-format-y2k', testflags=True) conf.ADD_CFLAGS('-Werror=format-security -Wformat-security', testflags=True) # This check is because for ldb_search(), a NULL format string # is not an error, but some compilers complain about that. if CHECK_CFLAGS( conf, ["-Werror=format", "-Wformat=2"], ''' int testformat(char *format, ...) __attribute__ ((format (__printf__, 1, 2))); int main(void) { testformat(0); return 0; } '''): if not 'EXTRA_CFLAGS' in conf.env: conf.env['EXTRA_CFLAGS'] = [] conf.env['EXTRA_CFLAGS'].extend(TO_LIST("-Werror=format")) if Options.options.picky_developer: conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Werror -Wno-error=deprecated-declarations', testflags=True) conf.ADD_NAMED_CFLAGS('PICKY_CFLAGS', '-Wno-error=tautological-compare', testflags=True) if Options.options.fatal_errors: conf.ADD_CFLAGS('-Wfatal-errors', testflags=True) if Options.options.pedantic: conf.ADD_CFLAGS('-W', testflags=True) if Options.options.address_sanitizer: conf.ADD_CFLAGS('-fno-omit-frame-pointer -O1 -fsanitize=address', testflags=True) conf.ADD_LDFLAGS('-fsanitize=address', testflags=True) conf.env['ADDRESS_SANITIZER'] = True # Let people pass an additional ADDITIONAL_{CFLAGS,LDFLAGS} # environment variables which are only used the for final build. # # The CFLAGS and LDFLAGS environment variables are also # used for the configure checks which might impact their results. conf.add_os_flags('ADDITIONAL_CFLAGS') if conf.env.ADDITIONAL_CFLAGS and conf.CHECK_CFLAGS( conf.env['ADDITIONAL_CFLAGS']): conf.env['EXTRA_CFLAGS'].extend(conf.env['ADDITIONAL_CFLAGS']) conf.add_os_flags('ADDITIONAL_LDFLAGS') if conf.env.ADDITIONAL_LDFLAGS and conf.CHECK_LDFLAGS( conf.env['ADDITIONAL_LDFLAGS']): conf.env['EXTRA_LDFLAGS'].extend(conf.env['ADDITIONAL_LDFLAGS']) if path is None: conf.write_config_header('config.h', top=True) else: conf.write_config_header(path) conf.SAMBA_CROSS_CHECK_COMPLETE()
def check_python_headers(conf): if not conf.env['CC_NAME'] and not conf.env['CXX_NAME']: conf.fatal('load a compiler first (gcc, g++, ..)') if not conf.env['PYTHON_VERSION']: conf.check_python_version() env = conf.env python = env['PYTHON'] assert python, ("python is %r !" % (python, )) if Options.platform == 'darwin': conf.check_tool('osx') try: v = 'prefix SO SYSLIBS LDFLAGS SHLIBS LIBDIR LIBPL INCLUDEPY Py_ENABLE_SHARED MACOSX_DEPLOYMENT_TARGET'.split( ) (python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET) = _get_python_variables( python, ["get_config_var('%s')" % x for x in v], ['from distutils.sysconfig import get_config_var']) except RuntimeError: conf.fatal("Python development headers not found (-v for details).") conf.log.write("""Configuration returned from %r: python_prefix = %r python_SO = %r python_SYSLIBS = %r python_LDFLAGS = %r python_SHLIBS = %r python_LIBDIR = %r python_LIBPL = %r INCLUDEPY = %r Py_ENABLE_SHARED = %r MACOSX_DEPLOYMENT_TARGET = %r """ % (python, python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET)) if python_MACOSX_DEPLOYMENT_TARGET: conf.env['MACOSX_DEPLOYMENT_TARGET'] = python_MACOSX_DEPLOYMENT_TARGET conf.environ[ 'MACOSX_DEPLOYMENT_TARGET'] = python_MACOSX_DEPLOYMENT_TARGET env['pyext_PATTERN'] = '%s' + python_SO if python_SYSLIBS is not None: for lib in python_SYSLIBS.split(): if lib.startswith('-l'): lib = lib[2:] env.append_value('LIB_PYEMBED', lib) if python_SHLIBS is not None: for lib in python_SHLIBS.split(): if lib.startswith('-l'): lib = lib[2:] env.append_value('LIB_PYEMBED', lib) if Options.platform != 'darwin' and python_LDFLAGS: env.append_value('LINKFLAGS_PYEMBED', python_LDFLAGS.split()) result = False name = 'python' + env['PYTHON_VERSION'] if python_LIBDIR is not None: path = [python_LIBDIR] conf.log.write("\n\n# Trying LIBDIR: %r\n" % path) result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if not result and python_LIBPL is not None: conf.log.write( "\n\n# try again with -L$python_LIBPL (some systems don't install the python library in $prefix/lib)\n" ) path = [python_LIBPL] result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if not result: conf.log.write( "\n\n# try again with -L$prefix/libs, and pythonXY name rather than pythonX.Y (win32)\n" ) path = [os.path.join(python_prefix, "libs")] name = 'python' + env['PYTHON_VERSION'].replace('.', '') result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if result: env['LIBPATH_PYEMBED'] = path env.append_value('LIB_PYEMBED', name) else: conf.log.write("\n\n### LIB NOT FOUND\n") if (sys.platform == 'win32' or sys.platform.startswith('os2') or sys.platform == 'darwin' or Py_ENABLE_SHARED): env['LIBPATH_PYEXT'] = env['LIBPATH_PYEMBED'] env['LIB_PYEXT'] = env['LIB_PYEMBED'] python_config = conf.find_program( 'python%s-config' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') if not python_config: python_config = conf.find_program( 'python-config-%s' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') includes = [] if python_config: for incstr in Utils.cmd_output("%s --includes" % (python_config)).strip().split(): if (incstr.startswith('-I') or incstr.startswith('/I')): incstr = incstr[2:] if incstr not in includes: includes.append(incstr) conf.log.write("Include path for Python extensions " "(found via python-config --includes): %r\n" % (includes, )) env['CPPPATH_PYEXT'] = includes env['CPPPATH_PYEMBED'] = includes else: conf.log.write("Include path for Python extensions " "(found via distutils module): %r\n" % (INCLUDEPY, )) env['CPPPATH_PYEXT'] = [INCLUDEPY] env['CPPPATH_PYEMBED'] = [INCLUDEPY] if env['CC_NAME'] == 'gcc': env.append_value('CCFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CCFLAGS_PYEXT', '-fno-strict-aliasing') if env['CXX_NAME'] == 'gcc': env.append_value('CXXFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CXXFLAGS_PYEXT', '-fno-strict-aliasing') test_env = env.copy() a = test_env.append_value a('CPPPATH', env['CPPPATH_PYEMBED']) a('LIBPATH', env['LIBPATH_PYEMBED']) a('LIB', env['LIB_PYEMBED']) a('LINKFLAGS', env['LINKFLAGS_PYEMBED']) a('CXXFLAGS', env['CXXFLAGS_PYEMBED']) a('CCFLAGS', env['CCFLAGS_PYEMBED']) conf.check(header_name='Python.h', define_name='HAVE_PYTHON_H', env=test_env, fragment=FRAG_2, errmsg='Could not find the python development headers', mandatory=1)
def check_python_headers(conf, mandatory=True): """Check for headers and libraries necessary to extend or embed python. On success the environment variables xxx_PYEXT and xxx_PYEMBED are added for uselib PYEXT: for compiling python extensions PYEMBED: for embedding a python interpreter""" if not conf.env['CC_NAME'] and not conf.env['CXX_NAME']: conf.fatal('load a compiler first (gcc, g++, ..)') if not conf.env['PYTHON_VERSION']: conf.check_python_version() env = conf.env python = env['PYTHON'] if not python: conf.fatal('could not find the python executable') ## On Mac OSX we need to use mac bundles for python plugins if Options.platform == 'darwin': conf.check_tool('osx') try: # Get some python configuration variables using distutils v = 'prefix SO SYSLIBS LDFLAGS SHLIBS LIBDIR LIBPL INCLUDEPY Py_ENABLE_SHARED MACOSX_DEPLOYMENT_TARGET'.split( ) (python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET) = \ _get_python_variables(python, ["get_config_var('%s') or ''" % x for x in v], ['from distutils.sysconfig import get_config_var']) except RuntimeError: conf.fatal("Python development headers not found (-v for details).") conf.log.write("""Configuration returned from %r: python_prefix = %r python_SO = %r python_SYSLIBS = %r python_LDFLAGS = %r python_SHLIBS = %r python_LIBDIR = %r python_LIBPL = %r INCLUDEPY = %r Py_ENABLE_SHARED = %r MACOSX_DEPLOYMENT_TARGET = %r """ % (python, python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET)) # Allow some python overrides from env vars for cross-compiling os_env = dict(os.environ) override_python_LDFLAGS = os_env.get('python_LDFLAGS', None) if override_python_LDFLAGS is not None: conf.log.write("python_LDFLAGS override from environment = %r\n" % (override_python_LDFLAGS)) python_LDFLAGS = override_python_LDFLAGS override_python_LIBDIR = os_env.get('python_LIBDIR', None) if override_python_LIBDIR is not None: conf.log.write("python_LIBDIR override from environment = %r\n" % (override_python_LIBDIR)) python_LIBDIR = override_python_LIBDIR if python_MACOSX_DEPLOYMENT_TARGET: conf.env['MACOSX_DEPLOYMENT_TARGET'] = python_MACOSX_DEPLOYMENT_TARGET conf.environ[ 'MACOSX_DEPLOYMENT_TARGET'] = python_MACOSX_DEPLOYMENT_TARGET env['pyext_PATTERN'] = '%s' + python_SO # Check for python libraries for embedding if python_SYSLIBS is not None: for lib in python_SYSLIBS.split(): if lib.startswith('-l'): lib = lib[2:] # strip '-l' env.append_value('LIB_PYEMBED', lib) if python_SHLIBS is not None: for lib in python_SHLIBS.split(): if lib.startswith('-l'): env.append_value('LIB_PYEMBED', lib[2:]) # strip '-l' else: env.append_value('LINKFLAGS_PYEMBED', lib) if Options.platform != 'darwin' and python_LDFLAGS: parse_flags(python_LDFLAGS, 'PYEMBED', env) result = False name = 'python' + env['PYTHON_VERSION'] if python_LIBDIR is not None: path = [python_LIBDIR] conf.log.write("\n\n# Trying LIBDIR: %r\n" % path) result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if not result and python_LIBPL is not None: conf.log.write( "\n\n# try again with -L$python_LIBPL (some systems don't install the python library in $prefix/lib)\n" ) path = [python_LIBPL] result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if not result: conf.log.write( "\n\n# try again with -L$prefix/libs, and pythonXY name rather than pythonX.Y (win32)\n" ) path = [os.path.join(python_prefix, "libs")] name = 'python' + env['PYTHON_VERSION'].replace('.', '') result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if result: env['LIBPATH_PYEMBED'] = path env.append_value('LIB_PYEMBED', name) else: conf.log.write("\n\n### LIB NOT FOUND\n") # under certain conditions, python extensions must link to # python libraries, not just python embedding programs. if (sys.platform == 'win32' or sys.platform.startswith('os2') or sys.platform == 'darwin' or Py_ENABLE_SHARED): env['LIBPATH_PYEXT'] = env['LIBPATH_PYEMBED'] env['LIB_PYEXT'] = env['LIB_PYEMBED'] # We check that pythonX.Y-config exists, and if it exists we # use it to get only the includes, else fall back to distutils. python_config = conf.find_program( 'python%s-config' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') if not python_config: python_config = conf.find_program( 'python-config-%s' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') includes = [] if python_config: for incstr in Utils.cmd_output("%s --includes" % (python_config, )).strip().split(): # strip the -I or /I if (incstr.startswith('-I') or incstr.startswith('/I')): incstr = incstr[2:] # append include path, unless already given if incstr not in includes: includes.append(incstr) conf.log.write("Include path for Python extensions " "(found via python-config --includes): %r\n" % (includes, )) env['CPPPATH_PYEXT'] = includes env['CPPPATH_PYEMBED'] = includes else: conf.log.write("Include path for Python extensions " "(found via distutils module): %r\n" % (INCLUDEPY, )) env['CPPPATH_PYEXT'] = [INCLUDEPY] env['CPPPATH_PYEMBED'] = [INCLUDEPY] # Code using the Python API needs to be compiled with -fno-strict-aliasing if env['CC_NAME'] == 'gcc': env.append_value('CCFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CCFLAGS_PYEXT', '-fno-strict-aliasing') if env['CXX_NAME'] == 'gcc': env.append_value('CXXFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CXXFLAGS_PYEXT', '-fno-strict-aliasing') # See if it compiles conf.check(define_name='HAVE_PYTHON_H', uselib='PYEMBED', fragment=FRAG_2, errmsg='Could not find the python development headers', mandatory=mandatory)
def check_python_headers(conf, mandatory=True): """Check for headers and libraries necessary to extend or embed python. On success the environment variables xxx_PYEXT and xxx_PYEMBED are added for uselib PYEXT: for compiling python extensions PYEMBED: for embedding a python interpreter""" if not conf.env['CC_NAME'] and not conf.env['CXX_NAME']: conf.fatal('load a compiler first (gcc, g++, ..)') if not conf.env['PYTHON_VERSION']: conf.check_python_version() env = conf.env python = env['PYTHON'] if not python: conf.fatal('could not find the python executable') ## On Mac OSX we need to use mac bundles for python plugins if Options.platform == 'darwin': conf.check_tool('osx') try: # Get some python configuration variables using distutils v = 'prefix SO SYSLIBS LDFLAGS SHLIBS LIBDIR LIBPL INCLUDEPY Py_ENABLE_SHARED MACOSX_DEPLOYMENT_TARGET LDVERSION'.split() (python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET, python_LDVERSION) = \ _get_python_variables(python, ["get_config_var('%s') or ''" % x for x in v], ['from distutils.sysconfig import get_config_var']) except RuntimeError: conf.fatal("Python development headers not found (-v for details).") conf.log.write("""Configuration returned from %r: python_prefix = %r python_SO = %r python_SYSLIBS = %r python_LDFLAGS = %r python_SHLIBS = %r python_LIBDIR = %r python_LIBPL = %r INCLUDEPY = %r Py_ENABLE_SHARED = %r MACOSX_DEPLOYMENT_TARGET = %r LDVERSION = %r """ % (python, python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET, python_LDVERSION)) # Allow some python overrides from env vars for cross-compiling os_env = dict(os.environ) override_python_LDFLAGS = os_env.get('python_LDFLAGS', None) if override_python_LDFLAGS is not None: conf.log.write("python_LDFLAGS override from environment = %r\n" % (override_python_LDFLAGS)) python_LDFLAGS = override_python_LDFLAGS override_python_LIBDIR = os_env.get('python_LIBDIR', None) if override_python_LIBDIR is not None: conf.log.write("python_LIBDIR override from environment = %r\n" % (override_python_LIBDIR)) python_LIBDIR = override_python_LIBDIR if python_MACOSX_DEPLOYMENT_TARGET: conf.env['MACOSX_DEPLOYMENT_TARGET'] = python_MACOSX_DEPLOYMENT_TARGET conf.environ['MACOSX_DEPLOYMENT_TARGET'] = python_MACOSX_DEPLOYMENT_TARGET env['pyext_PATTERN'] = '%s'+python_SO # Check for python libraries for embedding if python_SYSLIBS is not None: for lib in python_SYSLIBS.split(): if lib.startswith('-l'): lib = lib[2:] # strip '-l' env.append_value('LIB_PYEMBED', lib) if python_SHLIBS is not None: for lib in python_SHLIBS.split(): if lib.startswith('-l'): env.append_value('LIB_PYEMBED', lib[2:]) # strip '-l' else: env.append_value('LINKFLAGS_PYEMBED', lib) if Options.platform != 'darwin' and python_LDFLAGS: parse_flags(python_LDFLAGS, 'PYEMBED', env) result = False if not python_LDVERSION: python_LDVERSION = env['PYTHON_VERSION'] name = 'python' + python_LDVERSION if python_LIBDIR is not None: path = [python_LIBDIR] conf.log.write("\n\n# Trying LIBDIR: %r\n" % path) result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if not result and python_LIBPL is not None: conf.log.write("\n\n# try again with -L$python_LIBPL (some systems don't install the python library in $prefix/lib)\n") path = [python_LIBPL] result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if not result: conf.log.write("\n\n# try again with -L$prefix/libs, and pythonXY name rather than pythonX.Y (win32)\n") path = [os.path.join(python_prefix, "libs")] name = 'python' + python_LDVERSION.replace('.', '') result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if result: env['LIBPATH_PYEMBED'] = path env.append_value('LIB_PYEMBED', name) else: conf.log.write("\n\n### LIB NOT FOUND\n") # under certain conditions, python extensions must link to # python libraries, not just python embedding programs. if (sys.platform == 'win32' or sys.platform.startswith('os2') or sys.platform == 'darwin' or Py_ENABLE_SHARED): env['LIBPATH_PYEXT'] = env['LIBPATH_PYEMBED'] env['LIB_PYEXT'] = env['LIB_PYEMBED'] # We check that pythonX.Y-config exists, and if it exists we # use it to get only the includes, else fall back to distutils. python_config = conf.find_program( 'python%s-config' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') if not python_config: python_config = conf.find_program( 'python-config-%s' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') includes = [] if python_config: for incstr in Utils.cmd_output("%s --includes" % (python_config,)).strip().split(): # strip the -I or /I if (incstr.startswith('-I') or incstr.startswith('/I')): incstr = incstr[2:] # append include path, unless already given if incstr not in includes: includes.append(incstr) conf.log.write("Include path for Python extensions " "(found via python-config --includes): %r\n" % (includes,)) env['CPPPATH_PYEXT'] = includes env['CPPPATH_PYEMBED'] = includes else: conf.log.write("Include path for Python extensions " "(found via distutils module): %r\n" % (INCLUDEPY,)) env['CPPPATH_PYEXT'] = [INCLUDEPY] env['CPPPATH_PYEMBED'] = [INCLUDEPY] # Code using the Python API needs to be compiled with -fno-strict-aliasing if env['CC_NAME'] == 'gcc': env.append_value('CCFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CCFLAGS_PYEXT', '-fno-strict-aliasing') if env['CXX_NAME'] == 'gcc': env.append_value('CXXFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CXXFLAGS_PYEXT', '-fno-strict-aliasing') # See if it compiles conf.check(define_name='HAVE_PYTHON_H', uselib='PYEMBED', fragment=FRAG_2, errmsg='Could not find the python development headers', mandatory=mandatory)
def check_python_headers(conf): """Check for headers and libraries necessary to extend or embed python. If successful, xxx_PYEXT and xxx_PYEMBED variables are defined in the environment (for uselib). PYEXT should be used for compiling python extensions, while PYEMBED should be used by programs that need to embed a python interpreter. Note: this test requires that check_python_version was previously executed and successful.""" env = conf.env python = env['PYTHON'] assert python, ("python is %r !" % (python,)) ## On Mac OSX we need to use mac bundles for python plugins if Options.platform == 'darwin': conf.check_tool('osx') try: # Get some python configuration variables using distutils v = 'prefix SO SYSLIBS LDFLAGS SHLIBS LIBDIR LIBPL INCLUDEPY Py_ENABLE_SHARED'.split() (python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED) = \ _get_python_variables(python, ["get_config_var('%s')" % x for x in v], ['from distutils.sysconfig import get_config_var']) except ValueError: conf.fatal("Python development headers not found (-v for details).") conf.log.write("""Configuration returned from %r: python_prefix = %r python_SO = %r python_SYSLIBS = %r python_LDFLAGS = %r python_SHLIBS = %r python_LIBDIR = %r python_LIBPL = %r INCLUDEPY = %r Py_ENABLE_SHARED = %r """ % (python, python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED)) env['pyext_PATTERN'] = '%s'+python_SO # Check for python libraries for embedding if python_SYSLIBS is not None: for lib in python_SYSLIBS.split(): if lib.startswith('-l'): lib = lib[2:] # strip '-l' env.append_value('LIB_PYEMBED', lib) if python_SHLIBS is not None: for lib in python_SHLIBS.split(): if lib.startswith('-l'): lib = lib[2:] # strip '-l' env.append_value('LIB_PYEMBED', lib) env.append_value('LINKFLAGS_PYEMBED', python_LDFLAGS) code = ''' #ifdef __cplusplus extern "C" { #endif void Py_Initialize(void); void Py_Finalize(void); #ifdef __cplusplus } #endif int main(int argc, char *argv[]) { Py_Initialize(); Py_Finalize(); return 0; } ''' result = False name = 'python' + env['PYTHON_VERSION'] if python_LIBDIR is not None: path = [python_LIBDIR] result = conf.check(lib=name, uselib='PYEMBED', libpath=path) # try again with -L$python_LIBPL (some systems don't install the python library in $prefix/lib) if not result and python_LIBPL is not None: path = [python_LIBPL] result = conf.check(lib=name, uselib='PYEMBED', libpath=path) # try again with -L$prefix/libs, and pythonXY name rather than pythonX.Y (win32) if not result: path = [os.path.join(python_prefix, "libs")] name = 'python' + env['PYTHON_VERSION'].replace('.', '') result = conf.check(lib=name, uselib='PYEMBED', libpath=path) if result: env['LIBPATH_PYEMBED'] = path env.append_value('LIB_PYEMBED', name) # under certain conditions, python extensions must link to # python libraries, not just python embedding programs. if (sys.platform == 'win32' or sys.platform.startswith('os2') or sys.platform == 'darwin' or Py_ENABLE_SHARED): env['LIBPATH_PYEXT'] = env['LIBPATH_PYEMBED'] env['LIB_PYEXT'] = env['LIB_PYEMBED'] # We check that pythonX.Y-config exists, and if it exists we # use it to get only the includes, else fall back to distutils. python_config = conf.find_program( 'python%s-config' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') if not python_config: python_config = conf.find_program( 'python-config-%s' % ('.'.join(env['PYTHON_VERSION'].split('.')[:2])), var='PYTHON_CONFIG') includes = [] if python_config: for incstr in os.popen("%s %s --includes" % (python, python_config)).readline().strip().split(): # strip the -I or /I if (incstr.startswith('-I') or incstr.startswith('/I')): incstr = incstr[2:] # append include path, unless already given if incstr not in includes: includes.append(incstr) conf.log.write("Include path for Python extensions " "(found via python-config --includes): %r\n" % (includes,)) env['CPPPATH_PYEXT'] = includes env['CPPPATH_PYEMBED'] = includes else: conf.log.write("Include path for Python extensions " "(found via distutils module): %r\n" % (INCLUDEPY,)) env['CPPPATH_PYEXT'] = [INCLUDEPY] env['CPPPATH_PYEMBED'] = [INCLUDEPY] # Code using the Python API needs to be compiled with -fno-strict-aliasing if env['CC']: version = os.popen("%s --version" % env['CC']).readline() if '(GCC)' in version or 'gcc' in version: env.append_value('CCFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CCFLAGS_PYEXT', '-fno-strict-aliasing') if env['CXX']: version = os.popen("%s --version" % env['CXX']).readline() if '(GCC)' in version or 'g++' in version: env.append_value('CXXFLAGS_PYEMBED', '-fno-strict-aliasing') env.append_value('CXXFLAGS_PYEXT', '-fno-strict-aliasing') # See if it compiles test_env = env.copy() test_env.append_value('CPPPATH', env['CPPPATH_PYEMBED']) test_env.append_value('LIBPATH', env['LIBPATH_PYEMBED']) test_env.append_value('LIB', env['LIB_PYEMBED']) test_env.append_value('LINKFLAGS', env['LINKFLAGS_PYEMBED']) test_env.append_value('CXXFLAGS', env['CXXFLAGS_PYEMBED']) test_env.append_value('CCFLAGS', env['CCFLAGS_PYEMBED']) conf.check(header_name='Python.h', define_name='HAVE_PYTHON_H', env=test_env, fragment='''#include <Python.h>\nint main(int argc, char *argv[]) { Py_Initialize(); Py_Finalize(); return 0; }\n''', errmsg='Could not find the python development headers', mandatory=1)
def CHECK_CODE(conf, code, define, always=False, execute=False, addmain=True, add_headers=True, mandatory=False, headers=None, msg=None, cflags='', includes='# .', local_include=True, lib=None, link=True, define_ret=False, quote=False, on_target=True): '''check if some code compiles and/or runs''' if CONFIG_SET(conf, define): return True if headers is not None: CHECK_HEADERS(conf, headers=headers, lib=lib) if add_headers: hdrs = header_list(conf, headers=headers, lib=lib) else: hdrs = '' if execute: execute = 1 else: execute = 0 defs = conf.get_config_header() if addmain: fragment = '%s\n%s\n int main(void) { %s; return 0; }\n' % (defs, hdrs, code) else: fragment = '%s\n%s\n%s\n' % (defs, hdrs, code) if msg is None: msg = "Checking for %s" % define cflags = TO_LIST(cflags) if local_include: cflags.append('-I%s' % conf.curdir) if not link: type = 'nolink' else: type = 'cprogram' uselib = TO_LIST(lib) (ccflags, ldflags, cpppath) = library_flags(conf, uselib) includes = TO_LIST(includes) includes.extend(cpppath) uselib = [l.upper() for l in uselib] cflags.extend(ccflags) if on_target: exec_args = conf.SAMBA_CROSS_ARGS(msg=msg) else: exec_args = [] conf.COMPOUND_START(msg) ret = conf.check(fragment=fragment, execute=execute, define_name=define, mandatory=mandatory, ccflags=cflags, ldflags=ldflags, includes=includes, uselib=uselib, type=type, msg=msg, quote=quote, exec_args=exec_args, define_ret=define_ret) if not ret and CONFIG_SET(conf, define): # sometimes conf.check() returns false, but it # sets the define. Maybe a waf bug? ret = True if ret: if not define_ret: conf.DEFINE(define, 1) conf.COMPOUND_END(True) else: conf.COMPOUND_END(conf.env[define]) return True if always: conf.DEFINE(define, 0) conf.COMPOUND_END(False) return False
def check_python_headers(conf, mandatory=True): if not conf.env["CC_NAME"] and not conf.env["CXX_NAME"]: conf.fatal("load a compiler first (gcc, g++, ..)") if not conf.env["PYTHON_VERSION"]: conf.check_python_version() env = conf.env python = env["PYTHON"] if not python: conf.fatal("could not find the python executable") if Options.platform == "darwin": conf.check_tool("osx") try: v = "prefix SO SYSLIBS LDFLAGS SHLIBS LIBDIR LIBPL INCLUDEPY Py_ENABLE_SHARED MACOSX_DEPLOYMENT_TARGET".split() ( python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET, ) = _get_python_variables( python, ["get_config_var('%s')" % x for x in v], ["from distutils.sysconfig import get_config_var"] ) except RuntimeError: conf.fatal("Python development headers not found (-v for details).") conf.log.write( """Configuration returned from %r: python_prefix = %r python_SO = %r python_SYSLIBS = %r python_LDFLAGS = %r python_SHLIBS = %r python_LIBDIR = %r python_LIBPL = %r INCLUDEPY = %r Py_ENABLE_SHARED = %r MACOSX_DEPLOYMENT_TARGET = %r """ % ( python, python_prefix, python_SO, python_SYSLIBS, python_LDFLAGS, python_SHLIBS, python_LIBDIR, python_LIBPL, INCLUDEPY, Py_ENABLE_SHARED, python_MACOSX_DEPLOYMENT_TARGET, ) ) if python_MACOSX_DEPLOYMENT_TARGET: conf.env["MACOSX_DEPLOYMENT_TARGET"] = python_MACOSX_DEPLOYMENT_TARGET conf.environ["MACOSX_DEPLOYMENT_TARGET"] = python_MACOSX_DEPLOYMENT_TARGET env["pyext_PATTERN"] = "%s" + python_SO if python_SYSLIBS is not None: for lib in python_SYSLIBS.split(): if lib.startswith("-l"): lib = lib[2:] env.append_value("LIB_PYEMBED", lib) if python_SHLIBS is not None: for lib in python_SHLIBS.split(): if lib.startswith("-l"): env.append_value("LIB_PYEMBED", lib[2:]) else: env.append_value("LINKFLAGS_PYEMBED", lib) if Options.platform != "darwin" and python_LDFLAGS: env.append_value("LINKFLAGS_PYEMBED", python_LDFLAGS.split()) result = False name = "python" + env["PYTHON_VERSION"] if python_LIBDIR is not None: path = [python_LIBDIR] conf.log.write("\n\n# Trying LIBDIR: %r\n" % path) result = conf.check(lib=name, uselib="PYEMBED", libpath=path) if not result and python_LIBPL is not None: conf.log.write( "\n\n# try again with -L$python_LIBPL (some systems don't install the python library in $prefix/lib)\n" ) path = [python_LIBPL] result = conf.check(lib=name, uselib="PYEMBED", libpath=path) if not result: conf.log.write("\n\n# try again with -L$prefix/libs, and pythonXY name rather than pythonX.Y (win32)\n") path = [os.path.join(python_prefix, "libs")] name = "python" + env["PYTHON_VERSION"].replace(".", "") result = conf.check(lib=name, uselib="PYEMBED", libpath=path) if result: env["LIBPATH_PYEMBED"] = path env.append_value("LIB_PYEMBED", name) else: conf.log.write("\n\n### LIB NOT FOUND\n") if sys.platform == "win32" or sys.platform.startswith("os2") or sys.platform == "darwin" or Py_ENABLE_SHARED: env["LIBPATH_PYEXT"] = env["LIBPATH_PYEMBED"] env["LIB_PYEXT"] = env["LIB_PYEMBED"] python_config = conf.find_program( "python%s-config" % (".".join(env["PYTHON_VERSION"].split(".")[:2])), var="PYTHON_CONFIG" ) if not python_config: python_config = conf.find_program( "python-config-%s" % (".".join(env["PYTHON_VERSION"].split(".")[:2])), var="PYTHON_CONFIG" ) includes = [] if python_config: for incstr in Utils.cmd_output("%s %s --includes" % (python, python_config)).strip().split(): if incstr.startswith("-I") or incstr.startswith("/I"): incstr = incstr[2:] if incstr not in includes: includes.append(incstr) conf.log.write("Include path for Python extensions " "(found via python-config --includes): %r\n" % (includes,)) env["CPPPATH_PYEXT"] = includes env["CPPPATH_PYEMBED"] = includes else: conf.log.write("Include path for Python extensions " "(found via distutils module): %r\n" % (INCLUDEPY,)) env["CPPPATH_PYEXT"] = [INCLUDEPY] env["CPPPATH_PYEMBED"] = [INCLUDEPY] if env["CC_NAME"] == "gcc": env.append_value("CCFLAGS_PYEMBED", "-fno-strict-aliasing") env.append_value("CCFLAGS_PYEXT", "-fno-strict-aliasing") if env["CXX_NAME"] == "gcc": env.append_value("CXXFLAGS_PYEMBED", "-fno-strict-aliasing") env.append_value("CXXFLAGS_PYEXT", "-fno-strict-aliasing") conf.check( define_name="HAVE_PYTHON_H", uselib="PYEMBED", fragment=FRAG_2, errmsg="Could not find the python development headers", mandatory=mandatory, )