Add more rules to simplify dealing with build features

* Introduce the notion of build feature attributes and add rules
  SetBuildFeatureAttribute and BuildFeatureAttribute to set respectively
  get a build feature attribute.
* Add rule ExtractBuildFeatureArchives to download and extract archives
  and set build feature attributes to extracted entries.
* Add rule UseBuildFeatureHeaders as a shorthand for getting a build
  feature attribute and adding it as a system header search directory.
This commit is contained in:
Ingo Weinhold 2013-05-06 04:31:27 +02:00
parent b923a5072e
commit 4bee3d6fb9
2 changed files with 179 additions and 0 deletions

View File

@ -412,6 +412,20 @@ rule UsePrivateSystemHeaders
}
rule UseBuildFeatureHeaders feature : attribute
{
# UseBuildFeatureHeaders <feature> : [ <attribute> ] ;
# A shorthand for
# UseHeaders [ BuildFeatureAttribute <feature> : <attribute> ] : true ;
# Moreover the default value for <attribute> is "headers", which usually
# allows the rule to be called with the feature name as the only parameter.
local headers = [ BuildFeatureAttribute $(feature) : $(attribute:E=headers)
: path ] ;
UseHeaders $(headers) : true ;
}
rule FStandardOSHeaders
{
local osIncludes = add-ons add-ons/file_system add-ons/graphics

View File

@ -590,3 +590,168 @@ rule EnableBuildFeatures features : specification
}
}
}
rule BuildFeatureObject feature
{
# BuildFeatureObject <feature> ;
# Returns a unique object for the given build feature. It is used for
# attaching attribute values to it.
local featureObject = $(HAIKU_BUILD_FEATURE_$(feature:U)) ;
if ! $(featureObject) {
featureObject = [ NewUniqueTarget ] ;
HAIKU_BUILD_FEATURE_$(feature:U) = $(featureObject) ;
}
return $(featureObject) ;
}
rule SetBuildFeatureAttribute feature : attribute : values : package
{
# SetBuildFeatureAttribute <feature> : <attribute> : <values>
# [ : <package> ] ;
# Sets attribute <attribute> of a build feature <feature> to value <values>.
# If <package> is specified, it names the package the attribute belongs to.
local featureObject = [ BuildFeatureObject $(feature) ] ;
HAIKU_ATTRIBUTE_$(attribute) on $(featureObject) = $(values) ;
if $(package) {
HAIKU_ATTRIBUTE_$(attribute):package on $(featureObject) = $(package) ;
}
}
rule BuildFeatureAttribute feature : attribute : flags
{
# BuildFeatureAttribute <feature> : <attribute> [ : <flags> ] ;
# Returns the value of attribute <attribute> of a build feature <feature>.
# Flags can be a list of flags which influence the returned value. Currently
# only flag "path" is defined, which will convert the attribute value --
# which is assumed to be a list of (gristed) targets with a path relative to
# the extraction directory of the build feature archive files -- to paths.
# A typical example is the "headers" attribute, whose value can be used as
# dependency, but which must be converted to a path to be a valid headers
# search path.
local featureObject = [ BuildFeatureObject $(feature) ] ;
local values
= [ on $(featureObject) return $(HAIKU_ATTRIBUTE_$(attribute)) ] ;
if path in $(flags) {
# get the attribute's package and the corresponding extraction dir
local package
= [ BuildFeatureAttribute $(feature) : $(attribute):package ] ;
local directory ;
if $(package) {
directory = [ BuildFeatureAttribute $(feature)
: $(package):directory ] ;
}
# translate the values
local paths ;
local value ;
for value in $(values:G=) {
paths += [ FDirName $(directory) $(value) ] ;
}
values = $(paths) ;
}
return $(values) ;
}
rule ExtractBuildFeatureArchives feature : list
{
# ExtractBuildFeatureArchives <feature> : <list> ;
# Downloads and extracts one or more archives for build feature <feature>
# and sets attributes for the build feature to extracted entries. The syntax
# for <list> is:
# "file:" <packageName> <url>
# <attribute>: <value> ...
# ...
# "file:" <packageName2> <url2>
# ...
#
# <packageName> specifies a short name for the archive (e.g. "base" for the
# base package, "devel" for the development package, etc.), <url> the URL
# from which to download the file. <attribute> and be any name and <value>
# any relative path in the extraction directory.
#
# The attribute with the name "depends" will be handled specially. Its
# <value> specifies the name of a package the current package depends on
# (e.g. "devel" typically depends on "base"). If such a dependency is
# specified the current package will be extracted to the same directory as
# the package it depends on. The "depends" attribute must precede any other
# attribute for the package.
#
# The rule also sets the build feature attribute "<packageName>:directory"
# to the extraction directory for each package.
while $(list) {
if $(list[1]) != file: {
Exit "ExtractBuildFeatureArchives: Expected \"file: ...\", got:"
$(list) ;
}
local package = $(list[2]) ;
local url = $(list[3]) ;
local fileName = $(url:BS) ;
list = $(list[4-]) ;
local file = [ DownloadFile $(fileName) : $(url) ] ;
local directory = [ FDirName $(HAIKU_OPTIONAL_BUILD_PACKAGES_DIR)
$(fileName:B) ] ;
directory = $(directory:G=$(package)) ;
while $(list) {
local attribute = [ Match "(.*):" : $(list[1]) ] ;
if ! $(attribute) {
Exit "ExtractBuildFeatureArchives: Expected attribute, got:"
$(list) ;
}
if $(attribute) = file {
break ;
}
list = $(list[2-]) ;
local values ;
while $(list) {
switch $(list[1]) {
case *: :
{
break ;
}
case * :
{
values += $(list[1]) ;
list = $(list[2-]) ;
}
}
}
if $(attribute) = depends {
# Inherit the extraction directory (with a different grist) and
# depend on the extraction directory of the base package.
local basePackage = $(values[1]) ;
local baseDirectory = [ BuildFeatureAttribute $(feature)
: $(basePackage):directory ] ;
directory = $(baseDirectory:G=$(package)) ;
Depends $(directory) : $(directory:G=$(basePackage)) ;
} else {
SetBuildFeatureAttribute $(feature) : $(attribute)
: [ ExtractArchive $(directory)
: $(values) : $(file)
: extracted-$(feature)-$(package) ] ;
SetBuildFeatureAttribute $(feature) : $(attribute):package
: $(package) ;
}
}
SetBuildFeatureAttribute $(feature) : $(package):directory
: $(directory:G=) ;
}
}