⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 project.jam

📁 boost库提供标准的C++ API 配合dev c++使用,功能更加强大
💻 JAM
📖 第 1 页 / 共 2 页
字号:
#  Copyright (C) Vladimir Prus and Rene Rivera 2002.
#  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.

#  Implements project representation and loading.
#   Each project is represented by 
#   - a module where all the Jamfile content live. 
#   - an instance of 'project-attributes' class.
#     (given module name, can be obtained by 'attributes' rule)
#   - an instance of 'project-target' class (from targets.jam)
#     (given a module name, can be obtained by 'target' rule)
#
#  Typically, projects are created as result of loading Jamfile, which is
#  do by rules 'load' and 'initialize', below. First, module for Jamfile
#  is loaded and new project-attributes instance is created. Some rules
#  necessary for project are added to the module (see 'project-rules' module)
#  at the bottom of this file.
#  Default project attributes are set (inheriting attributes of parent project, if
#  it exists). After that, Jamfile is read. It can declare its own attributes,
#  via 'project' rule, which will be combined with already set attributes.
#
#
#  The 'project' rule can also declare project id, which will be associated with 
#  the project module.
#
#  There can also be 'standalone' projects. They are created by calling 'initialize'
#  on arbitrary module, and not specifying location. After the call, the module can
#  call 'project' rule, declare main target and behave as regular projects. However,
#  since it's not associated with any location, it's better declare only prebuilt 
#  targets.
#
#  The list of all loaded Jamfile is stored in variable .project-locations. It's possible
#  to obtain module name for a location using 'module-name' rule. The standalone projects
#  are not recorded, the only way to use them is by project id.


import modules : peek poke ;
import numbers ;
import path ;
import sequence ;
import errors : error ;
import project-roots ;

import print ;
import "class" : new ;
import errors ;
import assert ;
import property-set ;

#
#   Loads jamfile at the given location. After loading, project global
#   file and jamfile needed by the loaded one will be loaded recursively.
#   If the jamfile at that location is loaded already, does nothing.
#   Returns the project module for the Jamfile.
#
rule load ( jamfile-location )
{   
    # Load project root, first. It might decide to act as Jamfile.
    project-roots.load $(jamfile-location) ;
        
    local module-name = [ module-name $(jamfile-location) ] ;            
    # If Jamfile is already loaded, don't try again.
    if ! $(module-name) in $(.jamfile-modules)
    {      
        load-jamfile $(jamfile-location) ;
                
        for local p in [ attribute $(module-name) projects-to-build ]
        {
            load [ path.join $(jamfile-location) $(p) ] ;
        }
    }                
    return $(module-name) ;        
}

# Makes the specified 'module' act as if it were a regularly loaded Jamfile 
# at 'location'. If Jamfile is already located for that location, it's an 
# error. 
rule act-as-jamfile ( module : location )
{
    if [ module-name $(location) ] in $(.jamfile-modules)
    {
        errors.error "Jamfile was already loaded for '$(location)'" ;
    }
    # Set up non-default mapping from location to module.
    .module.$(location) = $(module) ;    
    
    # Add the location to the list of project locations
    # so that we don't try to load Jamfile in future
    .jamfile-modules += [ module-name $(location) ] ;
    
    initialize $(module) : $(location) ;
}


# Given 'name' which can be project-id or plain directory name,
# return project module corresponding to that id or directory.
# Returns nothing of project is not found.
rule find ( name : current-location )
{
    local project-module ;
    
    # Try interpreting name as project id.
    if [ path.is-rooted $(name) ]
    {            
        project-module =  $($(name).jamfile-module) ;
    }            
                
    if ! $(project-module)
    {            
        local location = [ path.root $(name) $(current-location) ] ;
        # If no project is registered for the given location, try to
        # load it. First see if we have Jamfile. If not we might have project
        # root, willing to act as Jamfile. In that case, project-root
        # must be placed in the directory referred by id.
        
        project-module = [ module-name $(location) ] ;
        if ! $(project-module) in $(.jamfile-modules) 
        {
            if [ find-jamfile $(location) ]
            {
                project-module = [ load $(location) ] ;            
            }        
            else
            {
                project-module = ;
            }
        }                    
    }
    
    return $(project-module) ;
}

#
# Returns the name of module corresponding to 'jamfile-location'.
# If no module corresponds to location yet, associates default
# module name with that location.
#
rule module-name ( jamfile-location )
{
    if ! $(.module.$(jamfile-location))
    {
        # Root the path, so that locations are always umbiguious.
        # Without this, we can't decide if '../../exe/program1' and '.'
        # are the same paths, or not.
        jamfile-location = [ path.root $(jamfile-location) [ path.pwd ] ] ;
        .module.$(jamfile-location) =  Jamfile<$(jamfile-location)> ;
    }
    return $(.module.$(jamfile-location)) ;
}

# Default patterns to search for the Jamfiles to use for build
# declarations.
#
JAMFILE = [ modules.peek : JAMFILE ] ;
JAMFILE ?= [Jj]amfile.v2 [Jj]amfile [Jj]amfile.jam ;

# Find the Jamfile at the given location. This returns the exact names of
# all the Jamfiles in the given directory. The optional parent-root argument
# causes this to search not the given directory but the ones above it up
# to the directory given in it.
#
local rule find-jamfile (
    dir # The directory(s) to look for a Jamfile.
    parent-root ? # Optional flag indicating to search for the parent Jamfile.
    )
{
    # Glob for all the possible Jamfiles according to the match pattern.
    #
    local jamfile-glob = ;
    if $(parent-root)
    {
        if ! $(.parent-jamfile.$(dir))
        {     
            .parent-jamfile.$(dir) = 
              [ path.glob-in-parents $(dir) : $(JAMFILE) : $(parent-root) ] ;            
        }        
        jamfile-glob = $(.parent-jamfile.$(dir)) ;                            
    }
    else
    {
        if ! $(.jamfile.$(dir))
        {            
            .jamfile.$(dir) = [ path.glob $(dir) : $(JAMFILE) ] ;         
        }   
        jamfile-glob = $(.jamfile.$(dir)) ;
        
    }

    return $(jamfile-glob) ;
}

# Load a Jamfile at the given directory. Returns nothing.
# Will attempt to load the file as indicated by the JAMFILE patterns. 
# Effect of calling this rule twice with the same 'dir' is underfined.

local rule load-jamfile (
    dir # The directory of the project Jamfile.
    )
{
    # See if the Jamfile is where it should be.
    #
    local jamfile-to-load = [ find-jamfile $(dir) ] ;

    # Could not find it, error.
    #
    if ! $(jamfile-to-load)
    {
        errors.error
            "Unable to load Jamfile." :
            "Could not find a Jamfile in directory '$(dir)'". : 
            "Attempted to find it with pattern '"$(JAMFILE:J=" ")"'." :
            "Please consult the documentation at 'http://www.boost.org'." ;
    }

    # Multiple Jamfiles found in the same place. Warn about this.
    # And ensure we use only one of them.
    # As a temporary convenience measure, if there's Jamfile.v2 amount
    # found files, suppress the warning and use it.
    #
    if $(jamfile-to-load[2-])
    {
        local v2-jamfiles = [ MATCH (.*[Jj]amfile\\.v2) : $(jamfile-to-load) ] ;

        if $(v2-jamfiles) && ! $(v2-jamfiles[2])
        {
            jamfile-to-load = $(v2-jamfiles) ;
        }        
        else
        {                    
            ECHO
              "WARNING: Found multiple Jamfiles at this '"$(dir)"' location!"
                "Loading the first one: '" [ path.basename $(jamfile-to-load[1]) ]  "'." ;
        }
                    
        jamfile-to-load = $(jamfile-to-load[1]) ;
    }
    
    # The module of the jamfile.
    #
    local jamfile-module = [ module-name  [ path.parent $(jamfile-to-load) ] ] ;

    # Initialize the jamfile module before loading.
    #
    initialize $(jamfile-module) : [ path.parent $(jamfile-to-load) ] ;

    # Now load the Jamfile in it's own context.
    # Initialization might have load parent Jamfiles, which might have
    # loaded the current Jamfile with use-project. Do a final check to make
    # sure it's not loaded already.
    if ! $(jamfile-module) in $(.jamfile-modules)
    {           
        .jamfile-modules += $(jamfile-module) ;
        modules.load $(jamfile-module) :  [ path.native $(jamfile-to-load) ] : . ;
    }
    
}

# Initialize the module for a project. 
#
rule initialize (
    module-name # The name of the project module.
    : location ? # The location (directory) of the project to initialize.
                 # If not specified, stanalone project will be initialized.               
    )
{
    # TODO: need to consider if standalone projects can do anything but defining
    # prebuilt targets. If so, we need to give more sensible "location", so that
    # source paths are correct.
    location ?= "" ;
    # Create the module for the Jamfile first.    
    module $(module-name)
    {          
    }    
    $(module-name).attributes = [ new project-attributes $(location) ] ;
    local attributes = $($(module-name).attributes) ;
    
    $(attributes).set source-location : $(location) : exact ;    
    $(attributes).set requirements : [ property-set.empty ] : exact ;
    $(attributes).set usage-requirements : [ property-set.empty ] : exact ;    

    # Import rules common to all project modules from project-rules module,
    # defined at the end of this file.
    modules.clone-rules project-rules $(module-name) ;

    # We search for parent/project-root only if jamfile was specified --- i.e
    # if the project is not standalone.
    if $(location)
    {       
        # Make sure we've loaded the project-root corresponding to this
        # Jamfile.
        #
        local project-root-module = [ project-roots.load $(location) ] ;
        local project-root = [ $(project-root-module).project-root get-location ] ;
        
        $(attributes).set project-root-module : $(project-root-module) : exact ;

        local parent = [ find-jamfile $(location) $(project-root) ] ;
        local parent-module = ;
        if $(parent)
        {
            parent-module = [ load [ path.parent $(parent[1]) ] ] ;
        }
        

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -