# Copyright (c) 2010 WorkWare Systems http://www.workware.net.au/ # All rights reserved # @synopsis: # # This module supports common system interrogation and options # such as --host, --build, --prefix, and setting srcdir, builddir, and EXEEXT # # It also support the 'feature' naming convention, where searching # for a feature such as sys/type.h defines HAVE_SYS_TYPES_H # # It defines the following variables, based on --prefix unless overridden by the user: # ## datadir ## sysconfdir ## sharedstatedir ## localstatedir ## infodir ## mandir ## includedir # Do "define defaultprefix myvalue" to set the default prefix *before* the first "use" set defaultprefix [get-define defaultprefix /usr/local] module-options [subst -noc -nob { host:host-alias => {a complete or partial cpu-vendor-opsys for the system where the application will run (defaults to the same value as --build)} build:build-alias => {a complete or partial cpu-vendor-opsys for the system where the application will be built (defaults to the result of running config.guess)} prefix:dir => {the target directory for the build (defaults to '$defaultprefix')} # These (hidden) options are supported for autoconf/automake compatibility exec-prefix: bindir: sbindir: includedir: mandir: infodir: libexecdir: datadir: libdir: sysconfdir: sharedstatedir: localstatedir: maintainer-mode=0 dependency-tracking=0 }] # Returns 1 if exists, or 0 if not # proc check-feature {name code} { msg-checking "Checking for $name..." set r [uplevel 1 $code] define-feature $name $r if {$r} { msg-result "ok" } else { msg-result "not found" } return $r } # @have-feature name ?default=0? # # Returns the value of the feature if defined, or $default if not. # See 'feature-define-name' for how the feature name # is translated into the define name. # proc have-feature {name {default 0}} { get-define [feature-define-name $name] $default } # @define-feature name ?value=1? # # Sets the feature 'define' to the given value. # See 'feature-define-name' for how the feature name # is translated into the define name. # proc define-feature {name {value 1}} { define [feature-define-name $name] $value } # @feature-checked name # # Returns 1 if the feature has been checked, whether true or not # proc feature-checked {name} { is-defined [feature-define-name $name] } # @feature-define-name name ?prefix=HAVE_? # # Converts a name to the corresponding define, # e.g. sys/stat.h becomes HAVE_SYS_STAT_H. # # Converts * to P and all non-alphanumeric to underscore. # proc feature-define-name {name {prefix HAVE_}} { string toupper $prefix[regsub -all {[^a-zA-Z0-9]} [regsub -all {[*]} $name p] _] } # If $file doesn't exist, or it's contents are different than $buf, # the file is written and $script is executed. # Otherwise a "file is unchanged" message is displayed. proc write-if-changed {file buf {script {}}} { set old [readfile $file ""] if {$old eq $buf && [file exists $file]} { msg-result "$file is unchanged" } else { writefile $file $buf\n uplevel 1 $script } } # @make-template template ?outfile? # # Reads the input file /$template and writes the output file $outfile. # If $outfile is blank/omitted, $template should end with ".in" which # is removed to create the output file name. # # Each pattern of the form @define@ is replaced with the corresponding # define, if it exists, or left unchanged if not. # # The special value @srcdir@ is substituted with the relative # path to the source directory from the directory where the output # file is created, while the special value @top_srcdir@ is substituted # with the relative path to the top level source directory. # # Conditional sections may be specified as follows: ## @if name == value ## lines ## @else ## lines ## @endif # # Where 'name' is a defined variable name and @else is optional. # If the expression does not match, all lines through '@endif' are ignored. # # The alternative forms may also be used: ## @if name ## @if name != value # # Where the first form is true if the variable is defined, but not empty or 0 # # Currently these expressions can't be nested. # proc make-template {template {out {}}} { set infile [file join $::autosetup(srcdir) $template] if {![file exists $infile]} { user-error "Template $template is missing" } # Define this as late as possible define AUTODEPS $::autosetup(deps) if {$out eq ""} { if {[file ext $template] ne ".in"} { autosetup-error "make_template $template has no target file and can't guess" } set out [file rootname $template] } set outdir [file dirname $out] # Make sure the directory exists file mkdir $outdir # Set up srcdir and top_srcdir to be relative to the target dir define srcdir [relative-path [file join $::autosetup(srcdir) $outdir] $outdir] define top_srcdir [relative-path $::autosetup(srcdir) $outdir] set mapping {} foreach {n v} [array get ::define] { lappend mapping @$n@ $v } set result {} foreach line [split [readfile $infile] \n] { if {[info exists cond]} { set l [string trimright $line] if {$l eq "@endif"} { unset cond continue } if {$l eq "@else"} { set cond [expr {!$cond}] continue } if {$cond} { lappend result $line } continue } if {[regexp {^@if\s+(\w+)(.*)} $line -> name expression]} { lassign $expression equal value set varval [get-define $name ""] if {$equal eq ""} { set cond [expr {$varval ni {"" 0}}] } else { set cond [expr {$varval eq $value}] if {$equal ne "=="} { set cond [expr {!$cond}] } } continue } lappend result $line } write-if-changed $out [string map $mapping [join $result \n]]\n { msg-result "Created [relative-path $out] from [relative-path $template]" } } # build/host tuples and cross-compilation prefix set build [opt-val build] define build_alias $build if {$build eq ""} { define build [config_guess] } else { define build [config_sub $build] } set host [opt-val host] define host_alias $host if {$host eq ""} { define host [get-define build] set cross "" } else { define host [config_sub $host] set cross $host- } define cross [get-env CROSS $cross] set prefix [opt-val prefix $defaultprefix] # These are for compatibility with autoconf define target [get-define host] define prefix $prefix define builddir $autosetup(builddir) define srcdir $autosetup(srcdir) # Allow this to come from the environment define top_srcdir [get-env top_srcdir [get-define srcdir]] # autoconf supports all of these set exec_prefix [opt-val exec-prefix $prefix] define exec_prefix $exec_prefix foreach {name defpath} { bindir /bin sbindir /sbin libexecdir /libexec libdir /lib } { define $name [opt-val $name $exec_prefix$defpath] } foreach {name defpath} { datadir /share sysconfdir /etc sharedstatedir /com localstatedir /var infodir /share/info mandir /share/man includedir /include } { define $name [opt-val $name $prefix$defpath] } define SHELL [get-env SHELL [find-an-executable sh bash ksh]] # Windows vs. non-Windows switch -glob -- [get-define host] { *-*-ming* - *-*-cygwin - *-*-msys { define-feature windows define EXEEXT .exe } default { define EXEEXT "" } } # Display msg-result "Host System...[get-define host]" msg-result "Build System...[get-define build]"