Fix Python bindings and openflow for waf 1.7.10 upgrade and take care about boost requirements globally

This commit is contained in:
Alexander Afanasyev
2013-04-01 22:34:50 +02:00
parent bbdb4231b3
commit 0e169c157f
4 changed files with 219 additions and 112 deletions

View File

@@ -6,25 +6,17 @@ import subprocess
import shutil
import sys
import Task
import Options
import Configure
import TaskGen
import Logs
import Build
import Utils
from waflib import Task, Options, Configure, TaskGen, Logs, Build, Utils, Errors
from waflib.Errors import WafError
feature = TaskGen.feature
after = TaskGen.after
## https://launchpad.net/pybindgen/
REQUIRED_PYBINDGEN_VERSION = (0, 15, 0, 809)
REQUIRED_PYGCCXML_VERSION = (0, 9, 5)
from TaskGen import feature, after
import Task
def add_to_python_path(path):
if os.environ.get('PYTHONPATH', ''):
@@ -38,7 +30,7 @@ def set_pybindgen_pythonpath(env):
def options(opt):
opt.tool_options('python')
opt.load('python')
opt.add_option('--disable-python',
help=("Don't build Python bindings."),
action="store_true", default=False,
@@ -76,7 +68,7 @@ def configure(conf):
available_modules.sort()
all_modules_enabled = (enabled_modules == available_modules)
conf.check_tool('misc', tooldir=['waf-tools'])
conf.load('misc', tooldir=['waf-tools'])
if sys.platform == 'cygwin':
conf.report_optional_feature("python", "Python Bindings", False,
@@ -91,20 +83,20 @@ def configure(conf):
conf.env.PYTHON = Options.options.with_python
try:
conf.check_tool('python')
except Configure.ConfigurationError, ex:
conf.load('python')
except Errors.ConfigurationError, ex:
conf.report_optional_feature("python", "Python Bindings", False,
"The python interpreter was not found")
return
try:
conf.check_python_version((2,3))
except Configure.ConfigurationError, ex:
except Errors.ConfigurationError, ex:
conf.report_optional_feature("python", "Python Bindings", False,
"The python found version is too low (2.3 required)")
return
try:
conf.check_python_headers()
except Configure.ConfigurationError, ex:
except Errors.ConfigurationError, ex:
conf.report_optional_feature("python", "Python Bindings", False,
"Python library or headers missing")
return
@@ -161,7 +153,7 @@ def configure(conf):
try:
conf.check_python_module('pybindgen')
except Configure.ConfigurationError:
except Errors.ConfigurationError:
Logs.warn("pybindgen missing => no python bindings")
conf.report_optional_feature("python", "Python Bindings", False,
"PyBindGen missing")
@@ -197,9 +189,9 @@ int main ()
try:
ret = conf.run_c_code(code=test_program,
env=conf.env.copy(), compile_filename='test.cc',
env=conf.env.derive(), compile_filename='test.cc',
features='cxx cprogram', execute=False)
except Configure.ConfigurationError:
except Errors.ConfigurationError:
ret = 1
conf.msg('Checking for types %s and %s equivalence' % (t1, t2), (ret and 'no' or 'yes'))
return not ret
@@ -250,7 +242,7 @@ int main ()
## Check for pygccxml
try:
conf.check_python_module('pygccxml')
except Configure.ConfigurationError:
except Errors.ConfigurationError:
conf.report_optional_feature("pygccxml", "Python API Scanning Support", False,
"Missing 'pygccxml' Python module")
return
@@ -322,7 +314,7 @@ class apiscan_task(Task.TaskBase):
"""Uses gccxml to scan the file 'everything.h' and extract API definitions.
"""
after = 'gen_ns3_module_header ns3header'
before = 'cc cxx command'
before = 'cxx command'
color = "BLUE"
def __init__(self, curdirnode, env, bld, target, cflags, module):
self.bld = bld
@@ -393,7 +385,7 @@ class python_scan_task_collector(Task.TaskBase):
"""Tasks that waits for the python-scan-* tasks to complete and then signals WAF to exit
"""
after = 'apiscan'
before = 'cc cxx'
before = 'cxx'
color = "BLUE"
def __init__(self, curdirnode, env, bld):
self.bld = bld
@@ -415,7 +407,7 @@ class python_scan_task_collector(Task.TaskBase):
class gen_ns3_compat_pymod_task(Task.Task):
"""Generates a 'ns3.py' compatibility module."""
before = 'cc cxx'
before = 'cxx'
color = 'BLUE'
def run(self):
@@ -437,8 +429,6 @@ def build(bld):
return
env = bld.env
curdir = bld.path.abspath()
set_pybindgen_pythonpath(env)
if Options.options.apiscan:
@@ -489,9 +479,7 @@ def build(bld):
grp = bld.get_group(bld.current_group)
grp.append(task)
bld.new_task_gen(features='copy',
source="ns__init__.py",
target='ns/__init__.py')
bld(features='copy', source="ns__init__.py", target='ns/__init__.py')
bld.install_as('${PYTHONARCHDIR}/ns/__init__.py', 'ns__init__.py')

View File

@@ -1,25 +1,21 @@
## -*- Mode: python; py-indent-offset: 4; indent-tabs-mode: nil; coding: utf-8; -*-
import os
import Options
from waflib import Logs, Options
from waflib.Errors import WafError
def options(opt):
opt.add_option('--with-openflow',
help=('Path to OFSID source for NS-3 OpenFlow Integration support'),
default='', dest='with_openflow')
opt.tool_options('boost', tooldir=["waf-tools"])
REQUIRED_BOOST_LIBS = ['system', 'signals', 'filesystem']
def required_boost_libs(conf):
conf.env['REQUIRED_BOOST_LIBS'] += REQUIRED_BOOST_LIBS
def configure(conf):
try:
conf.check_tool('boost')
conf.check_boost(lib='signals filesystem')
if not conf.env.LIB_BOOST:
conf.check_boost(lib='signals filesystem', libpath="/usr/lib64")
except WafError:
conf.env['LIB_BOOST'] = []
if not conf.env.LIB_BOOST:
if not conf.env['LIB_BOOST']:
conf.report_optional_feature("openflow", "NS-3 OpenFlow Integration", False,
"Required boost libraries not found")
@@ -29,6 +25,25 @@ def configure(conf):
return
present_boost_libs = []
for boost_lib_name in conf.env['LIB_BOOST']:
if boost_lib_name.startswith("boost_"):
boost_lib_name = boost_lib_name[6:]
if boost_lib_name.endswith("-mt"):
boost_lib_name = boost_lib_name[:-3]
present_boost_libs.append(boost_lib_name)
missing_boost_libs = [lib for lib in REQUIRED_BOOST_LIBS if lib not in present_boost_libs]
if missing_boost_libs != []:
conf.report_optional_feature("openflow", "NS-3 OpenFlow Integration", False,
"Required boost libraries not found, missing: %s" % ', '.join(missing_boost_libs))
# Add this module to the list of modules that won't be built
# if they are enabled.
conf.env['MODULES_NOT_BUILT'].append('openflow')
return
if Options.options.with_openflow:
if os.path.isdir(Options.options.with_openflow):
conf.msg("Checking for OpenFlow location", ("%s (given)" % Options.options.with_openflow))
@@ -142,7 +157,7 @@ def build(bld):
obj.use.extend('OPENFLOW DL XML2'.split())
obj_test.use.extend('OPENFLOW DL XML2'.split())
headers = bld.new_task_gen(features=['ns3header'])
headers = bld(features='ns3header')
headers.module = 'openflow'
headers.source = [
]
@@ -160,4 +175,4 @@ def build(bld):
headers.source.append('helper/openflow-switch-helper.h')
if bld.env['ENABLE_EXAMPLES'] and bld.env['ENABLE_OPENFLOW']:
bld.add_subdirs('examples')
bld.recurse('examples')

View File

@@ -6,14 +6,8 @@ import shutil
import types
import warnings
from waflib import TaskGen, Task, Options, Build, Utils
from waflib.Errors import WafError
import TaskGen
import Task
import Options
import Build
import Utils
import wutils
try:
@@ -47,13 +41,26 @@ def options(opt):
help=("Build only these modules (and dependencies)"),
dest='enable_modules')
for module in all_modules:
opt.sub_options(module, mandatory=False)
opt.load('boost', tooldir=['waf-tools'])
for module in all_modules:
opt.recurse(module, mandatory=False)
def configure(conf):
conf.env['REQUIRED_BOOST_LIBS'] = []
for module in all_modules:
conf.sub_config(module, mandatory=False)
conf.recurse (module, name="required_boost_libs", mandatory=False)
if conf.env['REQUIRED_BOOST_LIBS'] is not []:
conf.load('boost')
conf.check_boost(lib=' '.join (conf.env['REQUIRED_BOOST_LIBS']), mandatory=False)
if not conf.env['LIB_BOOST']:
conf.check_boost(lib=' '.join (conf.env['REQUIRED_BOOST_LIBS']), libpath="/usr/lib64", mandatory=False)
if not conf.env['LIB_BOOST']:
conf.env['LIB_BOOST'] = []
for module in all_modules:
conf.recurse(module, mandatory=False)
blddir = os.path.abspath(os.path.join(conf.bldnode.abspath(), conf.variant))
conf.env.append_value('NS3_MODULE_PATH', blddir)
@@ -75,10 +82,10 @@ def create_ns3_module(bld, name, dependencies=(), test=False):
static = bool(bld.env.ENABLE_STATIC_NS3)
# Create a separate library for this module.
if static:
module = bld.new_task_gen(features=['cxx', 'cxxstlib', 'ns3module'])
module = bld(features='cxx cxxstlib ns3module')
else:
module = bld.new_task_gen(features=['cxx', 'cxxshlib', 'ns3module'])
module.target = '%s/ns%s-%s%s' % (bld.srcnode.relpath_gen(module.path), wutils.VERSION,
module = bld(features='cxx cxxshlib ns3module')
module.target = '%s/ns%s-%s%s' % (bld.srcnode.path_from(module.path), wutils.VERSION,
name, bld.env.BUILD_SUFFIX)
linkflags = []
cxxflags = []
@@ -119,7 +126,7 @@ def create_ns3_module(bld, name, dependencies=(), test=False):
module.use = ['ns3-' + dep for dep in dependencies]
module.test = test
module.is_ns3_module = True
module.ns3_dir_location = bld.path.relpath_gen(bld.srcnode)
module.ns3_dir_location = bld.path.path_from(bld.srcnode)
module.env.append_value("INCLUDES", '#')
@@ -133,7 +140,7 @@ def create_ns3_module(bld, name, dependencies=(), test=False):
def apply_incpaths_ns3testlib(self):
if not self.source:
return
testdir = self.source[-1].parent.relpath_gen(self.bld.srcnode)
testdir = self.source[-1].parent.path_from(self.bld.srcnode)
self.env.append_value("DEFINES", 'NS_TEST_SOURCEDIR="%s"' % (testdir,))
@@ -142,7 +149,7 @@ def create_ns3_module_test_library(bld, name):
# the module being tested.
library_name = name + "-test"
library = bld.create_ns3_module(library_name, [name], test=True)
library.features.append("ns3testlib")
library.features += " ns3testlib"
# Modify attributes for the test library that are different from a
# normal module.
@@ -154,7 +161,7 @@ def create_ns3_module_test_library(bld, name):
bld.env.append_value('NS3_MODULES_WITH_TEST_LIBRARIES', [(library.module_name, library.name)])
# Set the include path from the build directory to modules.
relative_path_from_build_to_here = bld.path.relpath_gen(bld.bldnode)
relative_path_from_build_to_here = bld.path.path_from(bld.bldnode)
include_flag = '-I' + relative_path_from_build_to_here
library.env.append_value('CXXFLAGS', include_flag)
library.env.append_value('CCFLAGS', include_flag)
@@ -162,9 +169,9 @@ def create_ns3_module_test_library(bld, name):
return library
def create_obj(bld, *args):
warnings.warn("(in %s) Use bld.new_task_gen(...) now, instead of bld.create_obj(...)" % str(bld.path),
warnings.warn("(in %s) Use bld(...) call now, instead of bld.create_obj(...)" % str(bld.path),
DeprecationWarning, stacklevel=2)
return bld.new_task_gen(*args)
return bld(*args)
def ns3_python_bindings(bld):
@@ -197,23 +204,24 @@ def ns3_python_bindings(bld):
#debug = ('PYBINDGEN_DEBUG' in os.environ)
debug = True # XXX
source = [bld.srcnode.find_resource('bindings/python/ns3modulegen-modular.py').relpath_gen(bld.path),
"bindings/modulegen__%s.py" % apidefs]
source = [bld.srcnode.find_resource('bindings/python/ns3modulegen-modular.py'),
bld.path.find_resource("bindings/modulegen__%s.py" % apidefs)]
if bindings_dir.find_resource("modulegen_customizations.py") is not None:
source.append("bindings/modulegen_customizations.py")
modulegen_customizations = bindings_dir.find_resource("modulegen_customizations.py")
if modulegen_customizations is not None:
source.append(modulegen_customizations)
modulegen_local = bld.path.find_resource("bindings/modulegen_local.py")
# the local customization file may or not exist
if bld.path.find_resource("bindings/modulegen_local.py"):
if modulegen_local is not None:
source.append("bindings/modulegen_local.py")
module_py_name = module.replace('-', '_')
module_target_dir = bld.srcnode.find_dir("bindings/python/ns").relpath_gen(bld.path)
module_target_dir = bld.srcnode.find_dir("bindings/python/ns").path_from(bld.path)
# if bindings/<module>.py exists, it becomes the module frontend, and the C extension befomes _<module>
if bld.path.find_resource("bindings/%s.py" % (module_py_name,)) is not None:
bld.new_task_gen(
features='copy',
bld(features='copy',
source=("bindings/%s.py" % (module_py_name,)),
target=('%s/%s.py' % (module_target_dir, module_py_name)))
extension_name = '_%s' % (module_py_name,)
@@ -240,7 +248,7 @@ def ns3_python_bindings(bld):
if was_enabled:
features.append(name)
bindgen = bld.new_task_gen(features=['command'], source=source, target=target, command=argv)
bindgen = bld(features='command', source=source, target=target, command=argv)
bindgen.env['FEATURES'] = ','.join(features)
bindgen.dep_vars = ['FEATURES', "GCC_RTTI_ABI_COMPLETE"]
bindgen.before = 'cxx'
@@ -249,7 +257,7 @@ def ns3_python_bindings(bld):
bindgen.install_path = None
# generate the extension module
pymod = bld.new_task_gen(features='cxx cxxshlib pyext')
pymod = bld(features='cxx cxxshlib pyext')
pymod.source = ['bindings/ns3module.cc']
pymod.target = '%s/%s' % (module_target_dir, extension_name)
pymod.name = 'ns3module_%s' % module
@@ -305,14 +313,14 @@ def build(bld):
if not_built in all_modules:
all_modules.remove(not_built)
bld.add_subdirs(list(all_modules))
bld.recurse(list(all_modules))
for module in all_modules:
modheader = bld.new_task_gen(features=['ns3moduleheader'])
modheader = bld(features='ns3moduleheader')
modheader.module = module.split('/')[-1]
class ns3pcfile_task(Task.Task):
after = 'cc cxx'
after = 'cxx'
def __str__(self):
"string to display to the user"
@@ -448,7 +456,7 @@ def apply_ns3header(self):
class ns3header_task(Task.Task):
before = 'cc cxx gen_ns3_module_header'
before = 'cxx gen_ns3_module_header'
color = 'BLUE'
def __str__(self):
@@ -517,7 +525,7 @@ class ns3header_task(Task.Task):
class gen_ns3_module_header_task(Task.Task):
before = 'cc cxx'
before = 'cxx'
after = 'ns3header'
color = 'BLUE'

View File

@@ -9,34 +9,53 @@
# rewritten for waf 1.6.2, Sylvain Rouquette, 2011
'''
This is an extra tool, not bundled with the default waf binary.
To add the boost tool to the waf file:
$ ./waf-light --tools=compat15,boost
or, if you have waf >= 1.6.2
$ ./waf update --files=boost
The wscript will look like:
When using this tool, the wscript will look like:
def options(opt):
opt.load('compiler_cxx boost')
def options(opt):
opt.load('compiler_cxx boost')
def configure(conf):
conf.load('compiler_cxx boost')
conf.check_boost(lib='system filesystem', mt=True, static=True)
def configure(conf):
conf.load('compiler_cxx boost')
conf.check_boost(lib='system filesystem')
def build(bld):
bld(source='main.cpp', target='app', use='BOOST')
Options are generated, in order to specify the location of boost includes/libraries.
The `check_boost` configuration function allows to specify the used boost libraries.
It can also provide default arguments to the --boost-static and --boost-mt command-line arguments.
Everything will be packaged together in a BOOST component that you can use.
When using MSVC, a lot of compilation flags need to match your BOOST build configuration:
- you may have to add /EHsc to your CXXFLAGS or define boost::throw_exception if BOOST_NO_EXCEPTIONS is defined.
Errors: C4530
- boost libraries will try to be smart and use the (pretty but often not useful) auto-linking feature of MSVC
So before calling `conf.check_boost` you might want to disabling by adding:
conf.env.DEFINES_BOOST += ['BOOST_ALL_NO_LIB']
Errors:
- boost might also be compiled with /MT, which links the runtime statically.
If you have problems with redefined symbols,
self.env['DEFINES_%s' % var] += ['BOOST_ALL_NO_LIB']
self.env['CXXFLAGS_%s' % var] += ['/MD', '/EHsc']
Passing `--boost-linkage_autodetect` might help ensuring having a correct linkage in some basic cases.
def build(bld):
bld(source='main.cpp', target='app', use='BOOST')
'''
import sys
import re
from waflib import Utils, Logs
from waflib import Utils, Logs, Errors
from waflib.Configure import conf
from waflib.Errors import WafError
BOOST_LIBS = ('/usr/lib', '/usr/local/lib',
'/opt/local/lib', '/sw/lib', '/lib')
BOOST_INCLUDES = ('/usr/include', '/usr/local/include',
'/opt/local/include', '/sw/include')
BOOST_LIBS = ['/usr/lib', '/usr/local/lib', '/opt/local/lib', '/sw/lib', '/lib']
BOOST_INCLUDES = ['/usr/include', '/usr/local/include', '/opt/local/include', '/sw/include']
BOOST_VERSION_FILE = 'boost/version.hpp'
BOOST_VERSION_CODE = '''
#include <iostream>
@@ -76,21 +95,23 @@ BOOST_TOOLSETS = {
def options(opt):
opt.add_option('--boost-includes', type='string',
default='', dest='boost_includes',
help='''path to the boost directory where the includes are
e.g. /boost_1_45_0/include''')
help='''path to the boost includes root (~boost root)
e.g. /path/to/boost_1_47_0''')
opt.add_option('--boost-libs', type='string',
default='', dest='boost_libs',
help='''path to the directory where the boost libs are
e.g. /boost_1_45_0/stage/lib''')
e.g. /path/to/boost_1_47_0/stage/lib''')
opt.add_option('--boost-static', action='store_true',
default=False, dest='boost_static',
help='link static libraries')
help='link with static boost libraries (.lib/.a)')
opt.add_option('--boost-mt', action='store_true',
default=False, dest='boost_mt',
help='select multi-threaded libraries')
opt.add_option('--boost-abi', type='string', default='', dest='boost_abi',
help='''select libraries with tags (dgsyp, d for debug),
see doc Boost, Getting Started, chapter 6.1''')
opt.add_option('--boost-linkage_autodetect', action="store_true", dest='boost_linkage_autodetect',
help="auto-detect boost linkage options (don't get used to it / might break other stuff)")
opt.add_option('--boost-toolset', type='string',
default='', dest='boost_toolset',
help='force a toolset e.g. msvc, vc90, \
@@ -117,8 +138,7 @@ def boost_get_version(self, dir):
try:
val = re_but.search(self.__boost_get_version_file(dir).read()).group(1)
except:
val = self.check_cxx(fragment=BOOST_VERSION_CODE, includes=[dir],
execute=True, define_ret=True)
val = self.check_cxx(fragment=BOOST_VERSION_CODE, includes=[dir], execute=False, define_ret=True)
return val
@@ -130,10 +150,11 @@ def boost_get_includes(self, *k, **kw):
for dir in BOOST_INCLUDES:
if self.__boost_get_version_file(dir):
return dir
if includes:
self.fatal('headers not found in %s' % includes)
else:
self.fatal('headers not found, use --boost-includes=/path/to/boost')
if kw.get('boost_mandatory', True):
if includes:
self.fatal('headers not found in %s' % includes)
else:
self.fatal('headers not found, please provide a --boost-includes argument (see help)')
@conf
@@ -176,10 +197,12 @@ def __boost_get_libs_path(self, *k, **kw):
if libs:
self.fatal('libs not found in %s' % libs)
else:
self.fatal('libs not found, \
use --boost-includes=/path/to/boost/lib')
return path, files
self.fatal('libs not found, please provide a --boost-libs argument (see help)')
self.to_log('Found the boost path in %r with the libraries:' % path)
for x in files:
self.to_log(' %r' % x)
return path, files
@conf
def boost_get_libs(self, *k, **kw):
@@ -194,37 +217,40 @@ def boost_get_libs(self, *k, **kw):
if kw.get('abi', None):
t.append(kw['abi'])
tags = t and '(-%s)+' % '-'.join(t) or ''
toolset = '(-%s[0-9]{0,3})+' % self.boost_get_toolset(kw.get('toolset', ''))
toolset = self.boost_get_toolset(kw.get('toolset', ''))
toolset_pat = '(-%s[0-9]{0,3})+' % toolset
version = '(-%s)+' % self.env.BOOST_VERSION
def find_lib(re_lib, files):
for file in files:
if re_lib.search(file.name):
self.to_log('Found boost lib %s' % file)
return file
return None
def format_lib_name(name):
if name.startswith('lib'):
if name.startswith('lib') and self.env.CC_NAME != 'msvc':
name = name[3:]
return name.split('.')[0]
return name[:name.rfind('.')]
libs = []
for lib in Utils.to_list(k and k[0] or kw.get('lib', None)):
py = (lib == 'python') and '(-py%s)+' % kw['python'] or ''
# Trying libraries, from most strict match to least one
for pattern in ['boost_%s%s%s%s%s' % (lib, toolset, tags, py, version),
for pattern in ['boost_%s%s%s%s%s' % (lib, toolset_pat, tags, py, version),
'boost_%s%s%s%s' % (lib, tags, py, version),
'boost_%s%s%s' % (lib, tags, version),
# Give up trying to find the right version
'boost_%s%s%s%s' % (lib, toolset, tags, py),
'boost_%s%s%s%s' % (lib, toolset_pat, tags, py),
'boost_%s%s%s' % (lib, tags, py),
'boost_%s%s' % (lib, tags)]:
self.to_log('Trying pattern %s' % pattern)
file = find_lib(re.compile(pattern), files)
if file:
libs.append(format_lib_name(file.name))
break
else:
self.fatal('lib %s not found in %s' % (lib, path))
self.fatal('lib %s not found in %s' % (lib, path.abspath()))
return path.abspath(), libs
@@ -232,10 +258,10 @@ def boost_get_libs(self, *k, **kw):
@conf
def check_boost(self, *k, **kw):
"""
initialize boost
Initialize boost libraries to be used.
You can pass the same parameters as the command line (without "--boost-"),
but the command line has the priority.
Keywords: you can pass the same parameters as with the command line (without "--boost-").
Note that the command line has the priority, and should preferably be used.
"""
if not self.env['CXX']:
self.fatal('load a c++ compiler first, conf.load("compiler_cxx")')
@@ -256,6 +282,8 @@ def check_boost(self, *k, **kw):
except WafError:
self.end_msg("not found", 'YELLOW')
raise
#self.env['INCLUDES_%s' % var] = inc = self.boost_get_includes(**params)
#self.env.BOOST_VERSION = self.boost_get_version(inc)
self.end_msg(self.env.BOOST_VERSION)
if Logs.verbose:
Logs.pprint('CYAN', ' path : %s' % self.env['INCLUDES_%s' % var])
@@ -269,6 +297,8 @@ def check_boost(self, *k, **kw):
except WafError:
self.end_msg("not found", 'YELLOW')
raise
#suffix = params.get('static', None) and 'ST' or ''
#path, libs = self.boost_get_libs(**params)
self.env['%sLIBPATH_%s' % (suffix, var)] = [path]
self.env['%sLIB_%s' % (suffix, var)] = libs
self.end_msg('ok')
@@ -276,3 +306,69 @@ def check_boost(self, *k, **kw):
Logs.pprint('CYAN', ' path : %s' % path)
Logs.pprint('CYAN', ' libs : %s' % libs)
def try_link():
if 'system' in params['lib']:
self.check_cxx(
fragment="\n".join([
'#include <boost/system/error_code.hpp>',
'int main() { boost::system::error_code c; }',
]),
use=var,
execute=False,
)
if 'thread' in params['lib']:
self.check_cxx(
fragment="\n".join([
'#include <boost/thread.hpp>',
'int main() { boost::thread t; }',
]),
use=var,
execute=False,
)
if params.get('linkage_autodetect', False):
self.start_msg("Attempting to detect boost linkage flags")
toolset = self.boost_get_toolset(kw.get('toolset', ''))
if toolset in ['vc']:
# disable auto-linking feature, causing error LNK1181
# because the code wants to be linked against
self.env['DEFINES_%s' % var] += ['BOOST_ALL_NO_LIB']
# if no dlls are present, we guess the .lib files are not stubs
has_dlls = False
for x in Utils.listdir(path):
if x.endswith(self.env.cxxshlib_PATTERN % ''):
has_dlls = True
break
if not has_dlls:
self.env['STLIBPATH_%s' % var] = [path]
self.env['STLIB_%s' % var] = libs
del self.env['LIB_%s' % var]
del self.env['LIBPATH_%s' % var]
# we attempt to play with some known-to-work CXXFLAGS combinations
for cxxflags in (['/MD', '/EHsc'], []):
self.env.stash()
self.env["CXXFLAGS_%s" % var] += cxxflags
try:
try_link()
self.end_msg("ok: winning cxxflags combination: %s" % (self.env["CXXFLAGS_%s" % var]))
e = None
break
except Errors.ConfigurationError as exc:
self.env.revert()
e = exc
if e is not None:
self.fatal("Could not auto-detect boost linking flags combination, you may report it to boost.py author", ex=e)
else:
self.fatal("Boost linkage flags auto-detection not implemented (needed ?) for this toolchain")
else:
self.start_msg('Checking for boost linkage')
try:
try_link()
except Errors.ConfigurationError as e:
self.fatal("Could not link against boost libraries using supplied options")
self.end_msg('ok')