From 019cf3d483fa2c024845e9b0a9614a5341d412d5 Mon Sep 17 00:00:00 2001 From: Gustavo Jose de Sousa Date: Tue, 22 Mar 2016 19:28:19 -0300 Subject: [PATCH] waf: toolchain: clang: use configure wrapper This is a better approach than checking command line options --check-cxx-compiler and --check-c-compiler. Those values expect a list of compilers to try instead of the compiler to use. The benefits of this approach are: - Allowing correct use of options --check-cxx-compiler and --check-c-compiler. - Allowing user to pass CXX and CC environment variables, which is a common way of selecting the compiler. - Configuration is done *and committed* only for the specific compiler. --- Tools/ardupilotwaf/toolchain.py | 88 ++++++++++++++++++++------------- 1 file changed, 55 insertions(+), 33 deletions(-) diff --git a/Tools/ardupilotwaf/toolchain.py b/Tools/ardupilotwaf/toolchain.py index dd682415da..2b98c56818 100644 --- a/Tools/ardupilotwaf/toolchain.py +++ b/Tools/ardupilotwaf/toolchain.py @@ -13,7 +13,7 @@ Example:: """ from waflib import Errors, Context, Utils -from waflib.Tools import gxx, gcc +from waflib.Tools import clang, clangxx, gcc, gxx import os @@ -66,45 +66,67 @@ def _set_toolchain_prefix_wrapper(tool_module, var, compiler_names): _set_toolchain_prefix_wrapper(gxx, 'CXX', ('g++', 'c++')) _set_toolchain_prefix_wrapper(gcc, 'CC', ('gcc', 'cc')) -def configure(cfg): - toolchain = cfg.env.TOOLCHAIN - - if toolchain == 'native': - cfg.load('compiler_cxx compiler_c') +def _clang_cross_support(cfg): + if _clang_cross_support.called: return - cfg.msg('Using toolchain', toolchain) - prefix = toolchain + '-' + prefix = cfg.env.TOOLCHAIN + '-' + + cfg.find_program(prefix + 'gcc', var='CROSS_GCC') + toolchain_path = os.path.join(find_realexec_path(cfg, prefix + 'ar'), + '..') + toolchain_path = os.path.abspath(toolchain_path) + + cfg.msg('Using toolchain path for clang', toolchain_path) - c_compiler = cfg.options.check_c_compiler or 'gcc' - cxx_compiler = cfg.options.check_cxx_compiler or 'g++' + sysroot = cfg.cmd_and_log( + [cfg.env.CROSS_GCC[0], '--print-sysroot'], + quiet=Context.BOTH, + ).strip() - cfg.env['AR'] = prefix + 'ar' + cfg.env.CLANG_FLAGS = [ + '--target=' + cfg.env.TOOLCHAIN, + '--gcc-toolchain=' + toolchain_path, + '--sysroot=' + sysroot, + '-B' + os.path.join(toolchain_path, 'bin') + ] - if 'clang' == c_compiler or 'clang++' == cxx_compiler: - toolchain_path = os.path.join(find_realexec_path(cfg, prefix + 'ar'), - '..') - toolchain_path = os.path.abspath(toolchain_path) - cfg.msg('Using toolchain path', toolchain_path) +_clang_cross_support.called = False + +def _set_clang_crosscompilation_wrapper(tool_module): + original_configure = tool_module.configure + def new_configure(cfg): + if cfg.env.TOOLCHAIN == 'native': + original_configure(cfg) + return - sysroot = cfg.cmd_and_log( - [prefix + 'gcc', '--print-sysroot'], - quiet=Context.BOTH, - )[:-1] - clang_flags = [ - '--target=' + toolchain, - '--gcc-toolchain=' + toolchain_path, - '--sysroot=' + sysroot, - '-B' + os.path.join(toolchain_path, 'bin') - ] - cfg.env.LINKFLAGS += clang_flags + cfg.env.stash() + try: + _clang_cross_support(cfg) + original_configure(cfg) + except Errors.ConfigurationError as e: + cfg.env.revert() + raise + else: + cfg.env.commit() + tool_module.configure = new_configure - if 'clang' == c_compiler: - cfg.env['CC'] = 'clang' - cfg.env.CFLAGS += clang_flags +_set_clang_crosscompilation_wrapper(clang) +_set_clang_crosscompilation_wrapper(clangxx) - if 'clang++' == cxx_compiler: - cfg.env['CXX'] = 'clang++' - cfg.env.CXXFLAGS += clang_flags +def configure(cfg): + if cfg.env.TOOLCHAIN == 'native': + cfg.load('compiler_cxx compiler_c') + return + cfg.env.AR = cfg.env.TOOLCHAIN + '-ar' + cfg.msg('Using toolchain', cfg.env.TOOLCHAIN) cfg.load('compiler_cxx compiler_c') + + if cfg.env.COMPILER_CC == 'clang': + cfg.env.CFLAGS += cfg.env.CLANG_FLAGS + cfg.env.LINKFLAGS_cprogram += cfg.env.CLANG_FLAGS + + if cfg.env.COMPILER_CXX == 'clang++': + cfg.env.CXXFLAGS += cfg.env.CLANG_FLAGS + cfg.env.LINKFLAGS_cxxprogram += cfg.env.CLANG_FLAGS