# (C) Copyright David Abrahams 2001-2003. Permission to copy, use, # modify, sell and distribute this software is granted provided this # copyright notice appears in all copies. This software is provided # "as is" without express or implied warranty, and with no claim as # to its suitability for any purpose. # This file is part of Boost.Build version 2. You can think of it as # forming the main() routine. It is invoked by the bootstrapping code # in bootstrap.jam. # # The version of bootstrap.jam invoking this lives in # tools/build/kernel until BBv1 is retired, so that BBv1 can have its # bootstrap.jam in this directory. import project ; import targets ; import sequence ; import modules ; import feature ; import property-set ; import build-request ; import errors : error ; import "class" : new ; import builtin ; import make ; import os ; import version ; # Returns the location of the build system. The primary use case # is building Boost, where it's sometimes needed to get location # of other components (like BoostBook files), and it's convenient # to use location relatively to Boost.Build path. rule location ( ) { local r = [ modules.binding build-system ] ; return $(r:P) ; } # Check if we can load 'test-config.jam'. If we can, load it and # ignore user configs. local test-config = [ GLOB [ os.environ BOOST_BUILD_PATH ] : test-config.jam ] ; if $(test-config) { module test-config { import project : _using : using ; } import test-config ; } local ignore-config ; if $(test-config) || --ignore-config in [ modules.peek : ARGV ] { ignore-config = true ; } local user-path = [ os.home-directories ] [ os.environ BOOST_BUILD_PATH ] ; # Load site-config. module site-config { import project : initialize ; initialize site-config ; } if ! $(ignore-config) { local path ; if [ os.name ] in NT CYGWIN { path = [ modules.peek : SystemRoot ] $(user-path) ; } else { path = /etc $(user-path) ; } if --debug-configuration in [ modules.peek : ARGV ] { local where = [ GLOB $(path) : site-config.jam ] ; if $(where) { ECHO "notice: loading site-config.jam from" [ NORMALIZE_PATH $(where[1]) ] ; } } modules.load site-config : : $(path) ; } # Load user-config. module user-config { import project : initialize ; initialize user-config ; } if ! $(ignore-config) { if --debug-configuration in [ modules.peek : ARGV ] { local where = [ GLOB $(user-path) : user-config.jam ] ; if $(where) { ECHO "notice: loading user-config.jam from" [ NORMALIZE_PATH $(where[1]) ] ; } } modules.load user-config : : $(user-path) ; } if USER_MODULE in [ RULENAMES ] { USER_MODULE site-config user-config ; } if --version in [ modules.peek : ARGV ] { version.print ; EXIT ; } # We always load project in "." so that 'use-project' directives has # any chance of been seen. Otherwise, we won't be able to refer to # subprojects using target ids. if [ project.find "." : "." ] { current-project = [ project.target [ project.load "." ] ] ; } if ! [ feature.values ] { ECHO "warning: no toolsets are configured." ; ECHO "warning: you won't be able to build C++ programs." ; ECHO "warning: please consult the documentation." ; ECHO ; } build-request = [ build-request.from-command-line [ modules.peek : ARGV ] ] ; properties = [ $(build-request).get-at 2 ] ; if $(properties) { expanded = [ build-request.expand-no-defaults $(properties) ] ; local xexpanded ; for local e in $(expanded) { xexpanded += [ property-set.create [ feature.split $(e) ] ] ; } expanded = $(xexpanded) ; } local target-ids = [ $(build-request).get-at 1 ] ; local targets local clean ; if "--clean" in [ modules.peek : ARGV ] { clean = true ; } local bjam-targets ; # Given a target it, try to find and return corresponding target. # This is only invoked when there's no Jamfile in "." # This code somewhat duplicates code in project-target.find but we can't reuse # that code without project-targets instance. rule find-target ( target-id ) { local split = [ MATCH (.*)//(.*) : $(target-id) ] ; local pm ; if $(split) { pm = [ project.find $(split[1]) : "." ] ; } else { pm = [ project.find $(target-id) : "." ] ; } local result ; if $(pm) { result = [ project.target $(pm) ] ; } if $(split) { result = [ $(result).find $(split[2]) ] ; } return $(result) ; } if ! $(current-project) { if ! $(target-ids) { ECHO "error: no Jamfile in current directory found, and no target references specified." ; EXIT ; } } for local id in $(target-ids) { if $(id) = clean { clean = true ; } else { local t ; if $(current-project) { t = [ $(current-project).find $(id) : no-error ] ; } else { t = [ find-target $(id) ] ; } if ! $(t) { ECHO "notice: could not find main target " $(id) ; ECHO "notice: assuming it's a name of file to create " ; bjam-targets += $(id) ; } else { targets += $(t) ; } } } if ! $(targets) { targets += [ project.target [ project.module-name "." ] ] ; } virtual-targets = ; if $(expanded) { for local p in $(expanded) { for local t in $(targets) { local g = [ $(t).generate $(p) ] ; virtual-targets += $(g[2-]) ; } } } else { for local t in $(targets) { local g = [ $(t).generate [ property-set.empty ] ] ; virtual-targets += $(g[2-]) ; } } actual-targets = ; for t in $(virtual-targets) { actual-targets += [ $(t).actualize ] ; } NOTFILE all ; DEPENDS all : $(actual-targets) ; if $(bjam-targets) { UPDATE $(bjam-targets) ; } else if $(clean) { UPDATE clean ; } else { UPDATE all ; }