45103 lines
772 KiB
HTML
45103 lines
772 KiB
HTML
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN""http://www.w3.org/TR/html4/loose.dtd">
|
|
<HTML
|
|
><HEAD
|
|
><TITLE
|
|
>SCons User Guide 1.0.1</TITLE
|
|
><META
|
|
NAME="GENERATOR"
|
|
CONTENT="Modular DocBook HTML Stylesheet Version 1.79"></HEAD
|
|
><BODY
|
|
CLASS="book"
|
|
BGCOLOR="#FFFFFF"
|
|
TEXT="#000000"
|
|
LINK="#0000FF"
|
|
VLINK="#840084"
|
|
ALINK="#0000FF"
|
|
><DIV
|
|
CLASS="BOOK"
|
|
><A
|
|
NAME="AEN1"
|
|
></A
|
|
><DIV
|
|
CLASS="TITLEPAGE"
|
|
><H1
|
|
CLASS="title"
|
|
><A
|
|
NAME="AEN2"
|
|
>SCons User Guide 1.0.1</A
|
|
></H1
|
|
><H3
|
|
CLASS="author"
|
|
><A
|
|
NAME="AEN4"
|
|
></A
|
|
>Steven Knight</H3
|
|
><P
|
|
CLASS="copyright"
|
|
>Copyright © 2004, 2005, 2006, 2007, 2008 Steven Knight</P
|
|
><DIV
|
|
CLASS="legalnotice"
|
|
><P
|
|
></P
|
|
><A
|
|
NAME="AEN12"
|
|
></A
|
|
><A
|
|
NAME="AEN13"
|
|
></A
|
|
><BLOCKQUOTE
|
|
CLASS="BLOCKQUOTE"
|
|
><P
|
|
>
|
|
SCons User's Guide Copyright (c) 2004, 2005, 2006, 2007 Steven Knight
|
|
|
|
</P
|
|
></BLOCKQUOTE
|
|
><P
|
|
></P
|
|
></DIV
|
|
><HR></DIV
|
|
><DIV
|
|
CLASS="TOC"
|
|
><DL
|
|
><DT
|
|
><B
|
|
>Table of Contents</B
|
|
></DT
|
|
><DT
|
|
><A
|
|
HREF="#chap-preface"
|
|
>Preface</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>1. <A
|
|
HREF="#AEN29"
|
|
><SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Principles</A
|
|
></DT
|
|
><DT
|
|
>2. <A
|
|
HREF="#AEN54"
|
|
>A Caveat About This Guide's Completeness</A
|
|
></DT
|
|
><DT
|
|
>3. <A
|
|
HREF="#AEN62"
|
|
>Acknowledgements</A
|
|
></DT
|
|
><DT
|
|
>4. <A
|
|
HREF="#AEN83"
|
|
>Contact</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>1. <A
|
|
HREF="#chap-build-install"
|
|
>Building and Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
></A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>1.1. <A
|
|
HREF="#AEN102"
|
|
>Installing Python</A
|
|
></DT
|
|
><DT
|
|
>1.2. <A
|
|
HREF="#AEN124"
|
|
>Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> From Pre-Built Packages</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>1.2.1. <A
|
|
HREF="#AEN129"
|
|
>Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Red Hat (and Other RPM-based) Linux Systems</A
|
|
></DT
|
|
><DT
|
|
>1.2.2. <A
|
|
HREF="#AEN149"
|
|
>Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Debian Linux Systems</A
|
|
></DT
|
|
><DT
|
|
>1.2.3. <A
|
|
HREF="#AEN157"
|
|
>Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Windows Systems</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>1.3. <A
|
|
HREF="#AEN166"
|
|
>Building and Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Any System</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>1.3.1. <A
|
|
HREF="#AEN194"
|
|
>Building and Installing Multiple Versions of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Side-by-Side</A
|
|
></DT
|
|
><DT
|
|
>1.3.2. <A
|
|
HREF="#AEN218"
|
|
>Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in Other Locations</A
|
|
></DT
|
|
><DT
|
|
>1.3.3. <A
|
|
HREF="#AEN236"
|
|
>Building and Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Without Administrative Privileges</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>2. <A
|
|
HREF="#chap-simple"
|
|
>Simple Builds</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>2.1. <A
|
|
HREF="#AEN256"
|
|
>Building Simple C / C++ Programs</A
|
|
></DT
|
|
><DT
|
|
>2.2. <A
|
|
HREF="#AEN288"
|
|
>Building Object Files</A
|
|
></DT
|
|
><DT
|
|
>2.3. <A
|
|
HREF="#AEN307"
|
|
>Simple Java Builds</A
|
|
></DT
|
|
><DT
|
|
>2.4. <A
|
|
HREF="#AEN328"
|
|
>Cleaning Up After a Build</A
|
|
></DT
|
|
><DT
|
|
>2.5. <A
|
|
HREF="#AEN348"
|
|
>The <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> File</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>2.5.1. <A
|
|
HREF="#AEN358"
|
|
><TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> Files Are Python Scripts</A
|
|
></DT
|
|
><DT
|
|
>2.5.2. <A
|
|
HREF="#AEN370"
|
|
><SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Functions Are Order-Independent</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>2.6. <A
|
|
HREF="#AEN420"
|
|
>Making the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Output Less Verbose</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>3. <A
|
|
HREF="#chap-less-simple"
|
|
>Less Simple Things to Do With Builds</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>3.1. <A
|
|
HREF="#AEN443"
|
|
>Specifying the Name of the Target (Output) File</A
|
|
></DT
|
|
><DT
|
|
>3.2. <A
|
|
HREF="#AEN467"
|
|
>Compiling Multiple Source Files</A
|
|
></DT
|
|
><DT
|
|
>3.3. <A
|
|
HREF="#AEN489"
|
|
>Making a list of files with <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
></A
|
|
></DT
|
|
><DT
|
|
>3.4. <A
|
|
HREF="#AEN508"
|
|
>Specifying Single Files Vs. Lists of Files</A
|
|
></DT
|
|
><DT
|
|
>3.5. <A
|
|
HREF="#AEN526"
|
|
>Making Lists of Files Easier to Read</A
|
|
></DT
|
|
><DT
|
|
>3.6. <A
|
|
HREF="#AEN552"
|
|
>Keyword Arguments</A
|
|
></DT
|
|
><DT
|
|
>3.7. <A
|
|
HREF="#AEN563"
|
|
>Compiling Multiple Programs</A
|
|
></DT
|
|
><DT
|
|
>3.8. <A
|
|
HREF="#AEN577"
|
|
>Sharing Source Files Between Multiple Programs</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>4. <A
|
|
HREF="#chap-libraries"
|
|
>Building and Linking with Libraries</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>4.1. <A
|
|
HREF="#AEN597"
|
|
>Building Libraries</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>4.1.1. <A
|
|
HREF="#AEN616"
|
|
>Building Libraries From Source Code or Object Files</A
|
|
></DT
|
|
><DT
|
|
>4.1.2. <A
|
|
HREF="#AEN627"
|
|
>Building Static Libraries Explicitly: the <CODE
|
|
CLASS="function"
|
|
>StaticLibrary</CODE
|
|
> Builder</A
|
|
></DT
|
|
><DT
|
|
>4.1.3. <A
|
|
HREF="#AEN641"
|
|
>Building Shared (DLL) Libraries: the <CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
> Builder</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>4.2. <A
|
|
HREF="#AEN658"
|
|
>Linking with Libraries</A
|
|
></DT
|
|
><DT
|
|
>4.3. <A
|
|
HREF="#AEN685"
|
|
>Finding Libraries: the <CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
> Construction Variable</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>5. <A
|
|
HREF="#chap-nodes"
|
|
>Node Objects</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>5.1. <A
|
|
HREF="#AEN716"
|
|
>Builder Methods Return Lists of Target Nodes</A
|
|
></DT
|
|
><DT
|
|
>5.2. <A
|
|
HREF="#AEN747"
|
|
>Explicitly Creating File and Directory Nodes</A
|
|
></DT
|
|
><DT
|
|
>5.3. <A
|
|
HREF="#AEN767"
|
|
>Printing <CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
> File Names</A
|
|
></DT
|
|
><DT
|
|
>5.4. <A
|
|
HREF="#AEN779"
|
|
>Using a <CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
>'s File Name as a String</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>6. <A
|
|
HREF="#chap-depends"
|
|
>Dependencies</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>6.1. <A
|
|
HREF="#AEN815"
|
|
>Deciding When an Input File Has Changed: the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> Function</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>6.1.1. <A
|
|
HREF="#AEN823"
|
|
>Using MD5 Signatures to Decide if a File Has Changed</A
|
|
></DT
|
|
><DT
|
|
>6.1.2. <A
|
|
HREF="#AEN866"
|
|
>Using Time Stamps to Decide If a File Has Changed</A
|
|
></DT
|
|
><DT
|
|
>6.1.3. <A
|
|
HREF="#AEN912"
|
|
>Deciding If a File Has Changed Using Both MD Signatures and Time Stamps</A
|
|
></DT
|
|
><DT
|
|
>6.1.4. <A
|
|
HREF="#AEN937"
|
|
>Writing Your Own Custom <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>6.1.5. <A
|
|
HREF="#AEN977"
|
|
>Mixing Different Ways of Deciding If a File Has Changed</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>6.2. <A
|
|
HREF="#AEN994"
|
|
>Older Functions for Deciding When an Input File Has Changed</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>6.2.1. <A
|
|
HREF="#AEN999"
|
|
>The <CODE
|
|
CLASS="function"
|
|
>SourceSignatures</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>6.2.2. <A
|
|
HREF="#AEN1011"
|
|
>The <CODE
|
|
CLASS="function"
|
|
>TargetSignatures</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>6.3. <A
|
|
HREF="#AEN1056"
|
|
>Implicit Dependencies: The <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> Construction Variable</A
|
|
></DT
|
|
><DT
|
|
>6.4. <A
|
|
HREF="#AEN1115"
|
|
>Caching Implicit Dependencies</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>6.4.1. <A
|
|
HREF="#AEN1154"
|
|
>The <TT
|
|
CLASS="literal"
|
|
>--implicit-deps-changed</TT
|
|
> Option</A
|
|
></DT
|
|
><DT
|
|
>6.4.2. <A
|
|
HREF="#AEN1166"
|
|
>The <TT
|
|
CLASS="literal"
|
|
>--implicit-deps-unchanged</TT
|
|
> Option</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>6.5. <A
|
|
HREF="#AEN1179"
|
|
>Explicit Dependencies: the <CODE
|
|
CLASS="function"
|
|
>Depends</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>6.6. <A
|
|
HREF="#AEN1198"
|
|
>Dependencies From External Files: the <CODE
|
|
CLASS="function"
|
|
>ParseDepends</CODE
|
|
>
|
|
Function</A
|
|
></DT
|
|
><DT
|
|
>6.7. <A
|
|
HREF="#AEN1234"
|
|
>Ignoring Dependencies: the <CODE
|
|
CLASS="function"
|
|
>Ignore</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>6.8. <A
|
|
HREF="#AEN1261"
|
|
>Order-Only Dependencies: the <CODE
|
|
CLASS="function"
|
|
>Requires</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>6.9. <A
|
|
HREF="#AEN1312"
|
|
>The <CODE
|
|
CLASS="function"
|
|
>AlwaysBuild</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>7. <A
|
|
HREF="#chap-environments"
|
|
>Environments</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>7.1. <A
|
|
HREF="#sect-external-environments"
|
|
>Using Values From the External Environment</A
|
|
></DT
|
|
><DT
|
|
>7.2. <A
|
|
HREF="#sect-construction-environments"
|
|
>Construction Environments</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>7.2.1. <A
|
|
HREF="#AEN1400"
|
|
>Creating a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>7.2.2. <A
|
|
HREF="#AEN1423"
|
|
>Fetching Values From a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
></A
|
|
></DT
|
|
><DT
|
|
>7.2.3. <A
|
|
HREF="#AEN1446"
|
|
>Expanding Values From a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>subst</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>7.2.4. <A
|
|
HREF="#AEN1479"
|
|
>Controlling the Default <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>DefaultEnvironment</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>7.2.5. <A
|
|
HREF="#AEN1510"
|
|
>Multiple <TT
|
|
CLASS="literal"
|
|
>Construction Environments</TT
|
|
></A
|
|
></DT
|
|
><DT
|
|
>7.2.6. <A
|
|
HREF="#AEN1550"
|
|
>Making Copies of <TT
|
|
CLASS="literal"
|
|
>Construction Environments</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>Clone</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>7.2.7. <A
|
|
HREF="#AEN1571"
|
|
>Replacing Values: the <CODE
|
|
CLASS="function"
|
|
>Replace</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>7.2.8. <A
|
|
HREF="#AEN1603"
|
|
>Setting Values Only If They're Not Already Defined: the <CODE
|
|
CLASS="function"
|
|
>SetDefault</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>7.2.9. <A
|
|
HREF="#AEN1612"
|
|
>Appending to the End of Values: the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>7.2.10. <A
|
|
HREF="#AEN1632"
|
|
>Appending Unique Values: the <CODE
|
|
CLASS="function"
|
|
>AppendUnique</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>7.2.11. <A
|
|
HREF="#AEN1642"
|
|
>Appending to the Beginning of Values: the <CODE
|
|
CLASS="function"
|
|
>Prepend</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>7.2.12. <A
|
|
HREF="#AEN1663"
|
|
>Prepending Unique Values: the <CODE
|
|
CLASS="function"
|
|
>PrependUnique</CODE
|
|
> Method</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>7.3. <A
|
|
HREF="#sect-execution-environments"
|
|
>Controlling the Execution Environment for Issued Commands</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>7.3.1. <A
|
|
HREF="#AEN1704"
|
|
>Propagating <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> From the External Environment</A
|
|
></DT
|
|
><DT
|
|
>7.3.2. <A
|
|
HREF="#AEN1723"
|
|
>Adding to <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> Values in the Execution Environment</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>8. <A
|
|
HREF="#chap-mergeflags"
|
|
>Merging Options into the Environment: the <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>9. <A
|
|
HREF="#chap-parseflags"
|
|
>Separating Compile Arguments into their Variables: the <CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>10. <A
|
|
HREF="#chap-parseconfig"
|
|
>Finding Installed Library Information: the <CODE
|
|
CLASS="function"
|
|
>ParseConfig</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>11. <A
|
|
HREF="#chap-output"
|
|
>Controlling Build Output</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>11.1. <A
|
|
HREF="#AEN1846"
|
|
>Providing Build Help: the <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>11.2. <A
|
|
HREF="#AEN1884"
|
|
>Controlling How <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Prints Build Commands: the <CODE
|
|
CLASS="envar"
|
|
>$*COMSTR</CODE
|
|
> Variables</A
|
|
></DT
|
|
><DT
|
|
>11.3. <A
|
|
HREF="#AEN1921"
|
|
>Providing Build Progress Output: the <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>11.4. <A
|
|
HREF="#AEN1977"
|
|
>Printing Detailed Build Status: the <CODE
|
|
CLASS="function"
|
|
>GetBuildFailures</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>12. <A
|
|
HREF="#chap-command-line"
|
|
>Controlling a Build From the Command Line</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>12.1. <A
|
|
HREF="#sect-command-line-options"
|
|
>Command-Line Options</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>12.1.1. <A
|
|
HREF="#AEN2048"
|
|
>Not Having to Specify Command-Line Options Each Time: the <CODE
|
|
CLASS="varname"
|
|
>SCONSFLAGS</CODE
|
|
> Environment Variable</A
|
|
></DT
|
|
><DT
|
|
>12.1.2. <A
|
|
HREF="#AEN2074"
|
|
>Getting Values Set by Command-Line Options: the <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>12.1.3. <A
|
|
HREF="#AEN2099"
|
|
>Setting Values of Command-Line Options: the <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>12.1.4. <A
|
|
HREF="#sect-command-line-option-strings"
|
|
>Strings for Getting or Setting Values of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Command-Line Options</A
|
|
></DT
|
|
><DT
|
|
>12.1.5. <A
|
|
HREF="#AEN2327"
|
|
>Adding Custom Command-Line Options: the <CODE
|
|
CLASS="function"
|
|
>AddOption</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>12.2. <A
|
|
HREF="#sect-command-line-variables"
|
|
>Command-Line <CODE
|
|
CLASS="varname"
|
|
>variable</CODE
|
|
>=<CODE
|
|
CLASS="varname"
|
|
>value</CODE
|
|
> Build Variables</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>12.2.1. <A
|
|
HREF="#AEN2420"
|
|
>Controlling Command-Line Build Variables</A
|
|
></DT
|
|
><DT
|
|
>12.2.2. <A
|
|
HREF="#AEN2456"
|
|
>Providing Help for Command-Line Build Variables</A
|
|
></DT
|
|
><DT
|
|
>12.2.3. <A
|
|
HREF="#AEN2471"
|
|
>Reading Build Variables From a File</A
|
|
></DT
|
|
><DT
|
|
>12.2.4. <A
|
|
HREF="#AEN2491"
|
|
>Pre-Defined Build Variable Functions</A
|
|
></DT
|
|
><DT
|
|
>12.2.5. <A
|
|
HREF="#AEN2677"
|
|
>Adding Multiple Command-Line Build Variables at Once</A
|
|
></DT
|
|
><DT
|
|
>12.2.6. <A
|
|
HREF="#AEN2687"
|
|
>Handling Unknown Command-Line Build Variables: the <CODE
|
|
CLASS="function"
|
|
>UnknownVariables</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>12.3. <A
|
|
HREF="#sect-command-line-targets"
|
|
>Command-Line Targets</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>12.3.1. <A
|
|
HREF="#AEN2722"
|
|
>Fetching Command-Line Targets: the <CODE
|
|
CLASS="varname"
|
|
>COMMAND_LINE_TARGETS</CODE
|
|
> Variable</A
|
|
></DT
|
|
><DT
|
|
>12.3.2. <A
|
|
HREF="#AEN2739"
|
|
>Controlling the Default Targets: the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>12.3.3. <A
|
|
HREF="#AEN2822"
|
|
>Fetching the List of Build Targets, Regardless of Origin: the <CODE
|
|
CLASS="varname"
|
|
>BUILD_TARGETS</CODE
|
|
> Variable</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>13. <A
|
|
HREF="#chap-install"
|
|
>Installing Files in Other Directories: the <CODE
|
|
CLASS="function"
|
|
>Install</CODE
|
|
> Builder</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>13.1. <A
|
|
HREF="#AEN2869"
|
|
>Installing Multiple Files in a Directory</A
|
|
></DT
|
|
><DT
|
|
>13.2. <A
|
|
HREF="#AEN2879"
|
|
>Installing a File Under a Different Name</A
|
|
></DT
|
|
><DT
|
|
>13.3. <A
|
|
HREF="#AEN2890"
|
|
>Installing Multiple Files Under Different Names</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>14. <A
|
|
HREF="#chap-factories"
|
|
>Platform-Independent File System Manipulation</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>14.1. <A
|
|
HREF="#AEN2906"
|
|
>Copying Files or Directories: The <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> Factory</A
|
|
></DT
|
|
><DT
|
|
>14.2. <A
|
|
HREF="#AEN2940"
|
|
>Deleting Files or Directories: The <CODE
|
|
CLASS="function"
|
|
>Delete</CODE
|
|
> Factory</A
|
|
></DT
|
|
><DT
|
|
>14.3. <A
|
|
HREF="#AEN2969"
|
|
>Moving (Renaming) Files or Directories: The <CODE
|
|
CLASS="function"
|
|
>Move</CODE
|
|
> Factory</A
|
|
></DT
|
|
><DT
|
|
>14.4. <A
|
|
HREF="#AEN2978"
|
|
>Updating the Modification Time of a File: The <CODE
|
|
CLASS="function"
|
|
>Touch</CODE
|
|
> Factory</A
|
|
></DT
|
|
><DT
|
|
>14.5. <A
|
|
HREF="#AEN2987"
|
|
>Creating a Directory: The <CODE
|
|
CLASS="function"
|
|
>Mkdir</CODE
|
|
> Factory</A
|
|
></DT
|
|
><DT
|
|
>14.6. <A
|
|
HREF="#AEN2996"
|
|
>Changing File or Directory Permissions: The <CODE
|
|
CLASS="function"
|
|
>Chmod</CODE
|
|
> Factory</A
|
|
></DT
|
|
><DT
|
|
>14.7. <A
|
|
HREF="#AEN3005"
|
|
>Executing an action immediately: the <CODE
|
|
CLASS="function"
|
|
>Execute</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>15. <A
|
|
HREF="#chap-file-removal"
|
|
>Controlling Removal of Targets</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>15.1. <A
|
|
HREF="#AEN3044"
|
|
>Preventing target removal during build: the <CODE
|
|
CLASS="function"
|
|
>Precious</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>15.2. <A
|
|
HREF="#AEN3060"
|
|
>Preventing target removal during clean: the <CODE
|
|
CLASS="function"
|
|
>NoClean</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>15.3. <A
|
|
HREF="#AEN3074"
|
|
>Removing additional files during clean: the <CODE
|
|
CLASS="function"
|
|
>Clean</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>16. <A
|
|
HREF="#chap-hierarchical"
|
|
>Hierarchical Builds</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>16.1. <A
|
|
HREF="#AEN3101"
|
|
><TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files</A
|
|
></DT
|
|
><DT
|
|
>16.2. <A
|
|
HREF="#AEN3129"
|
|
>Path Names Are Relative to the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Directory</A
|
|
></DT
|
|
><DT
|
|
>16.3. <A
|
|
HREF="#AEN3155"
|
|
>Top-Level Path Names in Subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files</A
|
|
></DT
|
|
><DT
|
|
>16.4. <A
|
|
HREF="#AEN3176"
|
|
>Absolute Path Names</A
|
|
></DT
|
|
><DT
|
|
>16.5. <A
|
|
HREF="#AEN3186"
|
|
>Sharing Environments (and Other Variables) Between <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>16.5.1. <A
|
|
HREF="#AEN3198"
|
|
>Exporting Variables</A
|
|
></DT
|
|
><DT
|
|
>16.5.2. <A
|
|
HREF="#AEN3226"
|
|
>Importing Variables</A
|
|
></DT
|
|
><DT
|
|
>16.5.3. <A
|
|
HREF="#AEN3249"
|
|
>Returning Values From an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> File</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>17. <A
|
|
HREF="#chap-separate"
|
|
>Separating Source and Build Directories</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>17.1. <A
|
|
HREF="#AEN3283"
|
|
>Specifying a Variant Directory Tree as Part of an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Call</A
|
|
></DT
|
|
><DT
|
|
>17.2. <A
|
|
HREF="#AEN3313"
|
|
>Why <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Duplicates Source Files in a Variant Directory Tree</A
|
|
></DT
|
|
><DT
|
|
>17.3. <A
|
|
HREF="#AEN3330"
|
|
>Telling <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to Not Duplicate Source Files in the Variant Directory Tree</A
|
|
></DT
|
|
><DT
|
|
>17.4. <A
|
|
HREF="#AEN3346"
|
|
>The <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>17.5. <A
|
|
HREF="#AEN3375"
|
|
>Using <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> With an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> File</A
|
|
></DT
|
|
><DT
|
|
>17.6. <A
|
|
HREF="#AEN3394"
|
|
>Using <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
> with <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
></A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>18. <A
|
|
HREF="#chap-variants"
|
|
>Variant Builds</A
|
|
></DT
|
|
><DT
|
|
>19. <A
|
|
HREF="#chap-builders-writing"
|
|
>Writing Your Own Builders</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>19.1. <A
|
|
HREF="#AEN3438"
|
|
>Writing Builders That Execute External Commands</A
|
|
></DT
|
|
><DT
|
|
>19.2. <A
|
|
HREF="#AEN3447"
|
|
>Attaching a Builder to a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
></A
|
|
></DT
|
|
><DT
|
|
>19.3. <A
|
|
HREF="#AEN3503"
|
|
>Letting <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Handle The File Suffixes</A
|
|
></DT
|
|
><DT
|
|
>19.4. <A
|
|
HREF="#AEN3524"
|
|
>Builders That Execute Python Functions</A
|
|
></DT
|
|
><DT
|
|
>19.5. <A
|
|
HREF="#AEN3560"
|
|
>Builders That Create Actions Using a <TT
|
|
CLASS="literal"
|
|
>Generator</TT
|
|
></A
|
|
></DT
|
|
><DT
|
|
>19.6. <A
|
|
HREF="#AEN3603"
|
|
>Builders That Modify the Target or Source Lists Using an <TT
|
|
CLASS="literal"
|
|
>Emitter</TT
|
|
></A
|
|
></DT
|
|
><DT
|
|
>19.7. <A
|
|
HREF="#AEN3627"
|
|
>Where To Put Your Custom Builders and Tools</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>20. <A
|
|
HREF="#chap-builders-commands"
|
|
>Not Writing a Builder: the <CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> Builder</A
|
|
></DT
|
|
><DT
|
|
>21. <A
|
|
HREF="#chap-add-method"
|
|
>Pseudo-Builders: the AddMethod function</A
|
|
></DT
|
|
><DT
|
|
>22. <A
|
|
HREF="#chap-scanners"
|
|
>Writing Scanners</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>22.1. <A
|
|
HREF="#AEN3743"
|
|
>A Simple Scanner Example</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>23. <A
|
|
HREF="#chap-repositories"
|
|
>Building From Code Repositories</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>23.1. <A
|
|
HREF="#AEN3794"
|
|
>The <CODE
|
|
CLASS="function"
|
|
>Repository</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>23.2. <A
|
|
HREF="#AEN3805"
|
|
>Finding source files in repositories</A
|
|
></DT
|
|
><DT
|
|
>23.3. <A
|
|
HREF="#AEN3837"
|
|
>Finding <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files in repositories</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>23.3.1. <A
|
|
HREF="#AEN3878"
|
|
>Limitations on <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files in repositories</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>23.4. <A
|
|
HREF="#AEN3919"
|
|
>Finding the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file in repositories</A
|
|
></DT
|
|
><DT
|
|
>23.5. <A
|
|
HREF="#AEN3937"
|
|
>Finding derived files in repositories</A
|
|
></DT
|
|
><DT
|
|
>23.6. <A
|
|
HREF="#AEN3966"
|
|
>Guaranteeing local copies of files</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>24. <A
|
|
HREF="#chap-sconf"
|
|
>Multi-Platform Configuration (<SPAN
|
|
CLASS="application"
|
|
>Autoconf</SPAN
|
|
> Functionality)</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>24.1. <A
|
|
HREF="#AEN4000"
|
|
><TT
|
|
CLASS="literal"
|
|
>Configure Contexts</TT
|
|
></A
|
|
></DT
|
|
><DT
|
|
>24.2. <A
|
|
HREF="#AEN4016"
|
|
>Checking for the Existence of Header Files</A
|
|
></DT
|
|
><DT
|
|
>24.3. <A
|
|
HREF="#AEN4025"
|
|
>Checking for the Availability of a Function</A
|
|
></DT
|
|
><DT
|
|
>24.4. <A
|
|
HREF="#AEN4030"
|
|
>Checking for the Availability of a Library</A
|
|
></DT
|
|
><DT
|
|
>24.5. <A
|
|
HREF="#AEN4045"
|
|
>Checking for the Availability of a <TT
|
|
CLASS="literal"
|
|
>typedef</TT
|
|
></A
|
|
></DT
|
|
><DT
|
|
>24.6. <A
|
|
HREF="#AEN4056"
|
|
>Adding Your Own Custom Checks</A
|
|
></DT
|
|
><DT
|
|
>24.7. <A
|
|
HREF="#AEN4085"
|
|
>Not Configuring When Cleaning Targets</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>25. <A
|
|
HREF="#chap-caching"
|
|
>Caching Built Files</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>25.1. <A
|
|
HREF="#AEN4101"
|
|
>Specifying the Shared Cache Directory</A
|
|
></DT
|
|
><DT
|
|
>25.2. <A
|
|
HREF="#AEN4123"
|
|
>Keeping Build Output Consistent</A
|
|
></DT
|
|
><DT
|
|
>25.3. <A
|
|
HREF="#AEN4137"
|
|
>Not Using the Shared Cache for Specific Files</A
|
|
></DT
|
|
><DT
|
|
>25.4. <A
|
|
HREF="#AEN4148"
|
|
>Disabling the Shared Cache</A
|
|
></DT
|
|
><DT
|
|
>25.5. <A
|
|
HREF="#AEN4160"
|
|
>Populating a Shared Cache With Already-Built Files</A
|
|
></DT
|
|
><DT
|
|
>25.6. <A
|
|
HREF="#AEN4177"
|
|
>Minimizing Cache Contention: the <TT
|
|
CLASS="literal"
|
|
>--random</TT
|
|
> Option</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>26. <A
|
|
HREF="#chap-alias"
|
|
>Alias Targets</A
|
|
></DT
|
|
><DT
|
|
>27. <A
|
|
HREF="#chap-java"
|
|
>Java Builds</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>27.1. <A
|
|
HREF="#AEN4237"
|
|
>Building Java Class Files: the <CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
> Builder</A
|
|
></DT
|
|
><DT
|
|
>27.2. <A
|
|
HREF="#AEN4261"
|
|
>How <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Handles Java Dependencies</A
|
|
></DT
|
|
><DT
|
|
>27.3. <A
|
|
HREF="#AEN4288"
|
|
>Building Java Archive (<TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
>) Files: the <CODE
|
|
CLASS="function"
|
|
>Jar</CODE
|
|
> Builder</A
|
|
></DT
|
|
><DT
|
|
>27.4. <A
|
|
HREF="#AEN4319"
|
|
>Building C Header and Stub Files: the <CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
> Builder</A
|
|
></DT
|
|
><DT
|
|
>27.5. <A
|
|
HREF="#AEN4373"
|
|
>Building RMI Stub and Skeleton Class Files: the <CODE
|
|
CLASS="function"
|
|
>RMIC</CODE
|
|
> Builder</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>28. <A
|
|
HREF="#chap-misc"
|
|
>Miscellaneous Functionality</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>28.1. <A
|
|
HREF="#AEN4401"
|
|
>Verifying the Python Version: the <CODE
|
|
CLASS="function"
|
|
>EnsurePythonVersion</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>28.2. <A
|
|
HREF="#AEN4417"
|
|
>Verifying the SCons Version: the <CODE
|
|
CLASS="function"
|
|
>EnsureSConsVersion</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>28.3. <A
|
|
HREF="#AEN4437"
|
|
>Explicitly Terminating <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> While Reading <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files: the <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>28.4. <A
|
|
HREF="#AEN4461"
|
|
>Searching for Files: the <CODE
|
|
CLASS="function"
|
|
>FindFile</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>28.5. <A
|
|
HREF="#AEN4490"
|
|
>Handling Nested Lists: the <CODE
|
|
CLASS="function"
|
|
>Flatten</CODE
|
|
> Function</A
|
|
></DT
|
|
><DT
|
|
>28.6. <A
|
|
HREF="#AEN4517"
|
|
>Finding the Invocation Directory: the <CODE
|
|
CLASS="function"
|
|
>GetLaunchDir</CODE
|
|
> Function</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>29. <A
|
|
HREF="#chap-troubleshooting"
|
|
>Troubleshooting</A
|
|
></DT
|
|
><DD
|
|
><DL
|
|
><DT
|
|
>29.1. <A
|
|
HREF="#AEN4543"
|
|
>Why is That Target Being Rebuilt? the <TT
|
|
CLASS="literal"
|
|
>--debug=explain</TT
|
|
> Option</A
|
|
></DT
|
|
><DT
|
|
>29.2. <A
|
|
HREF="#AEN4593"
|
|
>What's in That Construction Environment? the <CODE
|
|
CLASS="function"
|
|
>Dump</CODE
|
|
> Method</A
|
|
></DT
|
|
><DT
|
|
>29.3. <A
|
|
HREF="#AEN4619"
|
|
>What Dependencies Does <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Know About? the <TT
|
|
CLASS="literal"
|
|
>--tree</TT
|
|
> Option</A
|
|
></DT
|
|
><DT
|
|
>29.4. <A
|
|
HREF="#AEN4689"
|
|
>How is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Constructing the Command Lines It Executes? the <TT
|
|
CLASS="literal"
|
|
>--debug=presub</TT
|
|
> Option</A
|
|
></DT
|
|
><DT
|
|
>29.5. <A
|
|
HREF="#AEN4698"
|
|
>Where is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Searching for Libraries? the <TT
|
|
CLASS="literal"
|
|
>--debug=findlibs</TT
|
|
> Option</A
|
|
></DT
|
|
><DT
|
|
>29.6. <A
|
|
HREF="#AEN4715"
|
|
>Where is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Blowing Up? the <TT
|
|
CLASS="literal"
|
|
>--debug=stacktrace</TT
|
|
> Option</A
|
|
></DT
|
|
><DT
|
|
>29.7. <A
|
|
HREF="#AEN4736"
|
|
>How is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Making Its Decisions? the <TT
|
|
CLASS="literal"
|
|
>--taskmastertrace</TT
|
|
> Option</A
|
|
></DT
|
|
></DL
|
|
></DD
|
|
><DT
|
|
>A. <A
|
|
HREF="#app-variables"
|
|
>Construction Variables</A
|
|
></DT
|
|
><DT
|
|
>B. <A
|
|
HREF="#app-builders"
|
|
>Builders</A
|
|
></DT
|
|
><DT
|
|
>C. <A
|
|
HREF="#app-tools"
|
|
>Tools</A
|
|
></DT
|
|
><DT
|
|
>D. <A
|
|
HREF="#app-tasks"
|
|
>Handling Common Tasks</A
|
|
></DT
|
|
></DL
|
|
></DIV
|
|
><DIV
|
|
CLASS="LOT"
|
|
><DL
|
|
CLASS="LOT"
|
|
><DT
|
|
><B
|
|
>List of Examples</B
|
|
></DT
|
|
><DT
|
|
>D-1. <A
|
|
HREF="#AEN10745"
|
|
>Wildcard globbing to create a list of filenames</A
|
|
></DT
|
|
><DT
|
|
>D-2. <A
|
|
HREF="#AEN10748"
|
|
>Filename extension substitution</A
|
|
></DT
|
|
><DT
|
|
>D-3. <A
|
|
HREF="#AEN10751"
|
|
>Appending a path prefix to a list of filenames</A
|
|
></DT
|
|
><DT
|
|
>D-4. <A
|
|
HREF="#AEN10756"
|
|
>Substituting a path prefix with another one</A
|
|
></DT
|
|
><DT
|
|
>D-5. <A
|
|
HREF="#AEN10761"
|
|
>Filtering a filename list to exclude/retain only a specific set
|
|
of extensions</A
|
|
></DT
|
|
><DT
|
|
>D-6. <A
|
|
HREF="#AEN10766"
|
|
>The "backtick function": run a shell command and capture the
|
|
output</A
|
|
></DT
|
|
></DL
|
|
></DIV
|
|
><DIV
|
|
CLASS="preface"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-preface"
|
|
></A
|
|
>Preface</H1
|
|
><P
|
|
>
|
|
Thank you for taking the time to read about <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is a next-generation
|
|
software construction tool,
|
|
or make tool--that is, a software utility
|
|
for building software (or other files)
|
|
and keeping built software up-to-date
|
|
whenever the underlying input files change.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The most distinctive thing about <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
is that its configuration files are
|
|
actually <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>scripts</I
|
|
></SPAN
|
|
>,
|
|
written in the <SPAN
|
|
CLASS="application"
|
|
>Python</SPAN
|
|
> programming language.
|
|
This is in contrast to most alternative build tools,
|
|
which typically invent a new language to
|
|
configure the build.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> still has a learning curve, of course,
|
|
because you have to know what functions to call
|
|
to set up your build properly,
|
|
but the underlying syntax used should be familiar
|
|
to anyone who has ever looked at a Python script.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Paradoxically,
|
|
using Python as the configuration file format
|
|
makes <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>easier</I
|
|
></SPAN
|
|
>
|
|
for non-programmers to learn
|
|
than the cryptic languages of other build tools,
|
|
which are usually invented by programmers for other programmers.
|
|
This is in no small part due to the
|
|
consistency and readability that are built in to Python.
|
|
It just so happens that making a real, live
|
|
scripting language the basis for the
|
|
configuration files
|
|
makes it a snap for more accomplished programmers
|
|
to do more complicated things with builds,
|
|
as necessary.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN29"
|
|
>1. <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Principles</A
|
|
></H2
|
|
><P
|
|
>
|
|
There are a few overriding principles
|
|
we try to live up to in designing and implementing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>:
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
>Correctness</DT
|
|
><DD
|
|
><P
|
|
>
|
|
First and foremost,
|
|
by default, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> guarantees a correct build
|
|
even if it means sacrificing performance a little.
|
|
We strive to guarantee the build is correct
|
|
regardless of how the software being built is structured,
|
|
how it may have been written,
|
|
or how unusual the tools are that build it.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>Performance</DT
|
|
><DD
|
|
><P
|
|
>
|
|
Given that the build is correct,
|
|
we try to make <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> build software
|
|
as quickly as possible.
|
|
In particular, wherever we may have needed to slow
|
|
down the default <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> behavior to guarantee a correct build,
|
|
we also try to make it easy to speed up <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
through optimization options that let you trade off
|
|
guaranteed correctness in all end cases for
|
|
a speedier build in the usual cases.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>Convenience</DT
|
|
><DD
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> tries to do as much for you out of the box as reasonable,
|
|
including detecting the right tools on your system
|
|
and using them correctly to build the software.
|
|
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
><P
|
|
>
|
|
In a nutshell, we try hard to make <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> just
|
|
"do the right thing" and build software correctly,
|
|
with a minimum of hassles.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN54"
|
|
>2. A Caveat About This Guide's Completeness</A
|
|
></H2
|
|
><P
|
|
>
|
|
One word of warning as you read through this Guide:
|
|
Like too much Open Source software out there,
|
|
the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> documentation isn't always
|
|
kept up-to-date with the available features.
|
|
In other words,
|
|
there's a lot that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> can do that
|
|
isn't yet covered in this User's Guide.
|
|
(Come to think of it,
|
|
that also describes a lot of proprietary software, doesn't it?)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Although this User's Guide isn't as complete as we'd like it to be,
|
|
our development process does emphasize
|
|
making sure that the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> man page is kept up-to-date
|
|
with new features.
|
|
So if you're trying to figure out how to do something
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports
|
|
but can't find enough (or any) information here,
|
|
it would be worth your while to look
|
|
at the man page to see if the information is covered there.
|
|
And if you do,
|
|
maybe you'd even consider contributing
|
|
a section to the User's Guide
|
|
so the next person looking for
|
|
that information won't have to
|
|
go through the same thing...?
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN62"
|
|
>3. Acknowledgements</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> would not exist without a lot of help
|
|
from a lot of people,
|
|
many of whom may not even be aware
|
|
that they helped or served as inspiration.
|
|
So in no particular order,
|
|
and at the risk of leaving out someone:
|
|
|
|
</P
|
|
><P
|
|
>
|
|
First and foremost,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> owes a tremendous debt to Bob Sidebotham,
|
|
the original author of the classic Perl-based <SPAN
|
|
CLASS="application"
|
|
>Cons</SPAN
|
|
> tool
|
|
which Bob first released to the world back around 1996.
|
|
Bob's work on Cons classic provided the underlying architecture
|
|
and model of specifying a build configuration
|
|
using a real scripting language.
|
|
My real-world experience working on Cons
|
|
informed many of the design decisions in SCons,
|
|
including the improved parallel build support,
|
|
making Builder objects easily definable by users,
|
|
and separating the build engine from the wrapping interface.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Greg Wilson was instrumental in getting
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> started as a real project
|
|
when he initiated the Software Carpentry design
|
|
competition in February 2000.
|
|
Without that nudge,
|
|
marrying the advantages of the Cons classic
|
|
architecture with the readability of Python
|
|
might have just stayed no more than a nice idea.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The entire <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> team have been
|
|
absolutely wonderful to work with,
|
|
and <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> would be nowhere near as useful a
|
|
tool without the energy, enthusiasm
|
|
and time people have contributed over the past few years.
|
|
The "core team"
|
|
of Chad Austin, Anthony Roach,
|
|
Bill Deegan, Charles Crain, Steve Leblanc, Greg Noel,
|
|
Gary Oberbrunner, Greg Spencer and Christoph Wiedemann
|
|
have been great about reviewing my (and other) changes
|
|
and catching problems before they get in the code base.
|
|
Of particular technical note:
|
|
Anthony's outstanding and innovative work on the tasking engine
|
|
has given <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> a vastly superior parallel build model;
|
|
Charles has been the master of the crucial Node infrastructure;
|
|
Christoph's work on the Configure infrastructure
|
|
has added crucial Autoconf-like functionality;
|
|
and Greg has provided excellent support
|
|
for Microsoft Visual Studio.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Special thanks to David Snopek for contributing
|
|
his underlying "Autoscons" code that formed
|
|
the basis of Christoph's work with the Configure functionality.
|
|
David was extremely generous in making
|
|
this code available to <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
given that he initially released it under the GPL
|
|
and <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is released under a less-restrictive MIT-style license.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Thanks to Peter Miller
|
|
for his splendid change management system, <SPAN
|
|
CLASS="application"
|
|
>Aegis</SPAN
|
|
>,
|
|
which has provided the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> project
|
|
with a robust development methodology from day one,
|
|
and which showed me how you could
|
|
integrate incremental regression tests into
|
|
a practical development cycle
|
|
(years before eXtreme Programming arrived on the scene).
|
|
|
|
</P
|
|
><P
|
|
>
|
|
And last, thanks to Guido van Rossum
|
|
for his elegant scripting language,
|
|
which is the basis not only for the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> implementation,
|
|
but for the interface itself.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN83"
|
|
>4. Contact</A
|
|
></H2
|
|
><P
|
|
>
|
|
The best way to contact people involved with SCons,
|
|
including the author,
|
|
is through the SCons mailing lists.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you want to ask general questions about how to use <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
send email to <TT
|
|
CLASS="literal"
|
|
>users@scons.tigris.org</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you want to contact the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> development community directly,
|
|
send email to <TT
|
|
CLASS="literal"
|
|
>dev@scons.tigris.org</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you want to receive announcements about <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
join the low-volume <TT
|
|
CLASS="literal"
|
|
>announce@scons.tigris.org</TT
|
|
> mailing list.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-build-install"
|
|
></A
|
|
>Chapter 1. Building and Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
></H1
|
|
><P
|
|
>
|
|
This chapter will take you through the basic steps
|
|
of installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on your system,
|
|
and building <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> if you don't have a
|
|
pre-built package available
|
|
(or simply prefer the flexibility of building it yourself).
|
|
Before that, however, this chapter will also describe the basic steps
|
|
involved in installing Python on your system,
|
|
in case that is necessary.
|
|
Fortunately, both <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> and Python
|
|
are very easy to install on almost any system,
|
|
and Python already comes installed on many systems.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN102"
|
|
>1.1. Installing Python</A
|
|
></H2
|
|
><P
|
|
>
|
|
Because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is written in Python,
|
|
you must obviously have Python installed on your system
|
|
to use <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
Before you try to install Python,
|
|
you should check to see if Python is already
|
|
available on your system by typing
|
|
<KBD
|
|
CLASS="userinput"
|
|
>python -V</KBD
|
|
>
|
|
(capital 'V')
|
|
or
|
|
<KBD
|
|
CLASS="userinput"
|
|
>python --version</KBD
|
|
>
|
|
at your system's command-line prompt.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> $ <KBD
|
|
CLASS="userinput"
|
|
>python -V</KBD
|
|
>
|
|
Python 2.5.1
|
|
</PRE
|
|
><P
|
|
>
|
|
And on a Windows system with Python installed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>python -V</KBD
|
|
>
|
|
Python 2.5.1
|
|
</PRE
|
|
><P
|
|
>
|
|
If Python is not installed on your system,
|
|
you will see an error message
|
|
stating something like "command not found"
|
|
(on UNIX or Linux)
|
|
or "'python' is not recognized
|
|
as an internal or external command, operable progam or batch file"
|
|
(on Windows).
|
|
In that case, you need to install Python
|
|
before you can install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
(Note that the <CODE
|
|
CLASS="option"
|
|
>-V</CODE
|
|
> option
|
|
was added to Python version 2.0,
|
|
so if your system only has an earlier version available
|
|
you may see an
|
|
<TT
|
|
CLASS="literal"
|
|
>"Unknown option: -V"</TT
|
|
>
|
|
error message.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The standard location for information
|
|
about downloading and installing Python is
|
|
<A
|
|
HREF="http://www.python.org/download/"
|
|
TARGET="_top"
|
|
>http://www.python.org/download/</A
|
|
>.
|
|
See that page for information about
|
|
how to download and install Python on your system.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will work with any version of Python from 1.5.2 or later.
|
|
If you need to install Python and have a choice,
|
|
we recommend using the most recent Python 2.5 version available.
|
|
Python 2.5 has significant improvements
|
|
the help speed up the performance of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>'.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN124"
|
|
>1.2. Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> From Pre-Built Packages</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> comes pre-packaged for installation on a number of systems,
|
|
including Linux and Windows systems.
|
|
You do not need to read this entire section,
|
|
you should only need to read the section
|
|
appropriate to the type of system you're running on.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN129"
|
|
>1.2.1. Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Red Hat (and Other RPM-based) Linux Systems</A
|
|
></H3
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> comes in RPM (Red Hat Package Manager) format,
|
|
pre-built and ready to install on Red Hat Linux,
|
|
Fedora Core,
|
|
or any other Linux distribution that uses RPM.
|
|
Your distribution may
|
|
already have an <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> RPM built specifically for it;
|
|
many do, including SuSe, Mandrake and Fedora.
|
|
You can check for the availability of an <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> RPM
|
|
on your distribution's download servers,
|
|
or by consulting an RPM search site like
|
|
<A
|
|
HREF="http://www.rpmfind.net/"
|
|
TARGET="_top"
|
|
>http://www.rpmfind.net/</A
|
|
> or
|
|
<A
|
|
HREF="http://rpm.pbone.net/"
|
|
TARGET="_top"
|
|
>http://rpm.pbone.net/</A
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If your Linux distribution does not already have
|
|
a specific <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> RPM file,
|
|
you can download and install from the
|
|
generic RPM provided by the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> project.
|
|
This will install the
|
|
SCons script(s) in <TT
|
|
CLASS="filename"
|
|
>/usr/bin</TT
|
|
>,
|
|
and the SCons library modules in
|
|
<TT
|
|
CLASS="filename"
|
|
>/usr/lib/scons</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
To install from the command line, simply download the
|
|
appropriate <TT
|
|
CLASS="filename"
|
|
>.rpm</TT
|
|
> file,
|
|
and then run:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> # <KBD
|
|
CLASS="userinput"
|
|
>rpm -Uvh scons-0.96-1.noarch.rpm</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
Or, you can use a graphical RPM package manager
|
|
like <SPAN
|
|
CLASS="application"
|
|
>gnorpm</SPAN
|
|
>.
|
|
See your package manager application's documention
|
|
for specific instructions about
|
|
how to use it to install a downloaded RPM.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN149"
|
|
>1.2.2. Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Debian Linux Systems</A
|
|
></H3
|
|
><P
|
|
>
|
|
Debian Linux systems use a different package management
|
|
format that also makes it very easy to install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If your system is connected to the Internet,
|
|
you can install the latest official Debian package
|
|
by running:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> # <KBD
|
|
CLASS="userinput"
|
|
>apt-get install scons</KBD
|
|
>
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN157"
|
|
>1.2.3. Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Windows Systems</A
|
|
></H3
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a Windows installer
|
|
that makes installation extremely easy.
|
|
Download the <TT
|
|
CLASS="filename"
|
|
>scons-0.95.win32.exe</TT
|
|
>
|
|
file from the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> download page at
|
|
<A
|
|
HREF="http://www.scons.org/download.html"
|
|
TARGET="_top"
|
|
>http://www.scons.org/download.html</A
|
|
>.
|
|
Then all you need to do is execute the file
|
|
(usually by clicking on its icon in Windows Explorer).
|
|
These will take you through a small
|
|
sequence of windows that will install
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on your system.
|
|
|
|
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN166"
|
|
>1.3. Building and Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> on Any System</A
|
|
></H2
|
|
><P
|
|
>
|
|
If a pre-built <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> package is not available for your system,
|
|
then you can still easily build and install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> using the native
|
|
Python <TT
|
|
CLASS="filename"
|
|
>distutils</TT
|
|
> package.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The first step is to download either the
|
|
<TT
|
|
CLASS="filename"
|
|
>scons-1.0.1.tar.gz</TT
|
|
>
|
|
or <TT
|
|
CLASS="filename"
|
|
>scons-1.0.1.zip</TT
|
|
>,
|
|
which are available from the SCons download page at
|
|
<A
|
|
HREF="http://www.scons.org/download.html"
|
|
TARGET="_top"
|
|
>http://www.scons.org/download.html</A
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Unpack the archive you downloaded,
|
|
using a utility like <SPAN
|
|
CLASS="application"
|
|
>tar</SPAN
|
|
>
|
|
on Linux or UNIX,
|
|
or <SPAN
|
|
CLASS="application"
|
|
>WinZip</SPAN
|
|
> on Windows.
|
|
This will create a directory called
|
|
<TT
|
|
CLASS="filename"
|
|
>scons-1.0.1</TT
|
|
>,
|
|
usually in your local directory.
|
|
Then change your working directory to that directory
|
|
and install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> by executing the following commands:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> # <KBD
|
|
CLASS="userinput"
|
|
>cd scons-1.0.1</KBD
|
|
>
|
|
# <KBD
|
|
CLASS="userinput"
|
|
>python setup.py install</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
This will build <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
install the <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> script
|
|
in the default system scripts directory
|
|
(<TT
|
|
CLASS="filename"
|
|
>/usr/local/bin</TT
|
|
> or
|
|
<TT
|
|
CLASS="filename"
|
|
>C:\Python25\Scripts</TT
|
|
>),
|
|
and will install the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> build engine
|
|
in an appropriate stand-alone library directory
|
|
(<TT
|
|
CLASS="filename"
|
|
>/usr/local/lib/scons</TT
|
|
> or
|
|
<TT
|
|
CLASS="filename"
|
|
>C:\Python25\scons</TT
|
|
>).
|
|
Because these are system directories,
|
|
you may need root (on Linux or UNIX) or Administrator (on Windows)
|
|
privileges to install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> like this.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN194"
|
|
>1.3.1. Building and Installing Multiple Versions of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Side-by-Side</A
|
|
></H3
|
|
><P
|
|
>
|
|
The <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> <TT
|
|
CLASS="filename"
|
|
>setup.py</TT
|
|
> script
|
|
has some extensions that support
|
|
easy installation of multiple versions of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
in side-by-side locations.
|
|
This makes it easier to download and
|
|
experiment with different versions of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
before moving your official build process to a new version,
|
|
for example.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
To install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in a version-specific location,
|
|
add the <CODE
|
|
CLASS="option"
|
|
>--version-lib</CODE
|
|
> option
|
|
when you call <TT
|
|
CLASS="filename"
|
|
>setup.py</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> # <KBD
|
|
CLASS="userinput"
|
|
>python setup.py install --version-lib</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
This will install the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> build engine
|
|
in the
|
|
<TT
|
|
CLASS="filename"
|
|
>/usr/lib/scons-1.0.1</TT
|
|
>
|
|
or
|
|
<TT
|
|
CLASS="filename"
|
|
>C:\Python25\scons-1.0.1</TT
|
|
>
|
|
directory, for example.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you use the <CODE
|
|
CLASS="option"
|
|
>--version-lib</CODE
|
|
> option
|
|
the first time you install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
you do not need to specify it each time you install
|
|
a new version.
|
|
The <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> <TT
|
|
CLASS="filename"
|
|
>setup.py</TT
|
|
> script
|
|
will detect the version-specific directory name(s)
|
|
and assume you want to install all versions
|
|
in version-specific directories.
|
|
You can override that assumption in the future
|
|
by explicitly specifying the <CODE
|
|
CLASS="option"
|
|
>--standalone-lib</CODE
|
|
> option.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN218"
|
|
>1.3.2. Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in Other Locations</A
|
|
></H3
|
|
><P
|
|
>
|
|
You can install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in locations other than
|
|
the default by specifying the <CODE
|
|
CLASS="option"
|
|
>--prefix=</CODE
|
|
> option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> # <KBD
|
|
CLASS="userinput"
|
|
>python setup.py install --prefix=/opt/scons</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
This would
|
|
install the <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> script in
|
|
<TT
|
|
CLASS="filename"
|
|
>/opt/scons/bin</TT
|
|
>
|
|
and the build engine in
|
|
<TT
|
|
CLASS="filename"
|
|
>/opt/scons/lib/scons</TT
|
|
>,
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that you can specify both the <CODE
|
|
CLASS="option"
|
|
>--prefix=</CODE
|
|
>
|
|
and the <CODE
|
|
CLASS="option"
|
|
>--version-lib</CODE
|
|
> options
|
|
at the same type,
|
|
in which case <TT
|
|
CLASS="filename"
|
|
>setup.py</TT
|
|
>
|
|
will install the build engine
|
|
in a version-specific directory
|
|
relative to the specified prefix.
|
|
Adding <CODE
|
|
CLASS="option"
|
|
>--version-lib</CODE
|
|
> to the
|
|
above example would install the build engine in
|
|
<TT
|
|
CLASS="filename"
|
|
>/opt/scons/lib/scons-1.0.1</TT
|
|
>.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN236"
|
|
>1.3.3. Building and Installing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Without Administrative Privileges</A
|
|
></H3
|
|
><P
|
|
>
|
|
If you don't have the right privileges to install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
in a system location,
|
|
simply use the <TT
|
|
CLASS="literal"
|
|
>--prefix=</TT
|
|
> option
|
|
to install it in a location of your choosing.
|
|
For example,
|
|
to install <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in appropriate locations
|
|
relative to the user's <TT
|
|
CLASS="literal"
|
|
>$HOME</TT
|
|
> directory,
|
|
the <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> script in
|
|
<TT
|
|
CLASS="filename"
|
|
>$HOME/bin</TT
|
|
>
|
|
and the build engine in
|
|
<TT
|
|
CLASS="filename"
|
|
>$HOME/lib/scons</TT
|
|
>,
|
|
simply type:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> $ <KBD
|
|
CLASS="userinput"
|
|
>python setup.py install --prefix=$HOME</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
You may, of course, specify any other location you prefer,
|
|
and may use the <CODE
|
|
CLASS="option"
|
|
>--version-lib</CODE
|
|
> option
|
|
if you would like to install version-specific directories
|
|
relative to the specified prefix.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-simple"
|
|
></A
|
|
>Chapter 2. Simple Builds</H1
|
|
><P
|
|
>
|
|
In this chapter,
|
|
you will see several examples of
|
|
very simple build configurations using <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
which will demonstrate how easy
|
|
it is to use <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to
|
|
build programs from several different programming languages
|
|
on different types of systems.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN256"
|
|
>2.1. Building Simple C / C++ Programs</A
|
|
></H2
|
|
><P
|
|
>
|
|
Here's the famous "Hello, World!" program in C:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> int
|
|
main()
|
|
{
|
|
printf("Hello, world!\n");
|
|
}
|
|
</PRE
|
|
><P
|
|
>
|
|
And here's how to build it using <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
Enter the following into a file named <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
This minimal configuration file gives
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> two pieces of information:
|
|
what you want to build
|
|
(an executable program),
|
|
and the input file from
|
|
which you want it built
|
|
(the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file).
|
|
<A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
> is a <I
|
|
CLASS="firstterm"
|
|
>builder_method</I
|
|
>,
|
|
a Python call that tells <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> that you want to build an
|
|
executable program.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
That's it. Now run the <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> command to build the program.
|
|
On a POSIX-compliant system like Linux or UNIX,
|
|
you'll see something like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
On a Windows system with the Microsoft Visual C++ compiler,
|
|
you'll see something like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cl /nologo /c hello.c /Fohello.obj
|
|
link /nologo /OUT:hello.exe hello.obj
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
First, notice that you only need
|
|
to specify the name of the source file,
|
|
and that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> correctly deduces the names of
|
|
the object and executable files to be built
|
|
from the base of the source file name.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Second, notice that the same input <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file,
|
|
without any changes,
|
|
generates the correct output file names on both systems:
|
|
<TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>hello</TT
|
|
>
|
|
on POSIX systems,
|
|
<TT
|
|
CLASS="filename"
|
|
>hello.obj</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>hello.exe</TT
|
|
>
|
|
on Windows systems.
|
|
This is a simple example of how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
makes it extremely easy to
|
|
write portable software builds.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
(Note that we won't provide duplicate side-by-side
|
|
POSIX and Windows output for all of the examples in this guide;
|
|
just keep in mind that, unless otherwise specified,
|
|
any of the examples should work equally well on both types of systems.)
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN288"
|
|
>2.2. Building Object Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
The <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
> builder method is only one of
|
|
many builder methods that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides
|
|
to build different types of files.
|
|
Another is the <A
|
|
HREF="#b-Object"
|
|
><CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
></A
|
|
> builder method,
|
|
which tells <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to build an object file
|
|
from the specified source file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Object('hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Now when you run the <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> command to build the program,
|
|
it will build just the <TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
> object file on a POSIX system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cc -o hello.o -c hello.c
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
And just the <TT
|
|
CLASS="filename"
|
|
>hello.obj</TT
|
|
> object file
|
|
on a Windows system (with the Microsoft Visual C++ compiler):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cl /nologo /c hello.c /Fohello.obj
|
|
scons: done building targets.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN307"
|
|
>2.3. Simple Java Builds</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> also makes building with Java extremely easy.
|
|
Unlike the <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#b-Object"
|
|
><CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
></A
|
|
> builder methods,
|
|
however, the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> builder method
|
|
requires that you specify
|
|
the name of a destination directory in which
|
|
you want the class files placed,
|
|
followed by the source directory
|
|
in which the <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files live:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Java('classes', 'src')
|
|
</PRE
|
|
><P
|
|
>
|
|
If the <TT
|
|
CLASS="filename"
|
|
>src</TT
|
|
> directory
|
|
contains a single <TT
|
|
CLASS="filename"
|
|
>hello.java</TT
|
|
> file,
|
|
then the output from running the <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> command
|
|
would look something like this
|
|
(on a POSIX system):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
javac -d classes -sourcepath src src/hello.java
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
We'll cover Java builds in more detail,
|
|
including building Java archive (<TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
>)
|
|
and other types of file,
|
|
in <A
|
|
HREF="#chap-java"
|
|
>Chapter 27</A
|
|
>.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN328"
|
|
>2.4. Cleaning Up After a Build</A
|
|
></H2
|
|
><P
|
|
>
|
|
When using <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>, it is unnecessary to add special
|
|
commands or target names to clean up after a build.
|
|
Instead, you simply use the
|
|
<TT
|
|
CLASS="literal"
|
|
>-c</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>--clean</TT
|
|
>
|
|
option when you invoke <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
and <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> removes the appropriate built files.
|
|
So if we build our example above
|
|
and then invoke <TT
|
|
CLASS="literal"
|
|
>scons -c</TT
|
|
>
|
|
afterwards, the output on POSIX looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
scons: done building targets.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -c</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Cleaning targets ...
|
|
Removed hello.o
|
|
Removed hello
|
|
scons: done cleaning targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
And the output on Windows looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cl /nologo /c hello.c /Fohello.obj
|
|
link /nologo /OUT:hello.exe hello.obj
|
|
scons: done building targets.
|
|
C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -c</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Cleaning targets ...
|
|
Removed hello.obj
|
|
Removed hello.exe
|
|
scons: done cleaning targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> changes its output to tell you that it
|
|
is <TT
|
|
CLASS="literal"
|
|
>Cleaning targets ...</TT
|
|
> and
|
|
<TT
|
|
CLASS="literal"
|
|
>done cleaning targets.</TT
|
|
>
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN348"
|
|
>2.5. The <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> File</A
|
|
></H2
|
|
><P
|
|
>
|
|
If you're used to build systems like <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>
|
|
you've already figured out that the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
is the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> equivalent of a <TT
|
|
CLASS="filename"
|
|
>Makefile</TT
|
|
>.
|
|
That is, the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file is the input file
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> reads to control the build.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN358"
|
|
>2.5.1. <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> Files Are Python Scripts</A
|
|
></H3
|
|
><P
|
|
>
|
|
There is, however, an important difference between
|
|
an <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file and a <TT
|
|
CLASS="filename"
|
|
>Makefile</TT
|
|
>:
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file is actually a Python script.
|
|
If you're not already familiar with Python, don't worry.
|
|
This User's Guide will introduce you step-by-step
|
|
to the relatively small amount of Python you'll
|
|
need to know to be able to use <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> effectively.
|
|
And Python is very easy to learn.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One aspect of using Python as the
|
|
scripting language is that you can put comments
|
|
in your <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file using Python's commenting convention;
|
|
that is, everything between a '#' and the end of the line
|
|
will be ignored:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Arrange to build the "hello" program.
|
|
Program('hello.c') # "hello.c" is the source file.
|
|
</PRE
|
|
><P
|
|
>
|
|
You'll see throughout the remainder of this Guide
|
|
that being able to use the power of a
|
|
real scripting language
|
|
can greatly simplify the solutions
|
|
to complex requirements of real-world builds.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN370"
|
|
>2.5.2. <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Functions Are Order-Independent</A
|
|
></H3
|
|
><P
|
|
>
|
|
One important way in which the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
>
|
|
file is not exactly like a normal Python script,
|
|
and is more like a <TT
|
|
CLASS="filename"
|
|
>Makefile</TT
|
|
>,
|
|
is that the order in which
|
|
the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> functions are called in
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
does <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
affect the order in which <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
actually builds the programs and object files
|
|
you want it to build.<A
|
|
NAME="AEN380"
|
|
HREF="#FTN.AEN380"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[1]</SPAN
|
|
></A
|
|
>
|
|
In other words, when you call the <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
> builder
|
|
(or any other builder method),
|
|
you're not telling <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to build
|
|
the program at the instant the builder method is called.
|
|
Instead, you're telling <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to build the program
|
|
that you want, for example,
|
|
a program built from a file named <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
>,
|
|
and it's up to <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to build that program
|
|
(and any other files) whenever it's necessary.
|
|
(We'll learn more about how
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> decides when building or rebuilding a file
|
|
is necessary in <A
|
|
HREF="#chap-depends"
|
|
>Chapter 6</A
|
|
>, below.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> reflects this distinction between
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>calling a builder method like</I
|
|
></SPAN
|
|
> <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
>>
|
|
and <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>actually building the program</I
|
|
></SPAN
|
|
>
|
|
by printing the status messages that indicate
|
|
when it's "just reading" the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file,
|
|
and when it's actually building the target files.
|
|
This is to make it clear when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is
|
|
executing the Python statements that make up the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file,
|
|
and when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is actually executing the
|
|
commands or other actions to
|
|
build the necessary files.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Let's clarify this with an example.
|
|
Python has a <TT
|
|
CLASS="literal"
|
|
>print</TT
|
|
> statement that
|
|
prints a string of characters to the screen.
|
|
If we put <TT
|
|
CLASS="literal"
|
|
>print</TT
|
|
> statements around
|
|
our calls to the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> builder method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> print "Calling Program('hello.c')"
|
|
Program('hello.c')
|
|
print "Calling Program('goodbye.c')"
|
|
Program('goodbye.c')
|
|
print "Finished calling Program()"
|
|
</PRE
|
|
><P
|
|
>
|
|
Then when we execute <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
we see the output from the <TT
|
|
CLASS="literal"
|
|
>print</TT
|
|
>
|
|
statements in between the messages about
|
|
reading the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
indicating that that is when the
|
|
Python statements are being executed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
Calling Program('hello.c')
|
|
Calling Program('goodbye.c')
|
|
Finished calling Program()
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cc -o goodbye.o -c goodbye.c
|
|
cc -o goodbye goodbye.o
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice also that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> built the <SPAN
|
|
CLASS="application"
|
|
>goodbye</SPAN
|
|
> program first,
|
|
even though the "reading <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>" output
|
|
shows that we called <TT
|
|
CLASS="literal"
|
|
>Program('hello.c')</TT
|
|
>
|
|
first in the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN420"
|
|
>2.6. Making the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Output Less Verbose</A
|
|
></H2
|
|
><P
|
|
>
|
|
You've already seen how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> prints
|
|
some messages about what it's doing,
|
|
surrounding the actual commands used to build the software:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cl /nologo /c hello.c /Fohello.obj
|
|
link /nologo /OUT:hello.exe hello.obj
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
These messages emphasize the
|
|
order in which <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does its work:
|
|
all of the configuration files
|
|
(generically referred to as <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files)
|
|
are read and executed first,
|
|
and only then are the target files built.
|
|
Among other benefits, these messages help to distinguish between
|
|
errors that occur while the configuration files are read,
|
|
and errors that occur while targets are being built.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One drawback, of course, is that these messages clutter the output.
|
|
Fortunately, they're easily disabled by using
|
|
the <TT
|
|
CLASS="literal"
|
|
>-Q</TT
|
|
> option when invoking <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl /nologo /c hello.c /Fohello.obj
|
|
link /nologo /OUT:hello.exe hello.obj
|
|
</PRE
|
|
><P
|
|
>
|
|
Because we want this User's Guide to focus
|
|
on what <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is actually doing,
|
|
we're going to use the <TT
|
|
CLASS="literal"
|
|
>-Q</TT
|
|
> option
|
|
to remove these messages from the
|
|
output of all the remaining examples in this Guide.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-less-simple"
|
|
></A
|
|
>Chapter 3. Less Simple Things to Do With Builds</H1
|
|
><P
|
|
>
|
|
In this chapter,
|
|
you will see several examples of
|
|
very simple build configurations using <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
which will demonstrate how easy
|
|
it is to use <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to
|
|
build programs from several different programming languages
|
|
on different types of systems.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN443"
|
|
>3.1. Specifying the Name of the Target (Output) File</A
|
|
></H2
|
|
><P
|
|
>
|
|
You've seen that when you call the <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
> builder method,
|
|
it builds the resulting program with the same
|
|
base name as the source file.
|
|
That is, the following call to build an
|
|
executable program from the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> source file
|
|
will build an executable program named <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> on POSIX systems,
|
|
and an executable program named <TT
|
|
CLASS="filename"
|
|
>hello.exe</TT
|
|
> on Windows systems:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
If you want to build a program with
|
|
a different name than the base of the source file name,
|
|
you simply put the target file name
|
|
to the left of the source file name:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('new_hello', 'hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
(<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> requires the target file name first,
|
|
followed by the source file name,
|
|
so that the order mimics that of an
|
|
assignment statement in most programming languages,
|
|
including Python:
|
|
<TT
|
|
CLASS="literal"
|
|
>"program = source files"</TT
|
|
>.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Now <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will build an executable program
|
|
named <SPAN
|
|
CLASS="application"
|
|
>new_hello</SPAN
|
|
> when run on a POSIX system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o new_hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
And <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will build an executable program
|
|
named <SPAN
|
|
CLASS="application"
|
|
>new_hello.exe</SPAN
|
|
> when run on a Windows system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl /nologo /c hello.c /Fohello.obj
|
|
link /nologo /OUT:new_hello.exe hello.obj
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN467"
|
|
>3.2. Compiling Multiple Source Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
You've just seen how to configure <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
to compile a program from a single source file.
|
|
It's more common, of course,
|
|
that you'll need to build a program from
|
|
many input source files, not just one.
|
|
To do this, you need to put the
|
|
source files in a Python list
|
|
(enclosed in square brackets),
|
|
like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program(['prog.c', 'file1.c', 'file2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
A build of the above example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o file1.o -c file1.c
|
|
cc -o file2.o -c file2.c
|
|
cc -o prog.o -c prog.c
|
|
cc -o prog prog.o file1.o file2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
deduces the output program name
|
|
from the first source file specified
|
|
in the list--that is,
|
|
because the first source file was <TT
|
|
CLASS="filename"
|
|
>prog.c</TT
|
|
>,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will name the resulting program <TT
|
|
CLASS="filename"
|
|
>prog</TT
|
|
>
|
|
(or <TT
|
|
CLASS="filename"
|
|
>prog.exe</TT
|
|
> on a Windows system).
|
|
If you want to specify a different program name,
|
|
then (as we've seen in the previous section)
|
|
you slide the list of source files
|
|
over to the right
|
|
to make room for the output program file name.
|
|
(<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> puts the output file name to the left
|
|
of the source file names
|
|
so that the order mimics that of an
|
|
assignment statement: "program = source files".)
|
|
This makes our example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('program', ['prog.c', 'file1.c', 'file2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
On Linux, a build of this example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o file1.o -c file1.c
|
|
cc -o file2.o -c file2.c
|
|
cc -o prog.o -c prog.c
|
|
cc -o program prog.o file1.o file2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Or on Windows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl /nologo /c file1.c /Fofile1.obj
|
|
cl /nologo /c file2.c /Fofile2.obj
|
|
cl /nologo /c prog.c /Foprog.obj
|
|
link /nologo /OUT:program.exe prog.obj file1.obj file2.obj
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN489"
|
|
>3.3. Making a list of files with <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
></A
|
|
></H2
|
|
><P
|
|
>
|
|
You can also use the <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
> function to find all files matching a
|
|
certain template, using the standard shell pattern matching
|
|
characters <TT
|
|
CLASS="literal"
|
|
>*</TT
|
|
>, <TT
|
|
CLASS="literal"
|
|
>?</TT
|
|
>
|
|
and <TT
|
|
CLASS="literal"
|
|
>[abc]</TT
|
|
> to match any of
|
|
<TT
|
|
CLASS="literal"
|
|
>a</TT
|
|
>, <TT
|
|
CLASS="literal"
|
|
>b</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>c</TT
|
|
>.
|
|
<TT
|
|
CLASS="literal"
|
|
>[!abc]</TT
|
|
> is also supported,
|
|
to match any character <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>except</I
|
|
></SPAN
|
|
>
|
|
<TT
|
|
CLASS="literal"
|
|
>a</TT
|
|
>, <TT
|
|
CLASS="literal"
|
|
>b</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>c</TT
|
|
>.
|
|
This makes many multi-source-file builds quite easy:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('program', Glob('*.c'))
|
|
</PRE
|
|
><P
|
|
>
|
|
The SCons man page has more details on using <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
> with Variant
|
|
directories and Repositories, and returning strings rather than Nodes.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN508"
|
|
>3.4. Specifying Single Files Vs. Lists of Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
We've now shown you two ways to specify
|
|
the source for a program,
|
|
one with a list of files:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello', ['file1.c', 'file2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
And one with a single file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello', 'hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
You could actually put a single file name in a list, too,
|
|
which you might prefer just for the sake of consistency:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello', ['hello.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> functions will accept a single file name in either form.
|
|
In fact, internally, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> treats all input as lists of files,
|
|
but allows you to omit the square brackets
|
|
to cut down a little on the typing
|
|
when there's only a single file name.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="important"
|
|
><P
|
|
></P
|
|
><TABLE
|
|
CLASS="important"
|
|
WIDTH="100%"
|
|
BORDER="0"
|
|
><TR
|
|
><TD
|
|
WIDTH="25"
|
|
ALIGN="CENTER"
|
|
VALIGN="TOP"
|
|
><IMG
|
|
SRC="../images/important.gif"
|
|
HSPACE="5"
|
|
ALT="Important"></TD
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
><P
|
|
>
|
|
Although <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> functions
|
|
are forgiving about whether or not you
|
|
use a string vs. a list for a single file name,
|
|
Python itself is more strict about
|
|
treating lists and strings differently.
|
|
So where <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> allows either
|
|
a string or list:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # The following two calls both work correctly:
|
|
Program('program1', 'program1.c')
|
|
Program('program2', ['program2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Trying to do "Python things" that mix strings and
|
|
lists will cause errors or lead to incorrect results:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> common_sources = ['file1.c', 'file2.c']
|
|
|
|
# THE FOLLOWING IS INCORRECT AND GENERATES A PYTHON ERROR
|
|
# BECAUSE IT TRIES TO ADD A STRING TO A LIST:
|
|
Program('program1', common_sources + 'program1.c')
|
|
|
|
# The following works correctly, because it's adding two
|
|
# lists together to make another list.
|
|
Program('program2', common_sources + ['program2.c'])
|
|
</PRE
|
|
></TD
|
|
></TR
|
|
></TABLE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN526"
|
|
>3.5. Making Lists of Files Easier to Read</A
|
|
></H2
|
|
><P
|
|
>
|
|
One drawback to the use of a Python list
|
|
for source files is that
|
|
each file name must be enclosed in quotes
|
|
(either single quotes or double quotes).
|
|
This can get cumbersome and difficult to read
|
|
when the list of file names is long.
|
|
Fortunately, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> and Python provide a number of ways
|
|
to make sure that
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file stays easy to read.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
To make long lists of file names
|
|
easier to deal with, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a
|
|
<CODE
|
|
CLASS="function"
|
|
>Split</CODE
|
|
> function
|
|
that takes a quoted list of file names,
|
|
with the names separated by spaces or other white-space characters,
|
|
and turns it into a list of separate file names.
|
|
Using the <CODE
|
|
CLASS="function"
|
|
>Split</CODE
|
|
> function turns the
|
|
previous example into:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('program', Split('main.c file1.c file2.c'))
|
|
</PRE
|
|
><P
|
|
>
|
|
(If you're already familiar with Python,
|
|
you'll have realized that this is similar to the
|
|
<CODE
|
|
CLASS="function"
|
|
>split()</CODE
|
|
> method
|
|
in the Python standard <CODE
|
|
CLASS="function"
|
|
>string</CODE
|
|
> module.
|
|
Unlike the <CODE
|
|
CLASS="function"
|
|
>string.split()</CODE
|
|
> method,
|
|
however, the <CODE
|
|
CLASS="function"
|
|
>Split</CODE
|
|
> function
|
|
does not require a string as input
|
|
and will wrap up a single non-string object in a list,
|
|
or return its argument untouched if it's already a list.
|
|
This comes in handy as a way to make sure
|
|
arbitrary values can be passed to <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> functions
|
|
without having to check the type of the variable by hand.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Putting the call to the <CODE
|
|
CLASS="function"
|
|
>Split</CODE
|
|
> function
|
|
inside the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> call
|
|
can also be a little unwieldy.
|
|
A more readable alternative is to
|
|
assign the output from the <CODE
|
|
CLASS="function"
|
|
>Split</CODE
|
|
> call
|
|
to a variable name,
|
|
and then use the variable when calling the
|
|
<CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> src_files = Split('main.c file1.c file2.c')
|
|
Program('program', src_files)
|
|
</PRE
|
|
><P
|
|
>
|
|
Lastly, the <CODE
|
|
CLASS="function"
|
|
>Split</CODE
|
|
> function
|
|
doesn't care how much white space separates
|
|
the file names in the quoted string.
|
|
This allows you to create lists of file
|
|
names that span multiple lines,
|
|
which often makes for easier editing:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> src_files = Split("""main.c
|
|
file1.c
|
|
file2.c""")
|
|
Program('program', src_files)
|
|
</PRE
|
|
><P
|
|
>
|
|
(Note in this example that we used
|
|
the Python "triple-quote" syntax,
|
|
which allows a string to contain
|
|
multiple lines.
|
|
The three quotes can be either
|
|
single or double quotes.)
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN552"
|
|
>3.6. Keyword Arguments</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> also allows you to identify
|
|
the output file and input source files
|
|
using Python keyword arguments.
|
|
The output file is known as the
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>target</I
|
|
></SPAN
|
|
>,
|
|
and the source file(s) are known (logically enough) as the
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>source</I
|
|
></SPAN
|
|
>.
|
|
The Python syntax for this is:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> src_files = Split('main.c file1.c file2.c')
|
|
Program(target = 'program', source = src_files)
|
|
</PRE
|
|
><P
|
|
>
|
|
Because the keywords explicitly identify
|
|
what each argument is,
|
|
you can actually reverse the order if you prefer:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> src_files = Split('main.c file1.c file2.c')
|
|
Program(source = src_files, target = 'program')
|
|
</PRE
|
|
><P
|
|
>
|
|
Whether or not you choose to use keyword arguments
|
|
to identify the target and source files,
|
|
and the order in which you specify them
|
|
when using keywords,
|
|
are purely personal choices;
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> functions the same regardless.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN563"
|
|
>3.7. Compiling Multiple Programs</A
|
|
></H2
|
|
><P
|
|
>
|
|
In order to compile multiple programs
|
|
within the same <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file,
|
|
simply call the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> method
|
|
multiple times,
|
|
once for each program you need to build:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('foo.c')
|
|
Program('bar', ['bar1.c', 'bar2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> would then build the programs as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o bar1.o -c bar1.c
|
|
cc -o bar2.o -c bar2.c
|
|
cc -o bar bar1.o bar2.o
|
|
cc -o foo.o -c foo.c
|
|
cc -o foo foo.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not necessarily build the
|
|
programs in the same order in which you specify
|
|
them in the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does, however, recognize that
|
|
the individual object files must be built
|
|
before the resulting program can be built.
|
|
We'll discuss this in greater detail in
|
|
the "Dependencies" section, below.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN577"
|
|
>3.8. Sharing Source Files Between Multiple Programs</A
|
|
></H2
|
|
><P
|
|
>
|
|
It's common to re-use code by sharing source files
|
|
between multiple programs.
|
|
One way to do this is to create a library
|
|
from the common source files,
|
|
which can then be linked into resulting programs.
|
|
(Creating libraries is discussed in
|
|
<A
|
|
HREF="#chap-libraries"
|
|
>Chapter 4</A
|
|
>, below.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
A more straightforward, but perhaps less convenient,
|
|
way to share source files between multiple programs
|
|
is simply to include the common files
|
|
in the lists of source files for each program:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program(Split('foo.c common1.c common2.c'))
|
|
Program('bar', Split('bar1.c bar2.c common1.c common2.c'))
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> recognizes that the object files for
|
|
the <TT
|
|
CLASS="filename"
|
|
>common1.c</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>common2.c</TT
|
|
> source files
|
|
each only need to be built once,
|
|
even though the resulting object files are
|
|
each linked in to both of the resulting executable programs:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o bar1.o -c bar1.c
|
|
cc -o bar2.o -c bar2.c
|
|
cc -o common1.o -c common1.c
|
|
cc -o common2.o -c common2.c
|
|
cc -o bar bar1.o bar2.o common1.o common2.o
|
|
cc -o foo.o -c foo.c
|
|
cc -o foo foo.o common1.o common2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
If two or more programs
|
|
share a lot of common source files,
|
|
repeating the common files in the list for each program
|
|
can be a maintenance problem when you need to change the
|
|
list of common files.
|
|
You can simplify this by creating a separate Python list
|
|
to hold the common file names,
|
|
and concatenating it with other lists
|
|
using the Python <TT
|
|
CLASS="literal"
|
|
>+</TT
|
|
> operator:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> common = ['common1.c', 'common2.c']
|
|
foo_files = ['foo.c'] + common
|
|
bar_files = ['bar1.c', 'bar2.c'] + common
|
|
Program('foo', foo_files)
|
|
Program('bar', bar_files)
|
|
</PRE
|
|
><P
|
|
>
|
|
This is functionally equivalent to the previous example.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-libraries"
|
|
></A
|
|
>Chapter 4. Building and Linking with Libraries</H1
|
|
><P
|
|
>
|
|
It's often useful to organize large software projects
|
|
by collecting parts of the software into one or more libraries.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> makes it easy to create libraries
|
|
and to use them in the programs.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN597"
|
|
>4.1. Building Libraries</A
|
|
></H2
|
|
><P
|
|
>
|
|
You build your own libraries by specifying <A
|
|
HREF="#b-Library"
|
|
><CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
></A
|
|
>
|
|
instead of <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Library('foo', ['f1.c', 'f2.c', 'f3.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses the appropriate library prefix and suffix for your system.
|
|
So on POSIX or Linux systems,
|
|
the above example would build as follows
|
|
(although <SPAN
|
|
CLASS="application"
|
|
>ranlib</SPAN
|
|
> may not be called on all systems):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o f1.o -c f1.c
|
|
cc -o f2.o -c f2.c
|
|
cc -o f3.o -c f3.c
|
|
ar rc libfoo.a f1.o f2.o f3.o
|
|
ranlib libfoo.a
|
|
</PRE
|
|
><P
|
|
>
|
|
On a Windows system,
|
|
a build of the above example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl /nologo /c f1.c /Fof1.obj
|
|
cl /nologo /c f2.c /Fof2.obj
|
|
cl /nologo /c f3.c /Fof3.obj
|
|
lib /nologo /OUT:foo.lib f1.obj f2.obj f3.obj
|
|
</PRE
|
|
><P
|
|
>
|
|
The rules for the target name of the library
|
|
are similar to those for programs:
|
|
if you don't explicitly specify a target library name,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will deduce one from the
|
|
name of the first source file specified,
|
|
and <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will add an appropriate
|
|
file prefix and suffix if you leave them off.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN616"
|
|
>4.1.1. Building Libraries From Source Code or Object Files</A
|
|
></H3
|
|
><P
|
|
>
|
|
The previous example shows building a library from a
|
|
list of source files.
|
|
You can, however, also give the <A
|
|
HREF="#b-Library"
|
|
><CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
></A
|
|
> call
|
|
object files,
|
|
and it will correctly realize
|
|
In fact, you can arbitrarily mix source code files
|
|
and object files in the source list:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Library('foo', ['f1.c', 'f2.o', 'f3.c', 'f4.o'])
|
|
</PRE
|
|
><P
|
|
>
|
|
And SCons realizes that only the source code files
|
|
must be compiled into object files
|
|
before creating the final library:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o f1.o -c f1.c
|
|
cc -o f3.o -c f3.c
|
|
ar rc libfoo.a f1.o f2.o f3.o f4.o
|
|
ranlib libfoo.a
|
|
</PRE
|
|
><P
|
|
>
|
|
Of course, in this example, the object files
|
|
must already exist for the build to succeed.
|
|
See <A
|
|
HREF="#chap-nodes"
|
|
>Chapter 5</A
|
|
>, below,
|
|
for information about how you can
|
|
build object files explicitly
|
|
and include the built files in a library.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN627"
|
|
>4.1.2. Building Static Libraries Explicitly: the <CODE
|
|
CLASS="function"
|
|
>StaticLibrary</CODE
|
|
> Builder</A
|
|
></H3
|
|
><P
|
|
>
|
|
The <A
|
|
HREF="#b-Library"
|
|
><CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
></A
|
|
> function builds a traditional static library.
|
|
If you want to be explicit about the type of library being built,
|
|
you can use the synonym <A
|
|
HREF="#b-StaticLibrary"
|
|
><CODE
|
|
CLASS="function"
|
|
>StaticLibrary</CODE
|
|
></A
|
|
> function
|
|
instead of <CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> StaticLibrary('foo', ['f1.c', 'f2.c', 'f3.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
There is no functional difference between the
|
|
<A
|
|
HREF="#b-StaticLibrary"
|
|
><CODE
|
|
CLASS="function"
|
|
>StaticLibrary</CODE
|
|
></A
|
|
> and <CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
> functions.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN641"
|
|
>4.1.3. Building Shared (DLL) Libraries: the <CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
> Builder</A
|
|
></H3
|
|
><P
|
|
>
|
|
If you want to build a shared library (on POSIX systems)
|
|
or a DLL file (on Windows systems),
|
|
you use the <A
|
|
HREF="#b-SharedLibrary"
|
|
><CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
></A
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SharedLibrary('foo', ['f1.c', 'f2.c', 'f3.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
The output on POSIX:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o f1.os -c f1.c
|
|
cc -o f2.os -c f2.c
|
|
cc -o f3.os -c f3.c
|
|
cc -o libfoo.so -shared f1.os f2.os f3.os
|
|
</PRE
|
|
><P
|
|
>
|
|
And the output on Windows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl /nologo /c f1.c /Fof1.obj
|
|
cl /nologo /c f2.c /Fof2.obj
|
|
cl /nologo /c f3.c /Fof3.obj
|
|
link /nologo /dll /out:foo.dll /implib:foo.lib f1.obj f2.obj f3.obj
|
|
RegServerFunc(target, source, env)
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice again that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> takes care of
|
|
building the output file correctly,
|
|
adding the <TT
|
|
CLASS="literal"
|
|
>-shared</TT
|
|
> option
|
|
for a POSIX compilation,
|
|
and the <TT
|
|
CLASS="literal"
|
|
>/dll</TT
|
|
> option on Windows.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN658"
|
|
>4.2. Linking with Libraries</A
|
|
></H2
|
|
><P
|
|
>
|
|
Usually, you build a library
|
|
because you want to link it with one or more programs.
|
|
You link libraries with a program by specifying
|
|
the libraries in the <A
|
|
HREF="#cv-LIBS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
></A
|
|
> construction variable,
|
|
and by specifying the directory in which
|
|
the library will be found in the
|
|
<A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
> construction variable:
|
|
|
|
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Library('foo', ['f1.c', 'f2.c', 'f3.c'])
|
|
Program('prog.c', LIBS=['foo', 'bar'], LIBPATH='.')
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice, of course, that you don't need to specify a library
|
|
prefix (like <TT
|
|
CLASS="literal"
|
|
>lib</TT
|
|
>)
|
|
or suffix (like <TT
|
|
CLASS="literal"
|
|
>.a</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>.lib</TT
|
|
>).
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses the correct prefix or suffix for the current system.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
On a POSIX or Linux system,
|
|
a build of the above example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o f1.o -c f1.c
|
|
cc -o f2.o -c f2.c
|
|
cc -o f3.o -c f3.c
|
|
ar rc libfoo.a f1.o f2.o f3.o
|
|
ranlib libfoo.a
|
|
cc -o prog.o -c prog.c
|
|
cc -o prog prog.o -L. -lfoo -lbar
|
|
</PRE
|
|
><P
|
|
>
|
|
On a Windows system,
|
|
a build of the above example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl /nologo /c f1.c /Fof1.obj
|
|
cl /nologo /c f2.c /Fof2.obj
|
|
cl /nologo /c f3.c /Fof3.obj
|
|
lib /nologo /OUT:foo.lib f1.obj f2.obj f3.obj
|
|
cl /nologo /c prog.c /Foprog.obj
|
|
link /nologo /OUT:prog.exe /LIBPATH:. foo.lib bar.lib prog.obj
|
|
</PRE
|
|
><P
|
|
>
|
|
As usual, notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has taken care
|
|
of constructing the correct command lines
|
|
to link with the specified library on each system.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note also that,
|
|
if you only have a single library to link with,
|
|
you can specify the library name in single string,
|
|
instead of a Python list,
|
|
so that:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('prog.c', LIBS='foo', LIBPATH='.')
|
|
</PRE
|
|
><P
|
|
>
|
|
is equivalent to:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('prog.c', LIBS=['foo'], LIBPATH='.')
|
|
</PRE
|
|
><P
|
|
>
|
|
This is similar to the way that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
handles either a string or a list to
|
|
specify a single source file.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN685"
|
|
>4.3. Finding Libraries: the <CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
> Construction Variable</A
|
|
></H2
|
|
><P
|
|
>
|
|
By default, the linker will only look in
|
|
certain system-defined directories for libraries.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> knows how to look for libraries
|
|
in directories that you specify with the
|
|
<A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
> construction variable.
|
|
<CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
> consists of a list of
|
|
directory names, like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('prog.c', LIBS = 'm',
|
|
LIBPATH = ['/usr/lib', '/usr/local/lib'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Using a Python list is preferred because it's portable
|
|
across systems. Alternatively, you could put all of
|
|
the directory names in a single string, separated by the
|
|
system-specific path separator character:
|
|
a colon on POSIX systems:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> LIBPATH = '/usr/lib:/usr/local/lib'
|
|
</PRE
|
|
><P
|
|
>
|
|
or a semi-colon on Windows systems:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> LIBPATH = 'C:\\lib;D:\\lib'
|
|
</PRE
|
|
><P
|
|
>
|
|
(Note that Python requires that the backslash
|
|
separators in a Windows path name
|
|
be escaped within strings.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
When the linker is executed,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will create appropriate flags
|
|
so that the linker will look for
|
|
libraries in the same directories as <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
So on a POSIX or Linux system,
|
|
a build of the above example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o prog.o -c prog.c
|
|
cc -o prog prog.o -L/usr/lib -L/usr/local/lib -lm
|
|
</PRE
|
|
><P
|
|
>
|
|
On a Windows system,
|
|
a build of the above example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl /nologo /c prog.c /Foprog.obj
|
|
link /nologo /OUT:prog.exe /LIBPATH:\usr\lib /LIBPATH:\usr\local\lib m.lib prog.obj
|
|
</PRE
|
|
><P
|
|
>
|
|
Note again that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has taken care of
|
|
the system-specific details of creating
|
|
the right command-line options.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-nodes"
|
|
></A
|
|
>Chapter 5. Node Objects</H1
|
|
><P
|
|
>
|
|
Internally, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> represents all of the files
|
|
and directories it knows about as <TT
|
|
CLASS="literal"
|
|
>Nodes</TT
|
|
>.
|
|
These internal objects
|
|
(not object <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>files</I
|
|
></SPAN
|
|
>)
|
|
can be used in a variety of ways
|
|
to make your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>
|
|
files portable and easy to read.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN716"
|
|
>5.1. Builder Methods Return Lists of Target Nodes</A
|
|
></H2
|
|
><P
|
|
>
|
|
All builder methods return a list of
|
|
<CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
> objects that identify the
|
|
target file or files that will be built.
|
|
These returned <TT
|
|
CLASS="literal"
|
|
>Nodes</TT
|
|
> can be passed
|
|
as source files to other builder methods,
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose that we want to build
|
|
the two object files that make up a program with different options.
|
|
This would mean calling the <A
|
|
HREF="#b-Object"
|
|
><CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
></A
|
|
>
|
|
builder once for each object file,
|
|
specifying the desired options:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Object('hello.c', CCFLAGS='-DHELLO')
|
|
Object('goodbye.c', CCFLAGS='-DGOODBYE')
|
|
</PRE
|
|
><P
|
|
>
|
|
One way to combine these object files
|
|
into the resulting program
|
|
would be to call the <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
>
|
|
builder with the names of the object files
|
|
listed as sources:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Object('hello.c', CCFLAGS='-DHELLO')
|
|
Object('goodbye.c', CCFLAGS='-DGOODBYE')
|
|
Program(['hello.o', 'goodbye.o'])
|
|
</PRE
|
|
><P
|
|
>
|
|
The problem with listing the names as strings
|
|
is that our <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file is no longer portable
|
|
across operating systems.
|
|
It won't, for example, work on Windows
|
|
because the object files there would be
|
|
named <TT
|
|
CLASS="filename"
|
|
>hello.obj</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>goodbye.obj</TT
|
|
>,
|
|
not <TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>goodbye.o</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
A better solution is to assign the lists of targets
|
|
returned by the calls to the <CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
> builder to variables,
|
|
which we can then concatenate in our
|
|
call to the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> builder:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello_list = Object('hello.c', CCFLAGS='-DHELLO')
|
|
goodbye_list = Object('goodbye.c', CCFLAGS='-DGOODBYE')
|
|
Program(hello_list + goodbye_list)
|
|
</PRE
|
|
><P
|
|
>
|
|
This makes our <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file portable again,
|
|
the build output on Linux looking like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o goodbye.o -c -DGOODBYE goodbye.c
|
|
cc -o hello.o -c -DHELLO hello.c
|
|
cc -o hello hello.o goodbye.o
|
|
</PRE
|
|
><P
|
|
>
|
|
And on Windows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cl -DGOODBYE /c goodbye.c /Fogoodbye.obj
|
|
cl -DHELLO /c hello.c /Fohello.obj
|
|
link /nologo /OUT:hello.exe hello.obj goodbye.obj
|
|
</PRE
|
|
><P
|
|
>
|
|
We'll see examples of using the list of nodes
|
|
returned by builder methods throughout
|
|
the rest of this guide.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN747"
|
|
>5.2. Explicitly Creating File and Directory Nodes</A
|
|
></H2
|
|
><P
|
|
>
|
|
It's worth mentioning here that
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> maintains a clear distinction
|
|
between Nodes that represent files
|
|
and Nodes that represent directories.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports <CODE
|
|
CLASS="function"
|
|
>File</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>
|
|
functions that, repectively,
|
|
return a file or directory Node:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello_c = File('hello.c')
|
|
Program(hello_c)
|
|
|
|
classes = Dir('classes')
|
|
Java(classes, 'src')
|
|
</PRE
|
|
><P
|
|
>
|
|
Normally, you don't need to call
|
|
<CODE
|
|
CLASS="function"
|
|
>File</CODE
|
|
> or <CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
> directly,
|
|
because calling a builder method automatically
|
|
treats strings as the names of files or directories,
|
|
and translates them into
|
|
the Node objects for you.
|
|
The <CODE
|
|
CLASS="function"
|
|
>File</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
> functions can come in handy
|
|
in situations where you need to explicitly
|
|
instruct <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> about the type of Node being
|
|
passed to a builder or other function,
|
|
or unambiguously refer to a specific
|
|
file in a directory tree.
|
|
|
|
|
|
</P
|
|
><P
|
|
>
|
|
There are also times when you may need to
|
|
refer to an entry in a file system
|
|
without knowing in advance
|
|
whether it's a file or a directory.
|
|
For those situations,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> also supports an <CODE
|
|
CLASS="function"
|
|
>Entry</CODE
|
|
> function,
|
|
which returns a Node
|
|
that can represent either a file or a directory.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> xyzzy = Entry('xyzzy')
|
|
</PRE
|
|
><P
|
|
>
|
|
The returned <TT
|
|
CLASS="literal"
|
|
>xyzzy</TT
|
|
> Node
|
|
will be turned into a file or directory Node
|
|
the first time it is used by a builder method
|
|
or other function that
|
|
requires one vs. the other.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN767"
|
|
>5.3. Printing <CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
> File Names</A
|
|
></H2
|
|
><P
|
|
>
|
|
One of the most common things you can do
|
|
with a Node is use it to print the
|
|
file name that the node represents.
|
|
For example, the following <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello_c = File('hello.c')
|
|
Program(hello_c)
|
|
|
|
classes = Dir('classes')
|
|
Java(classes, 'src')
|
|
|
|
object_list = Object('hello.c')
|
|
program_list = Program(object_list)
|
|
print "The object file is:", object_list[0]
|
|
print "The program file is:", program_list[0]
|
|
</PRE
|
|
><P
|
|
>
|
|
Would print the following file names on a POSIX system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
The object file is: hello.o
|
|
The program file is: hello
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
And the following file names on a Windows system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
The object file is: hello.obj
|
|
The program file is: hello.exe
|
|
cl /nologo /c hello.c /Fohello.obj
|
|
link /nologo /OUT:hello.exe hello.obj
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN779"
|
|
>5.4. Using a <CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
>'s File Name as a String</A
|
|
></H2
|
|
><P
|
|
>
|
|
Printing a <CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
>'s name
|
|
as described in the previous section
|
|
works because the string representation of a <CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
>
|
|
is the name of the file.
|
|
If you want to do something other than
|
|
print the name of the file,
|
|
you can fetch it by using the builtin Python
|
|
<CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
> function.
|
|
For example, if you want to use the Python
|
|
<CODE
|
|
CLASS="function"
|
|
>os.path.exists</CODE
|
|
>
|
|
to figure out whether a file
|
|
exists while the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
is being read and executed,
|
|
you can fetch the string as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os.path
|
|
program_list = Program('hello.c')
|
|
program_name = str(program_list[0])
|
|
if not os.path.exists(program_name):
|
|
print program_name, "does not exist!"
|
|
</PRE
|
|
><P
|
|
>
|
|
Which executes as follows on a POSIX system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
hello does not exist!
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-depends"
|
|
></A
|
|
>Chapter 6. Dependencies</H1
|
|
><P
|
|
>
|
|
So far we've seen how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> handles one-time builds.
|
|
But one of the main functions of a build tool like <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
is to rebuild only the necessary things
|
|
when source files change--or, put another way,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> should <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
waste time rebuilding things that have already been built.
|
|
You can see this at work simply by re-invoking <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
after building our simple <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
The second time it is executed,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> realizes that the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program
|
|
is up-to-date with respect to the current <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> source file,
|
|
and avoids rebuilding it.
|
|
You can see this more clearly by naming
|
|
the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program explicitly on the command line:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> reports <TT
|
|
CLASS="literal"
|
|
>"...is up to date"</TT
|
|
>
|
|
only for target files named explicitly on the command line,
|
|
to avoid cluttering the output.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN815"
|
|
>6.1. Deciding When an Input File Has Changed: the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Another aspect of avoiding unnecessary rebuilds
|
|
is the fundamental build tool behavior
|
|
of <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>rebuilding</I
|
|
></SPAN
|
|
>
|
|
things when an input file changes,
|
|
so that the built software is up to date.
|
|
By default,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> keeps track of this through an
|
|
MD5 <TT
|
|
CLASS="literal"
|
|
>signature</TT
|
|
>, or checksum, of the contents of each file,
|
|
although you can easily configure
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to use the
|
|
modification times (or time stamps)
|
|
instead.
|
|
You can even specify your own Python function
|
|
for deciding if an input file has changed.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN823"
|
|
>6.1.1. Using MD5 Signatures to Decide if a File Has Changed</A
|
|
></H3
|
|
><P
|
|
>
|
|
By default,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> keeps track of whether a file has changed
|
|
based on an MD5 checksum of the file's contents,
|
|
not the file's modification time.
|
|
This means that you may be surprised by the
|
|
default <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> behavior if you are used to the
|
|
<SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
> convention of forcing
|
|
a rebuild by updating the file's modification time
|
|
(using the <SPAN
|
|
CLASS="application"
|
|
>touch</SPAN
|
|
> command, for example):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>touch hello.c</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Even though the file's modification time has changed,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> realizes that the contents of the
|
|
<TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file have <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
> changed,
|
|
and therefore that the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program
|
|
need not be rebuilt.
|
|
This avoids unnecessary rebuilds when,
|
|
for example, someone rewrites the
|
|
contents of a file without making a change.
|
|
But if the contents of the file really do change,
|
|
then <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> detects the change
|
|
and rebuilds the program as required:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.c</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF hello.c]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that you can, if you wish,
|
|
specify this default behavior
|
|
(MD5 signatures) explicitly
|
|
using the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
Decider('MD5')
|
|
</PRE
|
|
><P
|
|
>
|
|
You can also use the string <TT
|
|
CLASS="literal"
|
|
>'content'</TT
|
|
>
|
|
as a synonym for <TT
|
|
CLASS="literal"
|
|
>'MD5'</TT
|
|
>
|
|
when calling the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H4
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN851"
|
|
>6.1.1.1. Ramifications of Using MD5 Signatures</A
|
|
></H4
|
|
><P
|
|
>
|
|
Using MD5 Signatures to decide if an input file has changed
|
|
has one surprising benefit:
|
|
if a source file has been changed
|
|
in such a way that the contents of the
|
|
rebuilt target file(s)
|
|
will be exactly the same as the last time
|
|
the file was built,
|
|
then any "downstream" target files
|
|
that depend on the rebuilt-but-not-changed target
|
|
file actually need not be rebuilt.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
So if, for example,
|
|
a user were to only change a comment in a <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file,
|
|
then the rebuilt <TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
> file
|
|
would be exactly the same as the one previously built
|
|
(assuming the compiler doesn't put any build-specific
|
|
information in the object file).
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> would then realize that it would not
|
|
need to rebuild the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.c</KBD
|
|
>
|
|
[CHANGE A COMMENT IN hello.c]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In essence, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
"short-circuits" any dependent builds
|
|
when it realizes that a target file
|
|
has been rebuilt to exactly the same file as the last build.
|
|
This does take some extra processing time
|
|
to read the contents of the target (<TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
>) file,
|
|
but often saves time when the rebuild that was avoided
|
|
would have been time-consuming and expensive.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN866"
|
|
>6.1.2. Using Time Stamps to Decide If a File Has Changed</A
|
|
></H3
|
|
><P
|
|
>
|
|
If you prefer, you can
|
|
configure <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to use the modification time
|
|
of a file, not the file contents,
|
|
when deciding if a target needs to be rebuilt.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> gives you two ways to use time stamps
|
|
to decide if an input file has changed
|
|
since the last time a target has been built.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The most familiar way to use time stamps
|
|
is the way <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
> does:
|
|
that is, have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> decide
|
|
and target must be rebuilt if
|
|
if a source file's modification time is
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>newer</I
|
|
></SPAN
|
|
>
|
|
than the target file.
|
|
To do this, call the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
>
|
|
function as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
Decider('timestamp-newer')
|
|
</PRE
|
|
><P
|
|
>
|
|
This makes <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> act like <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>
|
|
when a file's modification time is updated
|
|
(using the <SPAN
|
|
CLASS="application"
|
|
>touch</SPAN
|
|
> command, for example):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>touch hello.c</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
And, in fact, because this behavior is the same
|
|
as the behavior of <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>,
|
|
you can also use the string <TT
|
|
CLASS="literal"
|
|
>'make'</TT
|
|
>
|
|
as a synonym for <TT
|
|
CLASS="literal"
|
|
>'timestamp-newer'</TT
|
|
>
|
|
when calling the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
Decider('make')
|
|
</PRE
|
|
><P
|
|
>
|
|
One drawback to using times stamps exactly like <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>
|
|
is that if an input file's modification time suddenly
|
|
becomes <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>older</I
|
|
></SPAN
|
|
> than a target file,
|
|
the target file will not be rebuilt.
|
|
This can happen if an old copy of a source file is restored
|
|
from a backup archive, for example.
|
|
The contents of the restored file will likely be different
|
|
than they were the last time a dependent target was built,
|
|
but the target won't be rebuilt
|
|
because the modification time of the source file
|
|
is not newer than the target.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> actually stores information
|
|
about the source files' time stamps whenever a target is built,
|
|
it can handle this situation by checking for
|
|
an exact match of the source file time stamp,
|
|
instead of just whether or not the source file
|
|
is newer than the target file.
|
|
To do this, specify the argument
|
|
<TT
|
|
CLASS="literal"
|
|
>'timestamp-match'</TT
|
|
>
|
|
when calling the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
Decider('timestamp-match')
|
|
</PRE
|
|
><P
|
|
>
|
|
When configured this way,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will rebuild a target whenever
|
|
a source file's modification time has changed.
|
|
So if we use the <TT
|
|
CLASS="literal"
|
|
>touch -t</TT
|
|
>
|
|
option to change the modification time of
|
|
<TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> to an old date (January 1, 1989),
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will still rebuild the target file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>touch -t 198901010000 hello.c</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In general, the only reason to prefer
|
|
<TT
|
|
CLASS="literal"
|
|
>timestamp-newer</TT
|
|
>
|
|
instead of
|
|
<TT
|
|
CLASS="literal"
|
|
>timestamp-match</TT
|
|
>,
|
|
would be if you have some specific reason
|
|
to require this <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>-like behavior of
|
|
not rebuilding a target when an otherwise-modified
|
|
source file is older.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN912"
|
|
>6.1.3. Deciding If a File Has Changed Using Both MD Signatures and Time Stamps</A
|
|
></H3
|
|
><P
|
|
>
|
|
As a performance enhancement,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a way to use
|
|
MD5 checksums of file contents
|
|
but to only read the contents
|
|
whenever the file's timestamp has changed.
|
|
To do this, call the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
>
|
|
function with <TT
|
|
CLASS="literal"
|
|
>'MD5-timestamp'</TT
|
|
>
|
|
argument as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
Decider('MD5-timestamp')
|
|
</PRE
|
|
><P
|
|
>
|
|
So configured, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will still behave like
|
|
it does when using <TT
|
|
CLASS="literal"
|
|
>Decider('MD5')</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>touch hello.c</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.c</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF hello.c]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
However, the second call to <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in the above output,
|
|
when the build is up-to-date,
|
|
will have been performed by simply looking at the
|
|
modification time of the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file,
|
|
not by opening it and performing
|
|
an MD5 checksum calcuation on its contents.
|
|
This can significantly speed up many up-to-date builds.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The only drawback to using
|
|
<TT
|
|
CLASS="literal"
|
|
>Decider('MD5-timestamp')</TT
|
|
>
|
|
is that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
rebuild a target file if a source file was modified
|
|
within one second of the last time <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> built the file.
|
|
While most developers are programming,
|
|
this isn't a problem in practice,
|
|
since it's unlikely that someone will have built
|
|
and then thought quickly enought to make a substantive
|
|
change to a source file within one second.
|
|
Certain build scripts or
|
|
continuous integration tools may, however,
|
|
rely on the ability to applying changes to files
|
|
automatically and then rebuild as quickly as possible,
|
|
in which case use of
|
|
<TT
|
|
CLASS="literal"
|
|
>Decider('MD5-timestamp')</TT
|
|
>
|
|
may not be appropriate.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN937"
|
|
>6.1.4. Writing Your Own Custom <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
The different string values that we've passed to
|
|
the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function are essentially used by <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
to pick one of several specific internal functions
|
|
that implement various ways of deciding if a dependency
|
|
(usually a source file)
|
|
has changed since a target file has been built.
|
|
As it turns out,
|
|
you can also supply your own function
|
|
to decide if a dependency has changed.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose we have an input file
|
|
that contains a lot of data,
|
|
in some specific regular format,
|
|
that is used to rebuild a lot of different target files,
|
|
but each target file really only depends on
|
|
one particular section of the input file.
|
|
We'd like to have each target file depend on
|
|
only its section of the input file.
|
|
However, since the input file may contain a lot of data,
|
|
we only want to open the input file if its timestamp has changed.
|
|
This could done with a custom
|
|
<CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function that might look something like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
def decide_if_changed(dependency, target, prev_ni):
|
|
if self.get_timestamp() != prev_ni.timestamp:
|
|
dep = str(dependency)
|
|
tgt = str(target)
|
|
if specific_part_of_file_has_changed(dep, tgt):
|
|
return True
|
|
return False
|
|
Decider(decide_if_changed)
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that in the function definition,
|
|
the <CODE
|
|
CLASS="varname"
|
|
>dependency</CODE
|
|
>
|
|
(input file) is the first argument,
|
|
and then the <CODE
|
|
CLASS="varname"
|
|
>target</CODE
|
|
>.
|
|
Both of these are passed to the functions as
|
|
SCons <CODE
|
|
CLASS="classname"
|
|
>Node</CODE
|
|
> objects,
|
|
which we convert to strings using the Python
|
|
<CODE
|
|
CLASS="function"
|
|
>str()</CODE
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The third argument, <CODE
|
|
CLASS="varname"
|
|
>prev_ni</CODE
|
|
>,
|
|
is an object that holds the
|
|
signature or timestamp information
|
|
that was recorded about the dependency
|
|
the last time the target was built.
|
|
A <CODE
|
|
CLASS="varname"
|
|
>prev_ni</CODE
|
|
> object can hold
|
|
different information,
|
|
depending on the type of thing that the
|
|
<CODE
|
|
CLASS="varname"
|
|
>dependency</CODE
|
|
> argument represents.
|
|
For normal files,
|
|
the <CODE
|
|
CLASS="varname"
|
|
>prev_ni</CODE
|
|
> object
|
|
has the following attributes:
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
>.csig</DT
|
|
><DD
|
|
><P
|
|
> The <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>content signature</I
|
|
></SPAN
|
|
>,
|
|
or MD5 checksum, of the contents of the
|
|
<CODE
|
|
CLASS="varname"
|
|
>dependency</CODE
|
|
>
|
|
file the list time the <CODE
|
|
CLASS="varname"
|
|
>target</CODE
|
|
> was built.
|
|
</P
|
|
></DD
|
|
><DT
|
|
>.size</DT
|
|
><DD
|
|
><P
|
|
> The size in bytes of the <CODE
|
|
CLASS="varname"
|
|
>dependency</CODE
|
|
>
|
|
file the list time the target was built.
|
|
</P
|
|
></DD
|
|
><DT
|
|
>.timestamp</DT
|
|
><DD
|
|
><P
|
|
> The modification time of the <CODE
|
|
CLASS="varname"
|
|
>dependency</CODE
|
|
>
|
|
file the list time the <CODE
|
|
CLASS="varname"
|
|
>target</CODE
|
|
> was built.
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
><P
|
|
>
|
|
Note that ignoring some of the arguments
|
|
in your custom <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function
|
|
is a perfectly normal thing to do,
|
|
if they don't impact the way you want to
|
|
decide if the dependency file has changed.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN977"
|
|
>6.1.5. Mixing Different Ways of Deciding If a File Has Changed</A
|
|
></H3
|
|
><P
|
|
>
|
|
The previous examples have all demonstrated calling
|
|
the global <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function
|
|
to configure all dependency decisions that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> makes.
|
|
Sometimes, however, you want to be able to configure
|
|
different decision-making for different targets.
|
|
When that's necessary, you can use the
|
|
<CODE
|
|
CLASS="function"
|
|
>env.Decider</CODE
|
|
>
|
|
method to affect only the configuration
|
|
decisions for targets built with a
|
|
specific construction environment.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, if we arbitrarily want to build
|
|
one program using MD5 checkums
|
|
and another use file modification times
|
|
from the same source
|
|
we might configure it this way:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env1 = Environment(CPPPATH = ['.'])
|
|
env2 = env1.Clone()
|
|
env2.Decider('timestamp-match')
|
|
env1.Program('prog-MD5', 'program1.c')
|
|
env2.Program('prog-timestamp', 'program2.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
If both of the programs include the same
|
|
<TT
|
|
CLASS="filename"
|
|
>inc.h</TT
|
|
> file,
|
|
then updating the modification time of
|
|
<TT
|
|
CLASS="filename"
|
|
>inc.h</TT
|
|
>
|
|
(using the <SPAN
|
|
CLASS="application"
|
|
>touch</SPAN
|
|
> command)
|
|
will cause only <TT
|
|
CLASS="filename"
|
|
>prog-timestamp</TT
|
|
>
|
|
to be rebuilt:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o program1.o -c -I. program1.c
|
|
cc -o prog-MD5 program1.o
|
|
cc -o program2.o -c -I. program2.c
|
|
cc -o prog-timestamp program2.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>touch inc.h</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o program2.o -c -I. program2.c
|
|
cc -o prog-timestamp program2.o
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN994"
|
|
>6.2. Older Functions for Deciding When an Input File Has Changed</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> still supports two functions that used to be the
|
|
primary methods for configuring the
|
|
decision about whether or not an input file has changed.
|
|
Although they're not officially deprecated yet,
|
|
their use is discouraged,
|
|
mainly because they rely on a somewhat
|
|
confusing distinction between how
|
|
source files and target files are handled.
|
|
These functions are documented here mainly in case you
|
|
encounter them in existing <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN999"
|
|
>6.2.1. The <CODE
|
|
CLASS="function"
|
|
>SourceSignatures</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>SourceSignatures</CODE
|
|
> function is fairly straightforward,
|
|
and supports two different argument values
|
|
to configure whether source file changes should be decided
|
|
using MD5 signatures:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
SourceSignatures('MD5')
|
|
</PRE
|
|
><P
|
|
>
|
|
Or using time stamps:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
SourceSignatures('timestamp')
|
|
</PRE
|
|
><P
|
|
>
|
|
These are roughly equivalent to specifying
|
|
<CODE
|
|
CLASS="function"
|
|
>Decider('MD5')</CODE
|
|
>
|
|
or
|
|
<CODE
|
|
CLASS="function"
|
|
>Decider('timestamp-match')</CODE
|
|
>,
|
|
respectively,
|
|
although it only affects how SCons makes
|
|
decisions about dependencies on
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>source</I
|
|
></SPAN
|
|
> files--that is,
|
|
files that are not built from any other files.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1011"
|
|
>6.2.2. The <CODE
|
|
CLASS="function"
|
|
>TargetSignatures</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>TargetSignatures</CODE
|
|
> function
|
|
specifies how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> decides
|
|
when a target file has changed
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>when it is used as a
|
|
dependency of (input to) another target</I
|
|
></SPAN
|
|
>--that is,
|
|
the <CODE
|
|
CLASS="function"
|
|
>TargetSignatures</CODE
|
|
> function configures
|
|
how the signatures of "intermediate" target files
|
|
are used when deciding if a "downstream" target file
|
|
must be rebuilt.
|
|
<A
|
|
NAME="AEN1019"
|
|
HREF="#FTN.AEN1019"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[2]</SPAN
|
|
></A
|
|
>
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>TargetSignatures</CODE
|
|
> function supports the same
|
|
<TT
|
|
CLASS="literal"
|
|
>'MD5'</TT
|
|
> and <TT
|
|
CLASS="literal"
|
|
>'timestamp'</TT
|
|
>
|
|
argument values that are supported by the <CODE
|
|
CLASS="function"
|
|
>SourceSignatures</CODE
|
|
>,
|
|
with the same meanings, but applied to target files.
|
|
That is, in the example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
TargetSignatures('MD5')
|
|
</PRE
|
|
><P
|
|
>
|
|
The MD5 checksum of the <TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
> target file
|
|
will be used to decide if it has changed since the last
|
|
time the "downstream" <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> target file was built.
|
|
And in the example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
TargetSignatures('timestamp')
|
|
</PRE
|
|
><P
|
|
>
|
|
The modification time of the <TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
> target file
|
|
will be used to decide if it has changed since the last
|
|
time the "downstream" <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> target file was built.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>TargetSignatures</CODE
|
|
> function supports
|
|
two additional argument values:
|
|
<TT
|
|
CLASS="literal"
|
|
>'source'</TT
|
|
> and <TT
|
|
CLASS="literal"
|
|
>'build'</TT
|
|
>.
|
|
The <TT
|
|
CLASS="literal"
|
|
>'source'</TT
|
|
> argument
|
|
specifies that decisions involving
|
|
whether target files have changed
|
|
since a previous build
|
|
should use the same behavior
|
|
for the decisions configured for source files
|
|
(using the <CODE
|
|
CLASS="function"
|
|
>SourceSignatures</CODE
|
|
> function).
|
|
So in the example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c')
|
|
TargetSignatures('source')
|
|
SourceSignatures('timestamp')
|
|
</PRE
|
|
><P
|
|
>
|
|
All files, both targets and sources,
|
|
will use modification times
|
|
when deciding if an input file
|
|
has changed since the last
|
|
time a target was built.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Lastly, the <TT
|
|
CLASS="literal"
|
|
>'build'</TT
|
|
> argument
|
|
specifies that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> should examine
|
|
the build status of a target file
|
|
and always rebuild a "downstream" target
|
|
if the target file was itself rebuilt,
|
|
without re-examining the contents or timestamp
|
|
of the newly-built target file.
|
|
If the target file was not rebuilt during
|
|
this <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> invocation,
|
|
then the target file will be examined
|
|
the same way as configured by
|
|
the <CODE
|
|
CLASS="function"
|
|
>SourceSignature</CODE
|
|
> call
|
|
to decide if it has changed.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
This mimics the behavior of
|
|
<TT
|
|
CLASS="literal"
|
|
>build signatures</TT
|
|
>
|
|
in earlier versions of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
A <TT
|
|
CLASS="literal"
|
|
>build signature</TT
|
|
> re-combined
|
|
signatures of all the input files
|
|
that went into making the target file,
|
|
so that the target file itself
|
|
did not need to have its contents read
|
|
to compute an MD5 signature.
|
|
This can improve performance for some configurations,
|
|
but is generally not as effective as using
|
|
<TT
|
|
CLASS="literal"
|
|
>Decider('MD5-timestamp')</TT
|
|
>.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1056"
|
|
>6.3. Implicit Dependencies: The <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> Construction Variable</A
|
|
></H2
|
|
><P
|
|
>
|
|
Now suppose that our "Hello, World!" program
|
|
actually has an <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> line
|
|
to include the <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file in the compilation:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> #include <hello.h>
|
|
int
|
|
main()
|
|
{
|
|
printf("Hello, %s!\n", string);
|
|
}
|
|
</PRE
|
|
><P
|
|
>
|
|
And, for completeness, the <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file looks like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> #define string "world"
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case, we want <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to recognize that,
|
|
if the contents of the <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file change,
|
|
the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program must be recompiled.
|
|
To do this, we need to modify the
|
|
<TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c', CPPPATH = '.')
|
|
</PRE
|
|
><P
|
|
>
|
|
The <A
|
|
HREF="#cv-CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
></A
|
|
> value
|
|
tells <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to look in the current directory
|
|
(<TT
|
|
CLASS="literal"
|
|
>'.'</TT
|
|
>)
|
|
for any files included by C source files
|
|
(<TT
|
|
CLASS="filename"
|
|
>.c</TT
|
|
> or <TT
|
|
CLASS="filename"
|
|
>.h</TT
|
|
> files).
|
|
With this assignment in the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c -I. hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.h</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF hello.h]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c -I. hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
First, notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
added the <TT
|
|
CLASS="literal"
|
|
>-I.</TT
|
|
> argument
|
|
from the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> variable
|
|
so that the compilation would find the
|
|
<TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file in the local directory.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Second, realize that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> knows that the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
>
|
|
program must be rebuilt
|
|
because it scans the contents of
|
|
the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file
|
|
for the <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> lines that indicate
|
|
another file is being included in the compilation.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> records these as
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>implicit dependencies</I
|
|
></SPAN
|
|
>
|
|
of the target file,
|
|
Consequently,
|
|
when the <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file changes,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> realizes that the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file includes it,
|
|
and rebuilds the resulting <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program
|
|
that depends on both the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> files.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Like the <A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
> variable,
|
|
the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> variable
|
|
may be a list of directories,
|
|
or a string separated by
|
|
the system-specific path separation character
|
|
(':' on POSIX/Linux, ';' on Windows).
|
|
Either way, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> creates the
|
|
right command-line options
|
|
so that the following example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('hello.c', CPPPATH = ['include', '/home/project/inc'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Will look like this on POSIX or Linux:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c -Iinclude -I/home/project/inc hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
And like this on Windows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello.exe</KBD
|
|
>
|
|
cl /nologo /Iinclude /I\home\project\inc /c hello.c /Fohello.obj
|
|
link /nologo /OUT:hello.exe hello.obj
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1115"
|
|
>6.4. Caching Implicit Dependencies</A
|
|
></H2
|
|
><P
|
|
>
|
|
Scanning each file for <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> lines
|
|
does take some extra processing time.
|
|
When you're doing a full build of a large system,
|
|
the scanning time is usually a very small percentage
|
|
of the overall time spent on the build.
|
|
You're most likely to notice the scanning time,
|
|
however, when you <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>rebuild</I
|
|
></SPAN
|
|
>
|
|
all or part of a large system:
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will likely take some extra time to "think about"
|
|
what must be built before it issues the
|
|
first build command
|
|
(or decides that everything is up to date
|
|
and nothing must be rebuilt).
|
|
|
|
|
|
|
|
</P
|
|
><P
|
|
>
|
|
In practice, having <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> scan files saves time
|
|
relative to the amount of potential time
|
|
lost to tracking down subtle problems
|
|
introduced by incorrect dependencies.
|
|
Nevertheless, the "waiting time"
|
|
while <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> scans files can annoy
|
|
individual developers waiting for their builds to finish.
|
|
Consequently, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> lets you cache
|
|
the implicit dependencies
|
|
that its scanners find,
|
|
for use by later builds.
|
|
You can do this by specifying the
|
|
<TT
|
|
CLASS="literal"
|
|
>--implicit-cache</TT
|
|
> option on the command line:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --implicit-cache hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
If you don't want to specify <TT
|
|
CLASS="literal"
|
|
>--implicit-cache</TT
|
|
>
|
|
on the command line each time,
|
|
you can make it the default behavior for your build
|
|
by setting the <TT
|
|
CLASS="literal"
|
|
>implicit_cache</TT
|
|
> option
|
|
in an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SetOption('implicit_cache', 1)
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not cache implicit dependencies like this by default
|
|
because the <TT
|
|
CLASS="literal"
|
|
>--implicit-cache</TT
|
|
> causes <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to simply use the implicit
|
|
dependencies stored during the last run, without any checking
|
|
for whether or not those dependencies are still correct.
|
|
Specifically, this means <TT
|
|
CLASS="literal"
|
|
>--implicit-cache</TT
|
|
> instructs <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
to <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
> rebuild "correctly" in the
|
|
following cases:
|
|
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><UL
|
|
><LI
|
|
><P
|
|
>
|
|
When <TT
|
|
CLASS="literal"
|
|
>--implicit-cache</TT
|
|
> is used, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will ignore any changes that
|
|
may have been made to search paths
|
|
(like <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> or <CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
>,).
|
|
This can lead to <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> not rebuilding a file if a change to
|
|
<CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> would normally cause a different, same-named file from
|
|
a different directory to be used.
|
|
|
|
</P
|
|
></LI
|
|
><LI
|
|
><P
|
|
>
|
|
When <TT
|
|
CLASS="literal"
|
|
>--implicit-cache</TT
|
|
> is used, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will not detect if a
|
|
same-named file has been added to a directory that is earlier in
|
|
the search path than the directory in which the file was found
|
|
last time.
|
|
|
|
</P
|
|
></LI
|
|
></UL
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1154"
|
|
>6.4.1. The <TT
|
|
CLASS="literal"
|
|
>--implicit-deps-changed</TT
|
|
> Option</A
|
|
></H3
|
|
><P
|
|
>
|
|
When using cached implicit dependencies,
|
|
sometimes you want to "start fresh"
|
|
and have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> re-scan the files
|
|
for which it previously cached the dependencies.
|
|
For example,
|
|
if you have recently installed a new version of
|
|
external code that you use for compilation,
|
|
the external header files will have changed
|
|
and the previously-cached implicit dependencies
|
|
will be out of date.
|
|
You can update them by
|
|
running <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> with the <TT
|
|
CLASS="literal"
|
|
>--implicit-deps-changed</TT
|
|
> option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --implicit-deps-changed hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will re-scan all of the implicit dependencies
|
|
and cache updated copies of the information.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1166"
|
|
>6.4.2. The <TT
|
|
CLASS="literal"
|
|
>--implicit-deps-unchanged</TT
|
|
> Option</A
|
|
></H3
|
|
><P
|
|
>
|
|
By default when caching dependencies,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> notices when a file has been modified
|
|
and re-scans the file for any updated
|
|
implicit dependency information.
|
|
Sometimes, however, you may want
|
|
to force <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to use the cached implicit dependencies,
|
|
even if the source files changed.
|
|
This can speed up a build for example,
|
|
when you have changed your source files
|
|
but know that you haven't changed
|
|
any <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> lines.
|
|
In this case,
|
|
you can use the <TT
|
|
CLASS="literal"
|
|
>--implicit-deps-unchanged</TT
|
|
> option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --implicit-deps-unchanged hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will assume that the cached implicit
|
|
dependencies are correct and
|
|
will not bother to re-scan changed files.
|
|
For typical builds after small,
|
|
incremental changes to source files,
|
|
the savings may not be very big,
|
|
but sometimes every bit of
|
|
improved performance counts.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1179"
|
|
>6.5. Explicit Dependencies: the <CODE
|
|
CLASS="function"
|
|
>Depends</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Sometimes a file depends on another file
|
|
that is not detected by an <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> scanner.
|
|
For this situation,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> allows you to specific explicitly that one file
|
|
depends on another file,
|
|
and must be rebuilt whenever that file changes.
|
|
This is specified using the <CODE
|
|
CLASS="function"
|
|
>Depends</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello = Program('hello.c')
|
|
Depends(hello, 'other_file')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -c hello.c -o hello.o
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit other_file</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF other_file]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -c hello.c -o hello.o
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the dependency
|
|
(the second argument to <CODE
|
|
CLASS="function"
|
|
>Depends</CODE
|
|
>)
|
|
may also be a list of Node objects
|
|
(for example, as returned by a call to a Builder):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello = Program('hello.c')
|
|
goodbye = Program('goodbye.c')
|
|
Depends(hello, goodbye)
|
|
</PRE
|
|
><P
|
|
>
|
|
in which case the dependency or dependencies
|
|
will be built before the target(s):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -c goodbye.c -o goodbye.o
|
|
cc -o goodbye goodbye.o
|
|
cc -c hello.c -o hello.o
|
|
cc -o hello hello.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1198"
|
|
>6.6. Dependencies From External Files: the <CODE
|
|
CLASS="function"
|
|
>ParseDepends</CODE
|
|
>
|
|
Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has built-in scanners for a number of languages. Sometimes
|
|
these scanners fail to extract certain implicit dependencies due
|
|
to limitations of the scanner implementation.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The following example illustrates a case where the built-in C
|
|
scanner is unable to extract the implicit dependency on a header
|
|
file.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> #define FOO_HEADER <foo.h>
|
|
#include FOO_HEADER
|
|
|
|
int main() {
|
|
return FOO;
|
|
}
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c -I. hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit foo.h</KBD
|
|
>
|
|
[CHANGE CONTENTS OF foo.h]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Apparently, the scanner does not know about the header dependency.
|
|
Being not a full-fledged C preprocessor, the scanner does not
|
|
expand the macro.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
In these cases, you may also use the compiler to extract the
|
|
implicit dependencies. <CODE
|
|
CLASS="function"
|
|
>ParseDepends</CODE
|
|
> can parse the contents of
|
|
the compiler output in the style of <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>, and explicitly
|
|
establish all of the listed dependencies.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The following example uses <CODE
|
|
CLASS="function"
|
|
>ParseDepends</CODE
|
|
> to process a compiler
|
|
generated dependency file which is generated as a side effect
|
|
during compilation of the object file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> obj = Object('hello.c', CCFLAGS='-MD -MF hello.d', CPPPATH='.')
|
|
SideEffect('hello.d', obj)
|
|
ParseDepends('hello.d')
|
|
Program('hello', obj)
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c -MD -MF hello.d -I. hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit foo.h</KBD
|
|
>
|
|
[CHANGE CONTENTS OF foo.h]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c -MD -MF hello.d -I. hello.c
|
|
</PRE
|
|
><P
|
|
>
|
|
Parsing dependencies from a compiler-generated
|
|
<TT
|
|
CLASS="filename"
|
|
>.d</TT
|
|
> file has a chicken-and-egg problem, that
|
|
causes unnecessary rebuilds:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c -MD -MF hello.d -I. hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --debug=explain</KBD
|
|
>
|
|
scons: rebuilding `hello.o' because `foo.h' is a new dependency
|
|
cc -o hello.o -c -MD -MF hello.d -I. hello.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In the first pass, the dependency file is generated while the
|
|
object file is compiled. At that time, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not know about
|
|
the dependency on <TT
|
|
CLASS="filename"
|
|
>foo.h</TT
|
|
>. In the second pass,
|
|
the object file is regenerated because <TT
|
|
CLASS="filename"
|
|
>foo.h</TT
|
|
>
|
|
is detected as a new dependency.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<CODE
|
|
CLASS="function"
|
|
>ParseDepends</CODE
|
|
> immediately reads the specified file at invocation
|
|
time and just returns if the file does not exist. A dependency
|
|
file generated during the build process is not automatically
|
|
parsed again. Hence, the compiler-extracted dependencies are not
|
|
stored in the signature database during the same build pass. This
|
|
limitation of <CODE
|
|
CLASS="function"
|
|
>ParseDepends</CODE
|
|
> leads to unnecessary recompilations.
|
|
Therefore, <CODE
|
|
CLASS="function"
|
|
>ParseDepends</CODE
|
|
> should only be used if scanners are not
|
|
available for the employed language or not powerful enough for the
|
|
specific task.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1234"
|
|
>6.7. Ignoring Dependencies: the <CODE
|
|
CLASS="function"
|
|
>Ignore</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Sometimes it makes sense
|
|
to not rebuild a program,
|
|
even if a dependency file changes.
|
|
In this case,
|
|
you would tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> specifically
|
|
to ignore a dependency as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello = Program('hello.c')
|
|
Ignore(hello, 'hello.h')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -c -o hello.o hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.h</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF hello.h]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Now, the above example is a little contrived,
|
|
because it's hard to imagine a real-world situation
|
|
where you wouldn't want to rebuild <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
>
|
|
if the <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file changed.
|
|
A more realistic example
|
|
might be if the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
>
|
|
program is being built in a
|
|
directory that is shared between multiple systems
|
|
that have different copies of the
|
|
<TT
|
|
CLASS="filename"
|
|
>stdio.h</TT
|
|
> include file.
|
|
In that case,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> would notice the differences between
|
|
the different systems' copies of <TT
|
|
CLASS="filename"
|
|
>stdio.h</TT
|
|
>
|
|
and would rebuild <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
>
|
|
each time you change systems.
|
|
You could avoid these rebuilds as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello = Program('hello.c', CPPPATH=['/usr/include'])
|
|
Ignore(hello, '/usr/include/stdio.h')
|
|
</PRE
|
|
><P
|
|
> <CODE
|
|
CLASS="function"
|
|
>Ignore</CODE
|
|
> can also be used to prevent a generated file from being built
|
|
by default. This is due to the fact that directories depend on
|
|
their contents. So to ignore a generated file from the default build,
|
|
you specify that the directory should ignore the generated file.
|
|
Note that the file will still be built if the user specifically
|
|
requests the target on scons command line, or if the file is
|
|
a dependency of another file which is requested and/or is built
|
|
by default.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello_obj=Object('hello.c')
|
|
hello = Program(hello_obj)
|
|
Ignore('.',[hello,hello_obj])
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1261"
|
|
>6.8. Order-Only Dependencies: the <CODE
|
|
CLASS="function"
|
|
>Requires</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Occasionally,
|
|
it may be useful to specify that a certain
|
|
file or directory must, if necessary,
|
|
be built or created before some other target is built,
|
|
but that changes to that file or directory
|
|
do <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
require that the target itself be rebuilt.
|
|
Such a relationship is called an
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>order-only dependency</I
|
|
></SPAN
|
|
>
|
|
because it only affects the order in which
|
|
things must be built--the dependency before the target--but
|
|
it is not a strict dependency relationship
|
|
because the target should not
|
|
change in response to changes in the dependent file.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose that you want to create a file
|
|
every time you run a build
|
|
that identifies the time the build was performed,
|
|
the version number, etc.,
|
|
and which is included in every program that you build.
|
|
The version file's contents will change every build.
|
|
If you specify a normal dependency relationship,
|
|
then every program that depends on
|
|
that file would be rebuilt every time you ran <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
For example, we could use some Python code in
|
|
a <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file to create a new <TT
|
|
CLASS="filename"
|
|
>version.c</TT
|
|
> file
|
|
with a string containing the current date every time
|
|
we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
and then link a program with the resulting object file
|
|
by listing <TT
|
|
CLASS="filename"
|
|
>version.c</TT
|
|
> in the sources:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import time
|
|
|
|
version_c_text = """
|
|
char *date = "%s";
|
|
""" % time.ctime(time.time())
|
|
open('version.c', 'w').write(version_c_text)
|
|
|
|
hello = Program(['hello.c', 'version.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
If we list <TT
|
|
CLASS="filename"
|
|
>version.c</TT
|
|
> as an actual source file,
|
|
though, then <TT
|
|
CLASS="filename"
|
|
>version.o</TT
|
|
>
|
|
will get rebuilt every time we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
(because the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file itself changes
|
|
the contents of <TT
|
|
CLASS="filename"
|
|
>version.c</TT
|
|
>)
|
|
and the <TT
|
|
CLASS="filename"
|
|
>hello</TT
|
|
> executable
|
|
will get re-linked every time
|
|
(because the <TT
|
|
CLASS="filename"
|
|
>version.o</TT
|
|
> file changes):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
gcc -o hello.o -c hello.c
|
|
gcc -o version.o -c version.c
|
|
gcc -o hello hello.o version.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
gcc -o version.o -c version.c
|
|
gcc -o hello hello.o version.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
gcc -o version.o -c version.c
|
|
gcc -o hello hello.o version.o
|
|
</PRE
|
|
><P
|
|
>
|
|
One solution is to use the <CODE
|
|
CLASS="function"
|
|
>Requires</CODE
|
|
> function
|
|
to specify that the <TT
|
|
CLASS="filename"
|
|
>version.o</TT
|
|
>
|
|
must be rebuilt before it is used by the link step,
|
|
but that changes to <TT
|
|
CLASS="filename"
|
|
>version.o</TT
|
|
>
|
|
should not actually cause the <TT
|
|
CLASS="filename"
|
|
>hello</TT
|
|
>
|
|
executable to be re-linked:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import time
|
|
|
|
version_c_text = """
|
|
char *date = "%s";
|
|
""" % time.ctime(time.time())
|
|
open('version.c', 'w').write(version_c_text)
|
|
|
|
version_obj = Object('version.c')
|
|
|
|
hello = Program('hello.c',
|
|
LINKFLAGS = str(version_obj[0]))
|
|
|
|
Requires(hello, version_obj)
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that because we can no longer list <TT
|
|
CLASS="filename"
|
|
>version.c</TT
|
|
>
|
|
as one of the sources for the <TT
|
|
CLASS="filename"
|
|
>hello</TT
|
|
> program,
|
|
we have to find some other way to get it into the link command line.
|
|
For this example, we're cheating a bit and stuffing the
|
|
object file name (extracted from <TT
|
|
CLASS="literal"
|
|
>version_obj</TT
|
|
>
|
|
list returned by the <CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
> call)
|
|
into the <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
> variable,
|
|
because <CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
> is already included
|
|
in the <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
> command line.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
With these changes,
|
|
we get the desired behavior of
|
|
re-building the <TT
|
|
CLASS="filename"
|
|
>version.o</TT
|
|
> file,
|
|
and therefore re-linking the <TT
|
|
CLASS="filename"
|
|
>hello</TT
|
|
> executable,
|
|
only when the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> has changed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o version.o -c version.c
|
|
cc -o hello version.o hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.c</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF hello.c]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello version.o hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1312"
|
|
>6.9. The <CODE
|
|
CLASS="function"
|
|
>AlwaysBuild</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
How <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> handles dependencies can also be affected
|
|
by the <CODE
|
|
CLASS="function"
|
|
>AlwaysBuild</CODE
|
|
> method.
|
|
When a file is passed to the <CODE
|
|
CLASS="function"
|
|
>AlwaysBuild</CODE
|
|
> method,
|
|
like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> hello = Program('hello.c')
|
|
AlwaysBuild(hello)
|
|
</PRE
|
|
><P
|
|
>
|
|
Then the specified target file (<SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> in our example)
|
|
will always be considered out-of-date and
|
|
rebuilt whenever that target file is evaluated
|
|
while walking the dependency graph:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>AlwaysBuild</CODE
|
|
> function has a somewhat misleading name,
|
|
because it does not actually mean the target file will
|
|
be rebuilt every single time <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is invoked.
|
|
Instead, it means that the target will, in fact,
|
|
be rebuilt whenever the target file is encountered
|
|
while evaluating the targets specified on
|
|
the command line (and their dependencies).
|
|
So specifying some other target on the command line,
|
|
a target that does <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
itself depend on the <CODE
|
|
CLASS="function"
|
|
>AlwaysBuild</CODE
|
|
> target,
|
|
will still be rebuilt only if it's out-of-date
|
|
with respect to its dependencies:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q hello.o</KBD
|
|
>
|
|
scons: `hello.o' is up to date.
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-environments"
|
|
></A
|
|
>Chapter 7. Environments</H1
|
|
><P
|
|
>
|
|
An <TT
|
|
CLASS="literal"
|
|
>environment</TT
|
|
>
|
|
is a collection of values that
|
|
can affect how a program executes.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> distinguishes between three
|
|
different types of environments
|
|
that can affect the behavior of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> itself
|
|
(subject to the configuration in the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files),
|
|
as well as the compilers and other tools it executes:
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
>External Environment</DT
|
|
><DD
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>external environment</TT
|
|
>
|
|
is the set of variables in the user's environment
|
|
at the time the user runs <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
These variables are available within the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
through the Python <TT
|
|
CLASS="literal"
|
|
>os.environ</TT
|
|
> dictionary.
|
|
See <A
|
|
HREF="#sect-external-environments"
|
|
>Section 7.1</A
|
|
>, below.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
><TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
>
|
|
A <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
is a distinct object creating within
|
|
a <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file and
|
|
and which contains values that
|
|
affect how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> decides
|
|
what action to use to build a target,
|
|
and even to define which targets
|
|
should be built from which sources.
|
|
One of the most powerful features of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
is the ability to create multiple <TT
|
|
CLASS="literal"
|
|
>construction environments</TT
|
|
>,
|
|
including the ability to clone a new, customized
|
|
<TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
> from an existing <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>.
|
|
See <A
|
|
HREF="#sect-construction-environments"
|
|
>Section 7.2</A
|
|
>, below.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>Execution Environment</DT
|
|
><DD
|
|
><P
|
|
>
|
|
An <TT
|
|
CLASS="literal"
|
|
>execution environment</TT
|
|
>
|
|
is the values that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> sets
|
|
when executing an external
|
|
command (such as a compiler or linker)
|
|
to build one or more targets.
|
|
Note that this is not the same as
|
|
the <TT
|
|
CLASS="literal"
|
|
>external environment</TT
|
|
>
|
|
(see above).
|
|
See <A
|
|
HREF="#sect-execution-environments"
|
|
>Section 7.3</A
|
|
>, below.
|
|
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
><P
|
|
>
|
|
Unlike <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not automatically
|
|
copy or import values between different environments
|
|
(with the exception of explicit clones of <TT
|
|
CLASS="literal"
|
|
>construction environments</TT
|
|
>,
|
|
which inherit values from their parent).
|
|
This is a deliberate design choice
|
|
to make sure that builds are,
|
|
by default, repeatable regardless of
|
|
the values in the user's external environment.
|
|
This avoids a whole class of problems with builds
|
|
where a developer's local build works
|
|
because a custom variable setting
|
|
causes a different comiler or build option to be used,
|
|
but the checked-in change breaks the official build
|
|
because it uses different environment variable settings.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> writer can
|
|
easily arrange for variables to be
|
|
copied or imported between environments,
|
|
and this is often very useful
|
|
(or even downright necessary)
|
|
to make it easy for developers
|
|
to customize the build in appropriate ways.
|
|
The point is <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
that copying variables between different environments
|
|
is evil and must always be avoided.
|
|
Instead, it should be up to the
|
|
implementer of the build system
|
|
to make conscious choices
|
|
about how and when to import
|
|
a variable from one environment to another,
|
|
making informed decisions about
|
|
striking the right balance
|
|
between making the build
|
|
repeatable on the one hand
|
|
and convenient to use on the other.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="sect-external-environments"
|
|
>7.1. Using Values From the External Environment</A
|
|
></H2
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>external environment</TT
|
|
>
|
|
variable settings that
|
|
the user has in force
|
|
when executing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
are available through the normal Python
|
|
<CODE
|
|
CLASS="envar"
|
|
>os.environ</CODE
|
|
>
|
|
dictionary.
|
|
This means that you must add an
|
|
<TT
|
|
CLASS="literal"
|
|
>import os</TT
|
|
> statuement
|
|
to any <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file
|
|
in which you want to use
|
|
values from the user's external environment.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os
|
|
</PRE
|
|
><P
|
|
>
|
|
More usefully, you can use the
|
|
<CODE
|
|
CLASS="envar"
|
|
>os.environ</CODE
|
|
>
|
|
dictionary in your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>
|
|
files to initialize <TT
|
|
CLASS="literal"
|
|
>construction environments</TT
|
|
>
|
|
with values from the user's external environment.
|
|
See the next section,
|
|
<A
|
|
HREF="#sect-construction-environments"
|
|
>Section 7.2</A
|
|
>,
|
|
for information on how to do this.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="sect-construction-environments"
|
|
>7.2. Construction Environments</A
|
|
></H2
|
|
><P
|
|
>
|
|
It is rare that all of the software in a large,
|
|
complicated system needs to be built the same way.
|
|
For example, different source files may need different options
|
|
enabled on the command line,
|
|
or different executable programs need to be linked
|
|
with different libraries.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> accommodates these different build
|
|
requirements by allowing you to create and
|
|
configure multiple <TT
|
|
CLASS="literal"
|
|
>construction environments</TT
|
|
>
|
|
that control how the software is built.
|
|
A <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
> is an object
|
|
that has a number of associated
|
|
<TT
|
|
CLASS="literal"
|
|
>construction variables</TT
|
|
>, each with a name and a value.
|
|
(A construction environment also has an attached
|
|
set of <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> methods,
|
|
about which we'll learn more later.)
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1400"
|
|
>7.2.1. Creating a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
A <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
> is created by the <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
</PRE
|
|
><P
|
|
>
|
|
By default, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> initializes every
|
|
new construction environment
|
|
with a set of <TT
|
|
CLASS="literal"
|
|
>construction variables</TT
|
|
>
|
|
based on the tools that it finds on your system,
|
|
plus the default set of builder methods
|
|
necessary for using those tools.
|
|
The construction variables
|
|
are initialized with values describing
|
|
the C compiler,
|
|
the Fortran compiler,
|
|
the linker,
|
|
etc.,
|
|
as well as the command lines to invoke them.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
When you initialize a construction environment
|
|
you can set the values of the
|
|
environment's <TT
|
|
CLASS="literal"
|
|
>construction variables</TT
|
|
>
|
|
to control how a program is built.
|
|
For example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os
|
|
|
|
env = Environment(CC = 'gcc',
|
|
CCFLAGS = '-O2')
|
|
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
The construction environment in this example
|
|
is still initialized with the same default
|
|
construction variable values,
|
|
except that the user has explicitly specified use of the
|
|
GNU C compiler <SPAN
|
|
CLASS="application"
|
|
>gcc</SPAN
|
|
>,
|
|
and further specifies that the <TT
|
|
CLASS="literal"
|
|
>-O2</TT
|
|
>
|
|
(optimization level two)
|
|
flag should be used when compiling the object file.
|
|
In other words, the explicit initializations of
|
|
<A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>
|
|
override the default values in the newly-created
|
|
construction environment.
|
|
So a run from this example would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
gcc -o foo.o -c -O2 foo.c
|
|
gcc -o foo foo.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1423"
|
|
>7.2.2. Fetching Values From a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
></A
|
|
></H3
|
|
><P
|
|
>
|
|
You can fetch individual construction variables
|
|
using the normal syntax
|
|
for accessing individual named items in a Python dictionary:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
print "CC is:", env['CC']
|
|
</PRE
|
|
><P
|
|
>
|
|
This example <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file doesn't build anything,
|
|
but because it's actually a Python script,
|
|
it will print the value of <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
> for us:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CC is: cc
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
A construction environment, however,
|
|
is actually an object with associated methods, etc.
|
|
If you want to have direct access to only the
|
|
dictionary of construction variables,
|
|
you can fetch this using the <TT
|
|
CLASS="literal"
|
|
>Dictionary</TT
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(FOO = 'foo', BAR = 'bar')
|
|
dict = env.Dictionary()
|
|
for key in ['OBJSUFFIX', 'LIBSUFFIX', 'PROGSUFFIX']:
|
|
print "key = %s, value = %s" % (key, dict[key])
|
|
</PRE
|
|
><P
|
|
>
|
|
This <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
will print the specified dictionary items for us on POSIX
|
|
systems as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
key = OBJSUFFIX, value = .o
|
|
key = LIBSUFFIX, value = .a
|
|
key = PROGSUFFIX, value =
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
And on Windows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
key = OBJSUFFIX, value = .obj
|
|
key = LIBSUFFIX, value = .lib
|
|
key = PROGSUFFIX, value = .exe
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
If you want to loop and print the values of
|
|
all of the construction variables in a construction environment,
|
|
the Python code to do that in sorted order might look something like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
dict = env.Dictionary()
|
|
keys = dict.keys()
|
|
keys.sort()
|
|
for key in keys:
|
|
print "construction variable = '%s', value = '%s'" % (key, dict[key])
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1446"
|
|
>7.2.3. Expanding Values From a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>subst</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
Another way to get information from
|
|
a construction environment.
|
|
is to use the <CODE
|
|
CLASS="function"
|
|
>subst</CODE
|
|
> method
|
|
on a string containing <TT
|
|
CLASS="literal"
|
|
>$</TT
|
|
> expansions
|
|
of construction variable names.
|
|
As a simple example,
|
|
the example from the previous
|
|
section that used
|
|
<TT
|
|
CLASS="literal"
|
|
>env['CC']</TT
|
|
>
|
|
to fetch the value of <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>
|
|
could also be written as:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
print "CC is:", env.subst('$CC')
|
|
</PRE
|
|
><P
|
|
>
|
|
One advantage of using
|
|
<CODE
|
|
CLASS="function"
|
|
>subst</CODE
|
|
> to expand strings is
|
|
that construction variables
|
|
in the result get re-expanded until
|
|
there are no expansions left in the string.
|
|
So a simple fetch of a value like
|
|
<A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCFLAGS = '-DFOO')
|
|
print "CCCOM is:", env['CCCOM']
|
|
</PRE
|
|
><P
|
|
>
|
|
Will print the unexpanded value of <CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
>,
|
|
showing us the construction
|
|
variables that still need to be expanded:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CCCOM is: $CC $CCFLAGS $CPPFLAGS $_CPPDEFFLAGS $_CPPINCFLAGS -c -o $TARGET $SOURCES
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Calling the <CODE
|
|
CLASS="function"
|
|
>subst</CODE
|
|
> method on <CODE
|
|
CLASS="varname"
|
|
>$CCOM</CODE
|
|
>,
|
|
however:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCFLAGS = '-DFOO')
|
|
print "CCCOM is:", env.subst('$CCCOM')
|
|
</PRE
|
|
><P
|
|
>
|
|
Will recursively expand all of
|
|
the construction variables prefixed
|
|
with <TT
|
|
CLASS="literal"
|
|
>$</TT
|
|
> (dollar signs),
|
|
showing us the final output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CCCOM is: gcc -DFOO -c -o
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that because we're not expanding this
|
|
in the context of building something
|
|
there are no target or source files
|
|
for <A
|
|
HREF="#cv-TARGET"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARGET</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-SOURCES"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SOURCES</CODE
|
|
></A
|
|
> to expand.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1479"
|
|
>7.2.4. Controlling the Default <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>DefaultEnvironment</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
All of the <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> functions that we've introduced so far,
|
|
like <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
>,
|
|
actually use a default <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
that contains settings
|
|
for the various compilers
|
|
and other tools that
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> configures by default,
|
|
or otherwise knows about
|
|
and has discovered on your system.
|
|
The goal of the default construction environment
|
|
is to make many configurations to "just work"
|
|
to build software using
|
|
readily available tools
|
|
with a minimum of configuration changes.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
You can, however, control the settings
|
|
in the default contstruction environment
|
|
by using the <CODE
|
|
CLASS="function"
|
|
>DefaultEnvironment</CODE
|
|
> function
|
|
to initialize various settings:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
>
|
|
DefaultEnvironment(CC = '/usr/local/bin/gcc')
|
|
|
|
</PRE
|
|
><P
|
|
>
|
|
When configured as above,
|
|
all calls to the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
>
|
|
or <CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
> Builder
|
|
will build object files with the
|
|
<TT
|
|
CLASS="filename"
|
|
>/usr/local/bin/gcc</TT
|
|
>
|
|
compiler.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that the <CODE
|
|
CLASS="function"
|
|
>DefaultEnvironment</CODE
|
|
> function
|
|
returns the initialized
|
|
default construction environment object,
|
|
which can then be manipulated like any
|
|
other construction environment.
|
|
So the following
|
|
would be equivalent to the
|
|
previous example,
|
|
setting the <CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
>
|
|
variable to <TT
|
|
CLASS="filename"
|
|
>/usr/local/bin/gcc</TT
|
|
>
|
|
but as a separate step after
|
|
the default construction environment has been initialized:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
>
|
|
env = DefaultEnvironment()
|
|
env['CC'] = '/usr/local/bin/gcc'
|
|
|
|
</PRE
|
|
><P
|
|
>
|
|
One very common use of the <CODE
|
|
CLASS="function"
|
|
>DefaultEnvironment</CODE
|
|
> function
|
|
is to speed up <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> initialization.
|
|
As part of trying to make most default
|
|
configurations "just work,"
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will actually
|
|
search the local system for installed
|
|
compilers and other utilities.
|
|
This search can take time,
|
|
especially on systems with
|
|
slow or networked file systems.
|
|
If you know which compiler(s) and/or
|
|
other utilities you want to configure,
|
|
you can control the search
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> performs
|
|
by specifying some specific
|
|
tool modules with which to
|
|
initialize the default construction environment:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
>
|
|
env = DefaultEnvironment(tools = ['gcc', 'gnulink'],
|
|
CC = '/usr/local/bin/gcc')
|
|
|
|
</PRE
|
|
><P
|
|
>
|
|
So the above example would tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
to explicitly configure the default environment
|
|
to use its normal GNU Compiler and GNU Linker settings
|
|
(without having to search for them,
|
|
or any other utilities for that matter),
|
|
and specifically to use the compiler found at
|
|
<TT
|
|
CLASS="filename"
|
|
>/usr/local/bin/gcc</TT
|
|
>.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1510"
|
|
>7.2.5. Multiple <TT
|
|
CLASS="literal"
|
|
>Construction Environments</TT
|
|
></A
|
|
></H3
|
|
><P
|
|
>
|
|
The real advantage of construction environments
|
|
is that you can create as many different construction
|
|
environments as you need,
|
|
each tailored to a different way to build
|
|
some piece of software or other file.
|
|
If, for example, we need to build
|
|
one program with the <TT
|
|
CLASS="literal"
|
|
>-O2</TT
|
|
> flag
|
|
and another with the <TT
|
|
CLASS="literal"
|
|
>-g</TT
|
|
> (debug) flag,
|
|
we would do this like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> opt = Environment(CCFLAGS = '-O2')
|
|
dbg = Environment(CCFLAGS = '-g')
|
|
|
|
opt.Program('foo', 'foo.c')
|
|
|
|
dbg.Program('bar', 'bar.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o bar.o -c -g bar.c
|
|
cc -o bar bar.o
|
|
cc -o foo.o -c -O2 foo.c
|
|
cc -o foo foo.o
|
|
</PRE
|
|
><P
|
|
>
|
|
We can even use multiple construction environments to build
|
|
multiple versions of a single program.
|
|
If you do this by simply trying to use the
|
|
<A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
> builder with both environments, though,
|
|
like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> opt = Environment(CCFLAGS = '-O2')
|
|
dbg = Environment(CCFLAGS = '-g')
|
|
|
|
opt.Program('foo', 'foo.c')
|
|
|
|
dbg.Program('foo', 'foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> generates the following error:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
|
|
scons: *** Two environments with different actions were specified for the same target: foo.o
|
|
File "/home/my/project/SConstruct", line 6, in <module>
|
|
</PRE
|
|
><P
|
|
>
|
|
This is because the two <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> calls have
|
|
each implicitly told <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to generate an object file named
|
|
<TT
|
|
CLASS="filename"
|
|
>foo.o</TT
|
|
>,
|
|
one with a <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
> value of
|
|
<TT
|
|
CLASS="literal"
|
|
>-O2</TT
|
|
>
|
|
and one with a <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
> value of
|
|
<TT
|
|
CLASS="literal"
|
|
>-g</TT
|
|
>.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> can't just decide that one of them
|
|
should take precedence over the other,
|
|
so it generates the error.
|
|
To avoid this problem,
|
|
we must explicitly specify
|
|
that each environment compile
|
|
<TT
|
|
CLASS="filename"
|
|
>foo.c</TT
|
|
>
|
|
to a separately-named object file
|
|
using the <A
|
|
HREF="#b-Object"
|
|
><CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
></A
|
|
> builder, like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> opt = Environment(CCFLAGS = '-O2')
|
|
dbg = Environment(CCFLAGS = '-g')
|
|
|
|
o = opt.Object('foo-opt', 'foo.c')
|
|
opt.Program(o)
|
|
|
|
d = dbg.Object('foo-dbg', 'foo.c')
|
|
dbg.Program(d)
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that each call to the <CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
> builder
|
|
returns a value,
|
|
an internal <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> object that
|
|
represents the object file that will be built.
|
|
We then use that object
|
|
as input to the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> builder.
|
|
This avoids having to specify explicitly
|
|
the object file name in multiple places,
|
|
and makes for a compact, readable
|
|
<TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file.
|
|
Our <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> output then looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o foo-dbg.o -c -g foo.c
|
|
cc -o foo-dbg foo-dbg.o
|
|
cc -o foo-opt.o -c -O2 foo.c
|
|
cc -o foo-opt foo-opt.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1550"
|
|
>7.2.6. Making Copies of <TT
|
|
CLASS="literal"
|
|
>Construction Environments</TT
|
|
>: the <CODE
|
|
CLASS="function"
|
|
>Clone</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
Sometimes you want more than one construction environment
|
|
to share the same values for one or more variables.
|
|
Rather than always having to repeat all of the common
|
|
variables when you create each construction environment,
|
|
you can use the <CODE
|
|
CLASS="function"
|
|
>Clone</CODE
|
|
> method
|
|
to create a copy of a construction environment.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Like the <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> call that creates a construction environment,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Clone</CODE
|
|
> method takes <TT
|
|
CLASS="literal"
|
|
>construction variable</TT
|
|
> assignments,
|
|
which will override the values in the copied construction environment.
|
|
For example, suppose we want to use <SPAN
|
|
CLASS="application"
|
|
>gcc</SPAN
|
|
>
|
|
to create three versions of a program,
|
|
one optimized, one debug, and one with neither.
|
|
We could do this by creating a "base" construction environment
|
|
that sets <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
> to <SPAN
|
|
CLASS="application"
|
|
>gcc</SPAN
|
|
>,
|
|
and then creating two copies,
|
|
one which sets <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
> for optimization
|
|
and the other which sets <CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
> for debugging:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CC = 'gcc')
|
|
opt = env.Clone(CCFLAGS = '-O2')
|
|
dbg = env.Clone(CCFLAGS = '-g')
|
|
|
|
env.Program('foo', 'foo.c')
|
|
|
|
o = opt.Object('foo-opt', 'foo.c')
|
|
opt.Program(o)
|
|
|
|
d = dbg.Object('foo-dbg', 'foo.c')
|
|
dbg.Program(d)
|
|
</PRE
|
|
><P
|
|
>
|
|
Then our output would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
gcc -o foo.o -c foo.c
|
|
gcc -o foo foo.o
|
|
gcc -o foo-dbg.o -c -g foo.c
|
|
gcc -o foo-dbg foo-dbg.o
|
|
gcc -o foo-opt.o -c -O2 foo.c
|
|
gcc -o foo-opt foo-opt.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1571"
|
|
>7.2.7. Replacing Values: the <CODE
|
|
CLASS="function"
|
|
>Replace</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
You can replace existing construction variable values
|
|
using the <CODE
|
|
CLASS="function"
|
|
>Replace</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCFLAGS = '-DDEFINE1')
|
|
env.Replace(CCFLAGS = '-DDEFINE2')
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
The replacing value
|
|
(<TT
|
|
CLASS="literal"
|
|
>-DDEFINE2</TT
|
|
> in the above example)
|
|
completely replaces the value in the
|
|
construction environment:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o foo.o -c -DDEFINE2 foo.c
|
|
cc -o foo foo.o
|
|
</PRE
|
|
><P
|
|
>
|
|
You can safely call <CODE
|
|
CLASS="function"
|
|
>Replace</CODE
|
|
>
|
|
for construction variables that
|
|
don't exist in the construction environment:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Replace(NEW_VARIABLE = 'xyzzy')
|
|
print "NEW_VARIABLE =", env['NEW_VARIABLE']
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case,
|
|
the construction variable simply
|
|
gets added to the construction environment:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
NEW_VARIABLE = xyzzy
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Because the variables
|
|
aren't expanded until the construction environment
|
|
is actually used to build the targets,
|
|
and because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> function and method calls
|
|
are order-independent,
|
|
the last replacement "wins"
|
|
and is used to build all targets,
|
|
regardless of the order in which
|
|
the calls to Replace() are
|
|
interspersed with calls to
|
|
builder methods:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCFLAGS = '-DDEFINE1')
|
|
print "CCFLAGS =", env['CCFLAGS']
|
|
env.Program('foo.c')
|
|
|
|
env.Replace(CCFLAGS = '-DDEFINE2')
|
|
print "CCFLAGS =", env['CCFLAGS']
|
|
env.Program('bar.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
The timing of when the replacement
|
|
actually occurs relative
|
|
to when the targets get built
|
|
becomes apparent
|
|
if we run <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> without the <TT
|
|
CLASS="literal"
|
|
>-Q</TT
|
|
>
|
|
option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
CCFLAGS = -DDEFINE1
|
|
CCFLAGS = -DDEFINE2
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cc -o bar.o -c -DDEFINE2 bar.c
|
|
cc -o bar bar.o
|
|
cc -o foo.o -c -DDEFINE2 foo.c
|
|
cc -o foo foo.o
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
Because the replacement occurs while
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files are being read,
|
|
the <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>
|
|
variable has already been set to
|
|
<TT
|
|
CLASS="literal"
|
|
>-DDEFINE2</TT
|
|
>
|
|
by the time the <TT
|
|
CLASS="filename"
|
|
>foo.o</TT
|
|
> target is built,
|
|
even though the call to the <CODE
|
|
CLASS="function"
|
|
>Replace</CODE
|
|
>
|
|
method does not occur until later in
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1603"
|
|
>7.2.8. Setting Values Only If They're Not Already Defined: the <CODE
|
|
CLASS="function"
|
|
>SetDefault</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
Sometimes it's useful to be able to specify
|
|
that a construction variable should be
|
|
set to a value only if the construction environment
|
|
does not already have that variable defined
|
|
You can do this with the <CODE
|
|
CLASS="function"
|
|
>SetDefault</CODE
|
|
> method,
|
|
which behaves similarly to the <CODE
|
|
CLASS="function"
|
|
>set_default</CODE
|
|
>
|
|
method of Python dictionary objects:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.SetDefault(SPECIAL_FLAG = '-extra-option')
|
|
</PRE
|
|
><P
|
|
>
|
|
This is especially useful
|
|
when writing your own <TT
|
|
CLASS="literal"
|
|
>Tool</TT
|
|
> modules
|
|
to apply variables to construction environments.
|
|
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1612"
|
|
>7.2.9. Appending to the End of Values: the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
You can append a value to
|
|
an existing construction variable
|
|
using the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCFLAGS = ['-DMY_VALUE'])
|
|
env.Append(CCFLAGS = ['-DLAST'])
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> then supplies both the <TT
|
|
CLASS="literal"
|
|
>-DMY_VALUE</TT
|
|
> and
|
|
<TT
|
|
CLASS="literal"
|
|
>-DLAST</TT
|
|
> flags when compiling the object file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o foo.o -c -DMY_VALUE -DLAST foo.c
|
|
cc -o foo foo.o
|
|
</PRE
|
|
><P
|
|
>
|
|
If the construction variable doesn't already exist,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> method will create it:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Append(NEW_VARIABLE = 'added')
|
|
print "NEW_VARIABLE =", env['NEW_VARIABLE']
|
|
</PRE
|
|
><P
|
|
>
|
|
Which yields:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
NEW_VARIABLE = added
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> function tries to be "smart"
|
|
about how the new value is appended to the old value.
|
|
If both are strings, the previous and new strings
|
|
are simply concatenated.
|
|
Similarly, if both are lists,
|
|
the lists are concatenated.
|
|
If, however, one is a string and the other is a list,
|
|
the string is added as a new element to the list.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1632"
|
|
>7.2.10. Appending Unique Values: the <CODE
|
|
CLASS="function"
|
|
>AppendUnique</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
Some times it's useful to add a new value
|
|
only if the existing construction variable
|
|
doesn't already contain the value.
|
|
This can be done using the <CODE
|
|
CLASS="function"
|
|
>AppendUnique</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.AppendUnique(CCFLAGS=['-g'])
|
|
</PRE
|
|
><P
|
|
>
|
|
In the above example,
|
|
the <TT
|
|
CLASS="literal"
|
|
>-g</TT
|
|
> would be added
|
|
only if the <CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
> variable
|
|
does not already contain a <TT
|
|
CLASS="literal"
|
|
>-g</TT
|
|
> value.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1642"
|
|
>7.2.11. Appending to the Beginning of Values: the <CODE
|
|
CLASS="function"
|
|
>Prepend</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
You can append a value to the beginning of
|
|
an existing construction variable
|
|
using the <CODE
|
|
CLASS="function"
|
|
>Prepend</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCFLAGS = ['-DMY_VALUE'])
|
|
env.Prepend(CCFLAGS = ['-DFIRST'])
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> then supplies both the <TT
|
|
CLASS="literal"
|
|
>-DFIRST</TT
|
|
> and
|
|
<TT
|
|
CLASS="literal"
|
|
>-DMY_VALUE</TT
|
|
> flags when compiling the object file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o foo.o -c -DFIRST -DMY_VALUE foo.c
|
|
cc -o foo foo.o
|
|
</PRE
|
|
><P
|
|
>
|
|
If the construction variable doesn't already exist,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Prepend</CODE
|
|
> method will create it:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Prepend(NEW_VARIABLE = 'added')
|
|
print "NEW_VARIABLE =", env['NEW_VARIABLE']
|
|
</PRE
|
|
><P
|
|
>
|
|
Which yields:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
NEW_VARIABLE = added
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Like the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> function,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Prepend</CODE
|
|
> function tries to be "smart"
|
|
about how the new value is appended to the old value.
|
|
If both are strings, the previous and new strings
|
|
are simply concatenated.
|
|
Similarly, if both are lists,
|
|
the lists are concatenated.
|
|
If, however, one is a string and the other is a list,
|
|
the string is added as a new element to the list.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1663"
|
|
>7.2.12. Prepending Unique Values: the <CODE
|
|
CLASS="function"
|
|
>PrependUnique</CODE
|
|
> Method</A
|
|
></H3
|
|
><P
|
|
>
|
|
Some times it's useful to add a new value
|
|
to the beginning of a construction variable
|
|
only if the existing value
|
|
doesn't already contain the to-be-added value.
|
|
This can be done using the <CODE
|
|
CLASS="function"
|
|
>PrependUnique</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.PrependUnique(CCFLAGS=['-g'])
|
|
</PRE
|
|
><P
|
|
>
|
|
In the above example,
|
|
the <TT
|
|
CLASS="literal"
|
|
>-g</TT
|
|
> would be added
|
|
only if the <CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
> variable
|
|
does not already contain a <TT
|
|
CLASS="literal"
|
|
>-g</TT
|
|
> value.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="sect-execution-environments"
|
|
>7.3. Controlling the Execution Environment for Issued Commands</A
|
|
></H2
|
|
><P
|
|
>
|
|
When <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> builds a target file,
|
|
it does not execute the commands with
|
|
the same external environment
|
|
that you used to execute <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
Instead, it uses the dictionary
|
|
stored in the <A
|
|
HREF="#cv-ENV"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ENV</CODE
|
|
></A
|
|
> construction variable
|
|
as the external environment
|
|
for executing commands.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The most important ramification of this behavior
|
|
is that the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> environment variable,
|
|
which controls where the operating system
|
|
will look for commands and utilities,
|
|
is not the same as in the external environment
|
|
from which you called <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
This means that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will not, by default,
|
|
necessarily find all of the tools
|
|
that you can execute from the command line.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The default value of the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> environment variable
|
|
on a POSIX system
|
|
is <TT
|
|
CLASS="literal"
|
|
>/usr/local/bin:/bin:/usr/bin</TT
|
|
>.
|
|
The default value of the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> environment variable
|
|
on a Windows system comes from the Windows registry
|
|
value for the command interpreter.
|
|
If you want to execute any commands--compilers, linkers, etc.--that
|
|
are not in these default locations,
|
|
you need to set the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> value
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$ENV</CODE
|
|
> dictionary
|
|
in your construction environment.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The simplest way to do this is to initialize explicitly
|
|
the value when you create the construction environment;
|
|
this is one way to do that:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> path = ['/usr/local/bin', '/bin', '/usr/bin']
|
|
env = Environment(ENV = {'PATH' : path})
|
|
</PRE
|
|
><P
|
|
>
|
|
Assign a dictionary to the <CODE
|
|
CLASS="envar"
|
|
>$ENV</CODE
|
|
>
|
|
construction variable in this way
|
|
completely resets the external environment
|
|
so that the only variable that will be
|
|
set when external commands are executed
|
|
will be the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> value.
|
|
If you want to use the rest of
|
|
the values in <CODE
|
|
CLASS="envar"
|
|
>$ENV</CODE
|
|
> and only
|
|
set the value of <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
>,
|
|
the most straightforward way is probably:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['ENV']['PATH'] = ['/usr/local/bin', '/bin', '/usr/bin']
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does allow you to define
|
|
the directories in the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> in a string,
|
|
separated by the pathname-separator character
|
|
for your system (':' on POSIX systems, ';' on Windows):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['ENV']['PATH'] = '/usr/local/bin:/bin:/usr/bin'
|
|
</PRE
|
|
><P
|
|
>
|
|
But doing so makes your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file less portable,
|
|
(although in this case that may not be a huge concern
|
|
since the directories you list are likley system-specific, anyway).
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1704"
|
|
>7.3.1. Propagating <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> From the External Environment</A
|
|
></H3
|
|
><P
|
|
>
|
|
You may want to propagate the external <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
>
|
|
to the execution environment for commands.
|
|
You do this by initializing the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
>
|
|
variable with the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> value from
|
|
the <TT
|
|
CLASS="literal"
|
|
>os.environ</TT
|
|
>
|
|
dictionary,
|
|
which is Python's way of letting you
|
|
get at the external environment:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os
|
|
env = Environment(ENV = {'PATH' : os.environ['PATH']})
|
|
</PRE
|
|
><P
|
|
>
|
|
Alternatively, you may find it easier
|
|
to just propagate the entire external
|
|
environment to the execution environment
|
|
for commands.
|
|
This is simpler to code than explicity
|
|
selecting the <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> value:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os
|
|
env = Environment(ENV = os.environ)
|
|
</PRE
|
|
><P
|
|
>
|
|
Either of these will guarantee that
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will be able to execute
|
|
any command that you can execute from the command line.
|
|
The drawback is that the build can behave
|
|
differently if it's run by people with
|
|
different <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> values in their environment--for example,
|
|
if both the <TT
|
|
CLASS="literal"
|
|
>/bin</TT
|
|
> and
|
|
<TT
|
|
CLASS="literal"
|
|
>/usr/local/bin</TT
|
|
> directories
|
|
have different <SPAN
|
|
CLASS="application"
|
|
>cc</SPAN
|
|
> commands,
|
|
then which one will be used to compile programs
|
|
will depend on which directory is listed
|
|
first in the user's <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> variable.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1723"
|
|
>7.3.2. Adding to <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
> Values in the Execution Environment</A
|
|
></H3
|
|
><P
|
|
>
|
|
One of the most common requirements
|
|
for manipulating a variable in the execution environment
|
|
is to add one or more custom directories to a search
|
|
like the <CODE
|
|
CLASS="envar"
|
|
>$PATH</CODE
|
|
> variable on Linux or POSIX systems,
|
|
or the <CODE
|
|
CLASS="envar"
|
|
>%PATH%</CODE
|
|
> variable on Windows,
|
|
so that a locally-installed compiler or other utility
|
|
can be found when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> tries to execute it to update a target.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides <CODE
|
|
CLASS="function"
|
|
>PrependENVPath</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>AppendENVPath</CODE
|
|
> functions
|
|
to make adding things to execution variables convenient.
|
|
You call these functions by specifying the variable
|
|
to which you want the value added,
|
|
and then value itself.
|
|
So to add some <TT
|
|
CLASS="filename"
|
|
>/usr/local</TT
|
|
> directories
|
|
to the <CODE
|
|
CLASS="envar"
|
|
>$PATH</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$LIB</CODE
|
|
> variables,
|
|
you might:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(ENV = os.environ)
|
|
env.PrependENVPath('PATH', '/usr/local/bin')
|
|
env.AppendENVPath('LIB', '/usr/local/lib')
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the added values are strings,
|
|
and if you want to add multiple directories to
|
|
a variable like <CODE
|
|
CLASS="envar"
|
|
>$PATH</CODE
|
|
>,
|
|
you must include the path separate character
|
|
(<TT
|
|
CLASS="literal"
|
|
>:</TT
|
|
> on Linux or POSIX,
|
|
<TT
|
|
CLASS="literal"
|
|
>;</TT
|
|
> on Windows)
|
|
in the string.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-mergeflags"
|
|
></A
|
|
>Chapter 8. Merging Options into the Environment: the <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> Function</H1
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> construction environments have a <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> method
|
|
that merges a dictionary of values into the construction environment.
|
|
<CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> treats each value in the dictionary
|
|
as a list of options such as one might pass to a command
|
|
(such as a compiler or linker).
|
|
<CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> will not duplicate an option
|
|
if it already exists in the construction environment variable.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> tries to be intelligent about merging options.
|
|
When merging options to any variable
|
|
whose name ends in <CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> keeps the leftmost occurrence of the option,
|
|
because in typical lists of directory paths,
|
|
the first occurrence "wins."
|
|
When merging options to any other variable name,
|
|
<CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> keeps the rightmost occurrence of the option,
|
|
because in a list of typical command-line options,
|
|
the last occurrence "wins."
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Append(CCFLAGS = '-option -O3 -O1')
|
|
flags = { 'CCFLAGS' : '-whatever -O3' }
|
|
env.MergeFlags(flags)
|
|
print env['CCFLAGS']
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
['-option', '-O1', '-whatever', '-O3']
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the default value for <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>
|
|
|
|
is an internal <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> object
|
|
which automatically converts
|
|
the options we specified as a string into a list.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Append(CPPPATH = ['/include', '/usr/local/include', '/usr/include'])
|
|
flags = { 'CPPPATH' : ['/usr/opt/include', '/usr/local/include'] }
|
|
env.MergeFlags(flags)
|
|
print env['CPPPATH']
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
['/include', '/usr/local/include', '/usr/include', '/usr/opt/include']
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the default value for <A
|
|
HREF="#cv-CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
></A
|
|
>
|
|
|
|
is a normal Python list,
|
|
so we must specify its values as a list
|
|
in the dictionary we pass to the <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> function.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> is passed anything other than a dictionary,
|
|
it calls the <CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> method to convert it into a dictionary.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Append(CCFLAGS = '-option -O3 -O1')
|
|
env.Append(CPPPATH = ['/include', '/usr/local/include', '/usr/include'])
|
|
env.MergeFlags('-whatever -I/usr/opt/include -O3 -I/usr/local/include')
|
|
print env['CCFLAGS']
|
|
print env['CPPPATH']
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
['-option', '-O1', '-whatever', '-O3']
|
|
['/include', '/usr/local/include', '/usr/include', '/usr/opt/include']
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In the combined example above,
|
|
<CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> has sorted the options into their corresponding variables
|
|
and returned a dictionary for <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> to apply
|
|
to the construction variables
|
|
in the specified construction environment.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-parseflags"
|
|
></A
|
|
>Chapter 9. Separating Compile Arguments into their Variables: the <CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> Function</H1
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has a bewildering array of construction variables
|
|
for different types of options when building programs.
|
|
Sometimes you may not know exactly which variable
|
|
should be used for a particular option.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> construction environments have a <CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> method
|
|
that takes a set of typical command-line options
|
|
and distrbutes them into the appropriate construction variables.
|
|
Historically, it was created to support the <CODE
|
|
CLASS="function"
|
|
>ParseConfig</CODE
|
|
> method,
|
|
so it focuses on options used by the GNU Compiler Collection (GCC)
|
|
for the C and C++ toolchains.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> returns a dictionary containing the options
|
|
distributed into their respective construction variables.
|
|
Normally, this dictionary would be passed to <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
>
|
|
to merge the options into a <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>,
|
|
but the dictionary can be edited if desired to provide
|
|
additional functionality.
|
|
(Note that if the flags are not going to be edited,
|
|
calling <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> with the options directly
|
|
will avoid an additional step.)
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
d = env.ParseFlags("-I/opt/include -L/opt/lib -lfoo")
|
|
l = d.items()
|
|
l.sort()
|
|
for k,v in l:
|
|
if v:
|
|
print k, v
|
|
env.MergeFlags(d)
|
|
env.Program('f1.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CPPPATH ['/opt/include']
|
|
LIBPATH ['/opt/lib']
|
|
LIBS ['foo']
|
|
cc -o f1.o -c -I/opt/include f1.c
|
|
cc -o f1 f1.o -L/opt/lib -lfoo
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that if the options are limited to generic types
|
|
like those above,
|
|
they will be correctly translated for other platform types:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CPPPATH ['/opt/include']
|
|
LIBPATH ['/opt/lib']
|
|
LIBS ['foo']
|
|
cl /nologo /I\opt\include /c f1.c /Fof1.obj
|
|
link /nologo /OUT:f1.exe /LIBPATH:\opt\lib foo.lib f1.obj
|
|
</PRE
|
|
><P
|
|
>
|
|
Since the assumption is that the flags are used for the GCC toolchain,
|
|
unrecognized flags are placed in <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>
|
|
so they will be used for both C and C++ compiles:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
d = env.ParseFlags("-whatever")
|
|
l = d.items()
|
|
l.sort()
|
|
for k,v in l:
|
|
if v:
|
|
print k, v
|
|
env.MergeFlags(d)
|
|
env.Program('f1.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CCFLAGS -whatever
|
|
cc -o f1.o -c -whatever f1.c
|
|
cc -o f1 f1.o
|
|
</PRE
|
|
><P
|
|
>
|
|
<CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> will also accept a (recursive) list of strings as input;
|
|
the list is flattened before the strings are processed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
d = env.ParseFlags(["-I/opt/include", ["-L/opt/lib", "-lfoo"]])
|
|
l = d.items()
|
|
l.sort()
|
|
for k,v in l:
|
|
if v:
|
|
print k, v
|
|
env.MergeFlags(d)
|
|
env.Program('f1.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CPPPATH ['/opt/include']
|
|
LIBPATH ['/opt/lib']
|
|
LIBS ['foo']
|
|
cc -o f1.o -c -I/opt/include f1.c
|
|
cc -o f1 f1.o -L/opt/lib -lfoo
|
|
</PRE
|
|
><P
|
|
>
|
|
If a string begins with a "!" (an exclamation mark, often called a bang),
|
|
the string is passed to the shell for execution.
|
|
The output of the command is then parsed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
d = env.ParseFlags(["!echo -I/opt/include", "!echo -L/opt/lib", "-lfoo"])
|
|
l = d.items()
|
|
l.sort()
|
|
for k,v in l:
|
|
if v:
|
|
print k, v
|
|
env.MergeFlags(d)
|
|
env.Program('f1.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
CPPPATH ['/opt/include']
|
|
LIBPATH ['/opt/lib']
|
|
LIBS ['foo']
|
|
cc -o f1.o -c -I/opt/include f1.c
|
|
cc -o f1 f1.o -L/opt/lib -lfoo
|
|
</PRE
|
|
><P
|
|
>
|
|
<CODE
|
|
CLASS="function"
|
|
>ParseFlags</CODE
|
|
> is regularly updated for new options;
|
|
consult the man page for details about those currently recognized.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-parseconfig"
|
|
></A
|
|
>Chapter 10. Finding Installed Library Information: the <CODE
|
|
CLASS="function"
|
|
>ParseConfig</CODE
|
|
> Function</H1
|
|
><P
|
|
>
|
|
Configuring the right options to build programs to work with
|
|
libraries--especially shared libraries--that are available
|
|
on POSIX systems can be very complicated.
|
|
To help this situation,
|
|
various utilies with names that end in <TT
|
|
CLASS="filename"
|
|
>config</TT
|
|
>
|
|
return the command-line options for the GNU Compiler Collection (GCC)
|
|
that are needed to use these libraries;
|
|
for example, the command-line options
|
|
to use a library named <TT
|
|
CLASS="filename"
|
|
>lib</TT
|
|
>
|
|
would be found by calling a utility named <TT
|
|
CLASS="filename"
|
|
>lib-config</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
A more recent convention is that these options
|
|
are available from the generic <TT
|
|
CLASS="filename"
|
|
>pkg-config</TT
|
|
> program,
|
|
which has common framework, error handling, and the like,
|
|
so that all the package creator has to do is provide the set of strings
|
|
for his particular package.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> construction environments have a <CODE
|
|
CLASS="function"
|
|
>ParseConfig</CODE
|
|
> method
|
|
that executes a <TT
|
|
CLASS="filename"
|
|
>*config</TT
|
|
> utility
|
|
(either <TT
|
|
CLASS="filename"
|
|
>pkg-config</TT
|
|
> or a
|
|
more specific utility)
|
|
and configures the appropriate construction variables
|
|
in the environment
|
|
based on the command-line options
|
|
returned by the specified command.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env['CPPPATH'] = ['/lib/compat']
|
|
env.ParseConfig("pkg-config x11 --cflags --libs")
|
|
print env['CPPPATH']
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will execute the specified command string,
|
|
parse the resultant flags,
|
|
and add the flags to the appropriate environment variables.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
['/lib/compat', '/usr/X11/include']
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In the example above, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has added the include directory to
|
|
<CODE
|
|
CLASS="varname"
|
|
>CPPPATH</CODE
|
|
>.
|
|
(Depending upon what other flags are emitted by the
|
|
<TT
|
|
CLASS="filename"
|
|
>pkg-config</TT
|
|
> command,
|
|
other variables may have been extended as well.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that the options are merged with existing options using
|
|
the <CODE
|
|
CLASS="function"
|
|
>MergeFlags</CODE
|
|
> method,
|
|
so that each option only occurs once in the construction variable:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.ParseConfig("pkg-config x11 --cflags --libs")
|
|
env.ParseConfig("pkg-config x11 --cflags --libs")
|
|
print env['CPPPATH']
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
['/usr/X11/include']
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-output"
|
|
></A
|
|
>Chapter 11. Controlling Build Output</H1
|
|
><P
|
|
>
|
|
A key aspect of creating a usable build configuration
|
|
is providing good output from the build
|
|
so its users can readily understand
|
|
what the build is doing
|
|
and get information about how to control the build.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides several ways of
|
|
controlling output from the build configuration
|
|
to help make the build
|
|
more useful and understandable.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1846"
|
|
>11.1. Providing Build Help: the <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
It's often very useful to be able to give
|
|
users some help that describes the
|
|
specific targets, build options, etc.,
|
|
that can be used for your build.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides the <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> function
|
|
to allow you to specify this help text:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Help("""
|
|
Type: 'scons program' to build the production program,
|
|
'scons debug' to build the debug version.
|
|
""")
|
|
</PRE
|
|
><P
|
|
>
|
|
(Note the above use of the Python triple-quote syntax,
|
|
which comes in very handy for
|
|
specifying multi-line strings like help text.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
When the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> or <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
contain such a call to the <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> function,
|
|
the specified help text will be displayed in response to
|
|
the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> <TT
|
|
CLASS="literal"
|
|
>-h</TT
|
|
> option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -h</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
|
|
Type: 'scons program' to build the production program,
|
|
'scons debug' to build the debug version.
|
|
|
|
Use scons -H for help about command-line options.
|
|
</PRE
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files may contain
|
|
multiple calls to the <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> function,
|
|
in which case the specified text(s)
|
|
will be concatenated when displayed.
|
|
This allows you to split up the
|
|
help text across multiple <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
In this situation, the order in
|
|
which the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files are called
|
|
will determine the order in which the <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> functions are called,
|
|
which will determine the order in which
|
|
the various bits of text will get concatenated.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Another use would be to make the help text conditional
|
|
on some variable.
|
|
For example, suppose you only want to display
|
|
a line about building a Windows-only
|
|
version of a program when actually
|
|
run on Windows.
|
|
The following <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
|
|
Help("\nType: 'scons program' to build the production program.\n")
|
|
|
|
if env['PLATFORM'] == 'win32':
|
|
Help("\nType: 'scons windebug' to build the Windows debug version.\n")
|
|
</PRE
|
|
><P
|
|
>
|
|
Will display the complete help text on Windows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -h</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
|
|
Type: 'scons program' to build the production program.
|
|
|
|
Type: 'scons windebug' to build the Windows debug version.
|
|
|
|
Use scons -H for help about command-line options.
|
|
</PRE
|
|
><P
|
|
>
|
|
But only show the relevant option on a Linux or UNIX system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -h</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
|
|
Type: 'scons program' to build the production program.
|
|
|
|
Use scons -H for help about command-line options.
|
|
</PRE
|
|
><P
|
|
>
|
|
If there is no <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> text in the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> or
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will revert to displaying its
|
|
standard list that describes the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> command-line
|
|
options.
|
|
This list is also always displayed whenever
|
|
the <TT
|
|
CLASS="literal"
|
|
>-H</TT
|
|
> option is used.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1884"
|
|
>11.2. Controlling How <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Prints Build Commands: the <CODE
|
|
CLASS="envar"
|
|
>$*COMSTR</CODE
|
|
> Variables</A
|
|
></H2
|
|
><P
|
|
>
|
|
Sometimes the commands executed
|
|
to compile object files or link programs
|
|
(or build other targets)
|
|
can get very long,
|
|
long enough to make it difficult for users
|
|
to distinguish error messages or
|
|
other important build output
|
|
from the commands themselves.
|
|
All of the default <CODE
|
|
CLASS="envar"
|
|
>$*COM</CODE
|
|
> variables
|
|
that specify the command lines
|
|
used to build various types of target files
|
|
have a corresponding <CODE
|
|
CLASS="envar"
|
|
>$*COMSTR</CODE
|
|
> variable
|
|
that can be set to an alternative
|
|
string that will be displayed
|
|
when the target is built.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose you want to
|
|
have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> display a
|
|
<TT
|
|
CLASS="literal"
|
|
>"Compiling"</TT
|
|
>
|
|
message whenever it's compiling an object file,
|
|
and a
|
|
<TT
|
|
CLASS="literal"
|
|
>"Linking"</TT
|
|
>
|
|
when it's linking an executable.
|
|
You could write a <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
that looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCCOMSTR = "Compiling $TARGET",
|
|
LINKCOMSTR = "Linking $TARGET")
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Which would then yield the output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Compiling foo.o
|
|
Linking foo
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> performs complete variable substitution
|
|
on <CODE
|
|
CLASS="envar"
|
|
>$*COMSTR</CODE
|
|
> variables,
|
|
so they have access to all of the
|
|
standard variables like <CODE
|
|
CLASS="envar"
|
|
>$TARGET</CODE
|
|
> <CODE
|
|
CLASS="envar"
|
|
>$SOURCES</CODE
|
|
>, etc.,
|
|
as well as any construction variables
|
|
that happen to be configured in
|
|
the construction environment
|
|
used to build a specific target.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Of course, sometimes it's still important to
|
|
be able to see the exact command
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will execute to build a target.
|
|
For example, you may simply need to verify
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is configured to supply
|
|
the right options to the compiler,
|
|
or a developer may want to
|
|
cut-and-paste a comiloe command
|
|
to add a few options
|
|
for a custom test.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One common way to give users
|
|
control over whether or not
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> should print the actual command line
|
|
or a short, configured summary
|
|
is to add support for a
|
|
<CODE
|
|
CLASS="varname"
|
|
>VERBOSE</CODE
|
|
>
|
|
command-line variable to your <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file.
|
|
A simple configuration for this might look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
if ARGUMENTS.get('VERBOSE') != "1':
|
|
env['CCCOMSTR'] = "Compiling $TARGET"
|
|
env['LINKCOMSTR'] = "Linking $TARGET"
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
|
|
By only setting the appropriate
|
|
<CODE
|
|
CLASS="envar"
|
|
>$*COMSTR</CODE
|
|
> variables
|
|
if the user specifies
|
|
<TT
|
|
CLASS="literal"
|
|
>VERBOSE=1</TT
|
|
>
|
|
on the command line,
|
|
the user has control
|
|
over how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
displays these particular command lines:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Compiling foo.o
|
|
Linking foo
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed foo.o
|
|
Removed foo
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q VERBOSE=1</KBD
|
|
>
|
|
cc -o foo.o -c foo.c
|
|
cc -o foo foo.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1921"
|
|
>11.3. Providing Build Progress Output: the <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Another aspect of providing good build output
|
|
is to give the user feedback
|
|
about what <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is doing
|
|
even when nothing is being built at the moment.
|
|
This can be especially true for large builds
|
|
when most of the targets are already up-to-date.
|
|
Because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> can take a long time
|
|
making absolutely sure that every
|
|
target is, in fact, up-to-date
|
|
with respect to a lot of dependency files,
|
|
it can be easy for users to mistakenly
|
|
conclude that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is hung
|
|
or that there is some other problem with the build.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One way to deal with this perception
|
|
is to configure <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to print something to
|
|
let the user know what it's "thinking about."
|
|
The <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> function
|
|
allows you to specify a string
|
|
that will be printed for every file
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is "considering"
|
|
while it is traversing the dependency graph
|
|
to decide what targets are or are not up-to-date.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Progress('Evaluating $TARGET\n')
|
|
Program('f1.c')
|
|
Program('f2.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> function does not
|
|
arrange for a newline to be printed automatically
|
|
at the end of the string (as does the Python
|
|
<TT
|
|
CLASS="literal"
|
|
>print</TT
|
|
> statement),
|
|
and we must specify the
|
|
<TT
|
|
CLASS="literal"
|
|
>\n</TT
|
|
>
|
|
that we want printed at the end of the configured string.
|
|
This configuration, then,
|
|
will have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
print that it is <TT
|
|
CLASS="literal"
|
|
>Evaluating</TT
|
|
>
|
|
each file that it encounters
|
|
in turn as it traverses the dependency graph:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Evaluating SConstruct
|
|
Evaluating f1.c
|
|
Evaluating f1.o
|
|
cc -o f1.o -c f1.c
|
|
Evaluating f1
|
|
cc -o f1 f1.o
|
|
Evaluating f2.c
|
|
Evaluating f2.o
|
|
cc -o f2.o -c f2.c
|
|
Evaluating f2
|
|
cc -o f2 f2.o
|
|
Evaluating .
|
|
</PRE
|
|
><P
|
|
>
|
|
Of course, normally you don't want to add
|
|
all of these additional lines to your build output,
|
|
as that can make it difficult for the user
|
|
to find errors or other important messages.
|
|
A more useful way to display
|
|
this progress might be
|
|
to have the file names printed
|
|
directly to the user's screen,
|
|
not to the same standard output
|
|
stream where build output is printed,
|
|
and to use a carriage return character
|
|
(<TT
|
|
CLASS="literal"
|
|
>\r</TT
|
|
>)
|
|
so that each file name gets re-printed on the same line.
|
|
Such a configuration would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Progress('$TARGET\r',
|
|
file=open('/dev/tty', 'w'),
|
|
overwrite=True)
|
|
Program('f1.c')
|
|
Program('f2.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that we also specified the
|
|
<TT
|
|
CLASS="literal"
|
|
>overwrite=True</TT
|
|
> argument
|
|
to the <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> function,
|
|
which causes <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to
|
|
"wipe out" the previous string with space characters
|
|
before printing the next <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> string.
|
|
Without the
|
|
<TT
|
|
CLASS="literal"
|
|
>overwrite=True</TT
|
|
> argument,
|
|
a shorter file name would not overwrite
|
|
all of the charactes in a longer file name that
|
|
precedes it,
|
|
making it difficult to tell what the
|
|
actual file name is on the output.
|
|
Also note that we opened up the
|
|
<TT
|
|
CLASS="filename"
|
|
>/dev/tty</TT
|
|
> file
|
|
for direct access (on POSIX) to
|
|
the user's screen.
|
|
On Windows, the equivalent would be to open
|
|
the <TT
|
|
CLASS="filename"
|
|
>con:</TT
|
|
> file name.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Also, it's important to know that although you can use
|
|
<TT
|
|
CLASS="literal"
|
|
>$TARGET</TT
|
|
> to substitute the name of
|
|
the node in the string,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> function does <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
perform general variable substitution
|
|
(because there's not necessarily a construction
|
|
environment involved in evaluating a node
|
|
like a source file, for example).
|
|
|
|
</P
|
|
><P
|
|
>
|
|
You can also specify a list of strings
|
|
to the <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> function,
|
|
in which case <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will
|
|
display each string in turn.
|
|
This can be used to implement a "spinner"
|
|
by having <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> cycle through a
|
|
sequence of strings:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Progress(['-\r', '\\\r', '|\r', '/\r'], interval=5)
|
|
Program('f1.c')
|
|
Program('f2.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that here we have also used the
|
|
<TT
|
|
CLASS="literal"
|
|
>interval=</TT
|
|
>
|
|
keyword argument to have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
only print a new "spinner" string
|
|
once every five evaluated nodes.
|
|
Using an <TT
|
|
CLASS="literal"
|
|
>interval=</TT
|
|
> count,
|
|
even with strings that use <TT
|
|
CLASS="literal"
|
|
>$TARGET</TT
|
|
> like
|
|
our examples above,
|
|
can be a good way to lessen the
|
|
work that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> expends printing <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> strings,
|
|
while still giving the user feedback
|
|
that indicates <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is still
|
|
working on evaluating the build.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Lastly, you can have direct control
|
|
over how to print each evaluated node
|
|
by passing a Python function
|
|
(or other Python callable)
|
|
to the <CODE
|
|
CLASS="function"
|
|
>Progress</CODE
|
|
> function.
|
|
Your function will be called
|
|
for each evaluated node,
|
|
allowing you to
|
|
implement more sophisticated logic
|
|
like adding a counter:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> screen = open('/dev/tty', 'w')
|
|
count = 0
|
|
def progress_function(node)
|
|
count += 1
|
|
screen.write('Node %4d: %s\r' % (count, node))
|
|
|
|
Progress(progress_function)
|
|
</PRE
|
|
><P
|
|
>
|
|
Of course, if you choose,
|
|
you could completely ignore the
|
|
<CODE
|
|
CLASS="varname"
|
|
>node</CODE
|
|
> argument to the function,
|
|
and just print a count,
|
|
or anything else you wish.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
(Note that there's an obvious follow-on question here:
|
|
how would you find the total number of nodes
|
|
that <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>will be</I
|
|
></SPAN
|
|
>
|
|
evaluated so you can tell the user how
|
|
close the build is to finishing?
|
|
Unfortunately, in the general case,
|
|
there isn't a good way to do that,
|
|
short of having <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> evaluate its
|
|
dependency graph twice,
|
|
first to count the total and
|
|
the second time to actually build the targets.
|
|
This would be necessary because
|
|
you can't know in advance which
|
|
target(s) the user actually requested
|
|
to be built.
|
|
The entire build may consist of thousands of Nodes,
|
|
for example,
|
|
but maybe the user specifically requested
|
|
that only a single object file be built.)
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN1977"
|
|
>11.4. Printing Detailed Build Status: the <CODE
|
|
CLASS="function"
|
|
>GetBuildFailures</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
SCons, like most build tools, returns zero status to
|
|
the shell on success and nonzero status on failure.
|
|
Sometimes it's useful to give more information about
|
|
the build status at the end of the run, for instance
|
|
to print an informative message, send an email, or
|
|
page the poor slob who broke the build.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
SCons provides a <CODE
|
|
CLASS="function"
|
|
>GetBuildFailures</CODE
|
|
> method that
|
|
you can use in a python <CODE
|
|
CLASS="function"
|
|
>atexit</CODE
|
|
> function
|
|
to get a list of objects describing the actions that failed
|
|
while attempting to build targets. There can be more
|
|
than one if you're using <TT
|
|
CLASS="literal"
|
|
>-j</TT
|
|
>. Here's a
|
|
simple example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import atexit
|
|
|
|
def print_build_failures():
|
|
from SCons.Script import GetBuildFailures
|
|
for bf in GetBuildFailures():
|
|
print "%s failed: %s" % (bf.node, bf.errstr)
|
|
atexit.register(print_build_failures)
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>atexit.register</CODE
|
|
> call
|
|
registers <CODE
|
|
CLASS="function"
|
|
>print_build_failures</CODE
|
|
>
|
|
as an <CODE
|
|
CLASS="function"
|
|
>atexit</CODE
|
|
> callback, to be called
|
|
before <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> exits. When that function is called,
|
|
it calls <CODE
|
|
CLASS="function"
|
|
>GetBuildFailures</CODE
|
|
> to fetch the list of failed objects.
|
|
See the man page
|
|
for the detailed contents of the returned objects;
|
|
some of the more useful attributes are
|
|
<TT
|
|
CLASS="literal"
|
|
>.node</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>.errstr</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>.filename</TT
|
|
>, and
|
|
<TT
|
|
CLASS="literal"
|
|
>.command</TT
|
|
>.
|
|
The <TT
|
|
CLASS="literal"
|
|
>filename</TT
|
|
> is not necessarily
|
|
the same file as the <TT
|
|
CLASS="literal"
|
|
>node</TT
|
|
>; the
|
|
<TT
|
|
CLASS="literal"
|
|
>node</TT
|
|
> is the target that was
|
|
being built when the error occurred, while the
|
|
<TT
|
|
CLASS="literal"
|
|
>filename</TT
|
|
>is the file or dir that
|
|
actually caused the error.
|
|
Note: only call <CODE
|
|
CLASS="function"
|
|
>GetBuildFailures</CODE
|
|
> at the end of the
|
|
build; calling it at any other time is undefined.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
|
|
Here is a more complete example showing how to
|
|
turn each element of <CODE
|
|
CLASS="function"
|
|
>GetBuildFailures</CODE
|
|
> into a string:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Make the build fail if we pass fail=1 on the command line
|
|
if ARGUMENTS.get('fail', 0):
|
|
Command('target', 'source', ['/bin/false'])
|
|
|
|
def bf_to_str(bf):
|
|
"""Convert an element of GetBuildFailures() to a string
|
|
in a useful way."""
|
|
import SCons.Errors
|
|
if bf is None: # unknown targets product None in list
|
|
return '(unknown tgt)'
|
|
elif isinstance(bf, SCons.Errors.StopError):
|
|
return str(bf)
|
|
elif bf.node:
|
|
return str(bf.node) + ': ' + bf.errstr
|
|
elif bf.filename:
|
|
return bf.filename + ': ' + bf.errstr
|
|
return 'unknown failure: ' + bf.errstr
|
|
import atexit
|
|
|
|
def build_status():
|
|
"""Convert the build status to a 2-tuple, (status, msg)."""
|
|
from SCons.Script import GetBuildFailures
|
|
bf = GetBuildFailures()
|
|
if bf:
|
|
# bf is normally a list of build failures; if an element is None,
|
|
# it's because of a target that scons doesn't know anything about.
|
|
status = 'failed'
|
|
failures_message = "\n".join(["Failed building %s" % bf_to_str(x)
|
|
for x in bf if x is not None])
|
|
else:
|
|
# if bf is None, the build completed successfully.
|
|
status = 'ok'
|
|
failures_message = ''
|
|
return (status, failures_message)
|
|
|
|
def display_build_status():
|
|
"""Display the build status. Called by atexit.
|
|
Here you could do all kinds of complicated things."""
|
|
status, failures_message = build_status()
|
|
if status == 'failed':
|
|
print "FAILED!!!!" # could display alert, ring bell, etc.
|
|
elif status == 'ok':
|
|
print "Build succeeded."
|
|
print failures_message
|
|
|
|
atexit.register(display_build_status)
|
|
</PRE
|
|
><P
|
|
>
|
|
When this runs, you'll see the appropriate output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
Build succeeded.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q fail=1</KBD
|
|
>
|
|
scons: *** Source `source' not found, needed by target `target'. Stop.
|
|
FAILED!!!!
|
|
Failed building Source `source' not found, needed by target `target'.
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-command-line"
|
|
></A
|
|
>Chapter 12. Controlling a Build From the Command Line</H1
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a number of ways
|
|
for the writer of the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
to give the users who will run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
a great deal of control over the build execution.
|
|
The arguments that the user can specify on
|
|
the command line are broken down into three types:
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
>Options</DT
|
|
><DD
|
|
><P
|
|
>
|
|
Command-line options always begin with
|
|
one or two <TT
|
|
CLASS="literal"
|
|
>-</TT
|
|
> (hyphen) characters.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides ways for you to examind
|
|
and set options values from within your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
as well as the ability to define your own
|
|
custom options.
|
|
See <A
|
|
HREF="#sect-command-line-options"
|
|
>Section 12.1</A
|
|
>, below.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>Variables</DT
|
|
><DD
|
|
><P
|
|
>
|
|
Any command-line argument containing an <TT
|
|
CLASS="literal"
|
|
>=</TT
|
|
>
|
|
(equal sign) is considered a variable setting with the form
|
|
<CODE
|
|
CLASS="varname"
|
|
>variable</CODE
|
|
>=<CODE
|
|
CLASS="varname"
|
|
>value</CODE
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides direct access to
|
|
all of the command-line variable settings,
|
|
the ability to apply command-line variable settings
|
|
to construction environments,
|
|
and functions for configuring
|
|
specific types of variables
|
|
(Boolean values, path names, etc.)
|
|
with automatic validation of the user's specified values.
|
|
See <A
|
|
HREF="#sect-command-line-variables"
|
|
>Section 12.2</A
|
|
>, below.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>Targets</DT
|
|
><DD
|
|
><P
|
|
>
|
|
Any command-line argument that is not an option
|
|
or a variable setting
|
|
(does not begin with a hyphen
|
|
and does not contain an equal sign)
|
|
is considered a target that the user
|
|
(presumably) wants <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to build.
|
|
A list of Node objects representing
|
|
the target or targets to build.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides access to the list of specified targets,
|
|
as well as ways to set the default list of targets
|
|
from within the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
See <A
|
|
HREF="#sect-command-line-targets"
|
|
>Section 12.3</A
|
|
>, below.
|
|
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="sect-command-line-options"
|
|
>12.1. Command-Line Options</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has many <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>command-line options</I
|
|
></SPAN
|
|
>
|
|
that control its behavior.
|
|
A <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>command-line option</I
|
|
></SPAN
|
|
>
|
|
always begins with one or two <TT
|
|
CLASS="literal"
|
|
>-</TT
|
|
> (hyphen)
|
|
characters.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2048"
|
|
>12.1.1. Not Having to Specify Command-Line Options Each Time: the <CODE
|
|
CLASS="varname"
|
|
>SCONSFLAGS</CODE
|
|
> Environment Variable</A
|
|
></H3
|
|
><P
|
|
>
|
|
Users may find themselves supplying
|
|
the same command-line options every time
|
|
they run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
For example, you might find it saves time
|
|
to specify a value of <TT
|
|
CLASS="literal"
|
|
>-j 2</TT
|
|
>
|
|
to have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> run up to two build commands in parallel.
|
|
To avoid having to type <TT
|
|
CLASS="literal"
|
|
>-j 2</TT
|
|
> by hand
|
|
every time,
|
|
you can set the external environment variable
|
|
<CODE
|
|
CLASS="varname"
|
|
>SCONSFLAGS</CODE
|
|
> to a string containing
|
|
command-line options that you want <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to use.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If, for example,
|
|
you're using a POSIX shell that's
|
|
compatible with the Bourne shell,
|
|
and you always want <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to use the
|
|
<TT
|
|
CLASS="literal"
|
|
>-Q</TT
|
|
> option,
|
|
you can set the <CODE
|
|
CLASS="varname"
|
|
>SCONSFLAGS</CODE
|
|
>
|
|
environment as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
... [build output] ...
|
|
scons: done building targets.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>export SCONSFLAGS="-Q"</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
... [build output] ...
|
|
</PRE
|
|
><P
|
|
>
|
|
Users of <SPAN
|
|
CLASS="application"
|
|
>csh</SPAN
|
|
>-style shells on POSIX systems
|
|
can set the <CODE
|
|
CLASS="varname"
|
|
>SCONSFLAGS</CODE
|
|
> environment as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> $ <KBD
|
|
CLASS="userinput"
|
|
>setenv SCONSFLAGS "-Q"</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
Windows users may typically want to set the
|
|
<CODE
|
|
CLASS="varname"
|
|
>SCONSFLAGS</CODE
|
|
> in the appropriate tab of the
|
|
<TT
|
|
CLASS="literal"
|
|
>System Properties</TT
|
|
> window.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2074"
|
|
>12.1.2. Getting Values Set by Command-Line Options: the <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides the <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> function
|
|
to get the values set by the various command-line options.
|
|
One common use of this is to check whether or not
|
|
the <TT
|
|
CLASS="literal"
|
|
>-h</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>--help</TT
|
|
> option
|
|
has been specified.
|
|
Normally, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not print its help text
|
|
until after it has read all of the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
because it's possible that help text has been added
|
|
by some subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file deep in the
|
|
source tree hierarchy.
|
|
Of course, reading all of the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
takes extra time.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you know that your configuration does not define
|
|
any additional help text in subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
you can speed up the command-line help available to users
|
|
by using the <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> function to load the
|
|
subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files only if the
|
|
the user has <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
> specified
|
|
the <TT
|
|
CLASS="literal"
|
|
>-h</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>--help</TT
|
|
> option,
|
|
like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
></PRE
|
|
><P
|
|
>
|
|
In general, the string that you pass to the
|
|
<CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> function to fetch the value of a command-line
|
|
option setting is the same as the "most common" long option name
|
|
(beginning with two hyphen characters),
|
|
although there are some exceptions.
|
|
The list of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> command-line options
|
|
and the <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> strings for fetching them,
|
|
are available in the
|
|
<A
|
|
HREF="#sect-command-line-option-strings"
|
|
>Section 12.1.4</A
|
|
> section,
|
|
below.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2099"
|
|
>12.1.3. Setting Values of Command-Line Options: the <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
You can also set the values of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
command-line options from within the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
by using the <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
> function.
|
|
The strings that you use to set the values of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
command-line options are available in the
|
|
<A
|
|
HREF="#sect-command-line-option-strings"
|
|
>Section 12.1.4</A
|
|
> section,
|
|
below.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One use of the <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
> function is to
|
|
specify a value for the <TT
|
|
CLASS="literal"
|
|
>-j</TT
|
|
>
|
|
or <TT
|
|
CLASS="literal"
|
|
>--jobs</TT
|
|
> option,
|
|
so that users get the improved performance
|
|
of a parallel build without having to specify the option by hand.
|
|
A complicating factor is that a good value
|
|
for the <TT
|
|
CLASS="literal"
|
|
>-j</TT
|
|
> option is
|
|
somewhat system-dependent.
|
|
One rough guideline is that the more processors
|
|
your system has,
|
|
the higher you want to set the
|
|
<TT
|
|
CLASS="literal"
|
|
>-j</TT
|
|
> value,
|
|
in order to take advantage of the number of CPUs.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose the administrators
|
|
of your development systems
|
|
have standardized on setting a
|
|
<CODE
|
|
CLASS="varname"
|
|
>NUM_CPU</CODE
|
|
> environment variable
|
|
to the number of processors on each system.
|
|
A little bit of Python code
|
|
to access the environment variable
|
|
and the <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
> function
|
|
provide the right level of flexibility:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os
|
|
num_cpu = int(os.environ.get('NUM_CPU', 2))
|
|
SetOption('num_jobs', num_cpu)
|
|
print "running with -j", GetOption('num_jobs')
|
|
</PRE
|
|
><P
|
|
>
|
|
The above snippet of code
|
|
sets the value of the <TT
|
|
CLASS="literal"
|
|
>--jobs</TT
|
|
> option
|
|
to the value specified in the
|
|
<CODE
|
|
CLASS="varname"
|
|
>$NUM_CPU</CODE
|
|
> environment variable.
|
|
(This is one of the exception cases
|
|
where the string is spelled differently from
|
|
the from command-line option.
|
|
The string for fetching or setting the <TT
|
|
CLASS="literal"
|
|
>--jobs</TT
|
|
>
|
|
value is <TT
|
|
CLASS="literal"
|
|
>num_jobs</TT
|
|
>
|
|
for historical reasons.)
|
|
The code in this example prints the <TT
|
|
CLASS="literal"
|
|
>num_jobs</TT
|
|
>
|
|
value for illustrative purposes.
|
|
It uses a default value of <TT
|
|
CLASS="literal"
|
|
>2</TT
|
|
>
|
|
to provide some minimal parallelism even on
|
|
single-processor systems:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
running with -j 2
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
But if the <CODE
|
|
CLASS="varname"
|
|
>$NUM_CPU</CODE
|
|
>
|
|
environment variable is set,
|
|
then we use that for the default number of jobs:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>export NUM_CPU="4"</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
running with -j 4
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
But any explicit
|
|
<TT
|
|
CLASS="literal"
|
|
>-j</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>--jobs</TT
|
|
>
|
|
value the user specifies an the command line is used first,
|
|
regardless of whether or not
|
|
the <CODE
|
|
CLASS="varname"
|
|
>$NUM_CPU</CODE
|
|
> environment
|
|
variable is set:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -j 7</KBD
|
|
>
|
|
running with -j 7
|
|
scons: `.' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>export NUM_CPU="4"</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -j 3</KBD
|
|
>
|
|
running with -j 3
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="sect-command-line-option-strings"
|
|
>12.1.4. Strings for Getting or Setting Values of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Command-Line Options</A
|
|
></H3
|
|
><P
|
|
>
|
|
The strings that you can pass to the <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
>
|
|
and <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
> functions usually correspond to the
|
|
first long-form option name
|
|
(beginning with two hyphen characters: <TT
|
|
CLASS="literal"
|
|
>--</TT
|
|
>),
|
|
after replacing any remaining hyphen characters
|
|
with underscores.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The full list of strings and the variables they
|
|
correspond to is as follows:
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="informaltable"
|
|
><P
|
|
></P
|
|
><A
|
|
NAME="AEN2148"
|
|
></A
|
|
><TABLE
|
|
BORDER="1"
|
|
CLASS="CALSTABLE"
|
|
><COL><COL><THEAD
|
|
><TR
|
|
><TH
|
|
>String for <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
></TH
|
|
><TH
|
|
>Command-Line Option(s)</TH
|
|
></TR
|
|
></THEAD
|
|
><TBODY
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>cache_debug</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--cache-debug</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>cache_disable</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--cache-disable</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>cache_force</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--cache-force</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>cache_show</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--cache-show</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>clean</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-c</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--clean</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--remove</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>config</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--config</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>directory</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-C</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--directory</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>diskcheck</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--diskcheck</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>duplicate</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--duplicate</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>file</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-f</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--file</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--makefile </CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--sconstruct</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>help</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-h</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--help</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>ignore_errors</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--ignore-errors</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>implicit_cache</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--implicit-cache</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>implicit_deps_changed</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--implicit-deps-changed</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>implicit_deps_unchanged</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--implicit-deps-unchanged</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>interactive</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--interact</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--interactive</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>keep_going</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-k</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--keep-going</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>max_drift</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--max-drift</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>no_exec</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-n</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--no-exec</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--just-print</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--dry-run</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--recon</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>no_site_dir</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--no-site-dir</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>num_jobs</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-j</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--jobs</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>profile_file</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--profile</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>question</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-q</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--question</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>random</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--random</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>repository</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-Y</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--repository</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--srcdir</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>silent</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>-s</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--silent</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>--quiet</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>site_dir</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--site-dir</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>stack_size</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--stack-size</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>taskmastertrace_file</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--taskmastertrace</CODE
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
><TT
|
|
CLASS="literal"
|
|
>warn</TT
|
|
></TD
|
|
><TD
|
|
><CODE
|
|
CLASS="option"
|
|
>--warn</CODE
|
|
> <CODE
|
|
CLASS="option"
|
|
>--warning</CODE
|
|
></TD
|
|
></TR
|
|
></TBODY
|
|
></TABLE
|
|
><P
|
|
></P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2327"
|
|
>12.1.5. Adding Custom Command-Line Options: the <CODE
|
|
CLASS="function"
|
|
>AddOption</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> also allows you to define your own
|
|
command-line options with the <CODE
|
|
CLASS="function"
|
|
>AddOption</CODE
|
|
> function.
|
|
The <CODE
|
|
CLASS="function"
|
|
>AddOption</CODE
|
|
> function takes the same arguments
|
|
as the <CODE
|
|
CLASS="function"
|
|
>optparse.add_option</CODE
|
|
> function
|
|
from the standard Python library.
|
|
<A
|
|
NAME="AEN2335"
|
|
HREF="#FTN.AEN2335"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[3]</SPAN
|
|
></A
|
|
>
|
|
Once you have added a custom command-line option
|
|
with the <CODE
|
|
CLASS="function"
|
|
>AddOption</CODE
|
|
> function,
|
|
the value of the option (if any) is immediately available
|
|
using the standard <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> function.
|
|
(The value can also be set using <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
>,
|
|
although that's not very useful in practice
|
|
because a default value can be specified in
|
|
directly in the <CODE
|
|
CLASS="function"
|
|
>AddOption</CODE
|
|
> call.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One useful example of using this functionality
|
|
is to provide a <CODE
|
|
CLASS="option"
|
|
>--prefix</CODE
|
|
> for users:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> AddOption('--prefix',
|
|
dest='prefix',
|
|
type='string',
|
|
nargs=1,
|
|
action='store',
|
|
metavar='DIR',
|
|
help='installation prefix')
|
|
|
|
env = Environment(PREFIX = GetOption('prefix'))
|
|
|
|
installed_foo = env.Install('$PREFIX/usr/bin', 'foo.in')
|
|
Default(installed_foo)
|
|
</PRE
|
|
><P
|
|
>
|
|
The above code uses the <CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
> function
|
|
to set the <CODE
|
|
CLASS="varname"
|
|
>$PREFIX</CODE
|
|
>
|
|
construction variable to any
|
|
value that the user specifies with a command-line
|
|
option of <TT
|
|
CLASS="literal"
|
|
>--prefix</TT
|
|
>.
|
|
Because <CODE
|
|
CLASS="varname"
|
|
>$PREFIX</CODE
|
|
>
|
|
will expand to a null string if it's not initialized,
|
|
running <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> without the
|
|
option of <TT
|
|
CLASS="literal"
|
|
>--prefix</TT
|
|
>
|
|
will install the file in the
|
|
<TT
|
|
CLASS="filename"
|
|
>/usr/bin/</TT
|
|
> directory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -n</KBD
|
|
>
|
|
Install file: "foo.in" as "/usr/bin/foo.in"
|
|
</PRE
|
|
><P
|
|
>
|
|
But specifying <TT
|
|
CLASS="literal"
|
|
>--prefix=/tmp/install</TT
|
|
>
|
|
on the command line causes the file to be installed in the
|
|
<TT
|
|
CLASS="filename"
|
|
>/tmp/install/usr/bin/</TT
|
|
> directory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -n --prefix=/tmp/install</KBD
|
|
>
|
|
Install file: "foo.in" as "/tmp/install/usr/bin/foo.in"
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="sect-command-line-variables"
|
|
>12.2. Command-Line <CODE
|
|
CLASS="varname"
|
|
>variable</CODE
|
|
>=<CODE
|
|
CLASS="varname"
|
|
>value</CODE
|
|
> Build Variables</A
|
|
></H2
|
|
><P
|
|
>
|
|
You may want to control various aspects
|
|
of your build by allowing the user
|
|
to specify <CODE
|
|
CLASS="varname"
|
|
>variable</CODE
|
|
>=<CODE
|
|
CLASS="varname"
|
|
>value</CODE
|
|
>
|
|
values on the command line.
|
|
For example, suppose you
|
|
want users to be able to
|
|
build a debug version of a program
|
|
by running <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q debug=1</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides an <CODE
|
|
CLASS="varname"
|
|
>ARGUMENTS</CODE
|
|
> dictionary
|
|
that stores all of the
|
|
<CODE
|
|
CLASS="varname"
|
|
>variable</CODE
|
|
>=<CODE
|
|
CLASS="varname"
|
|
>value</CODE
|
|
>
|
|
assignments from the command line.
|
|
This allows you to modify
|
|
aspects of your build in response
|
|
to specifications on the command line.
|
|
(Note that unless you want to require
|
|
that users <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>always</I
|
|
></SPAN
|
|
>
|
|
specify a variable,
|
|
you probably want to use
|
|
the Python
|
|
<TT
|
|
CLASS="literal"
|
|
>ARGUMENTS.get()</TT
|
|
> function,
|
|
which allows you to specify a default value
|
|
to be used if there is no specification
|
|
on the command line.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The following code sets the <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
> construction
|
|
variable in response to the <CODE
|
|
CLASS="varname"
|
|
>debug</CODE
|
|
>
|
|
flag being set in the <CODE
|
|
CLASS="varname"
|
|
>ARGUMENTS</CODE
|
|
> dictionary:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
debug = ARGUMENTS.get('debug', 0)
|
|
if int(debug):
|
|
env.Append(CCFLAGS = '-g')
|
|
env.Program('prog.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
This results in the <CODE
|
|
CLASS="varname"
|
|
>-g</CODE
|
|
>
|
|
compiler option being used when
|
|
<TT
|
|
CLASS="literal"
|
|
>debug=1</TT
|
|
>
|
|
is used on the command line:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q debug=0</KBD
|
|
>
|
|
cc -o prog.o -c prog.c
|
|
cc -o prog prog.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q debug=0</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q debug=1</KBD
|
|
>
|
|
cc -o prog.o -c -g prog.c
|
|
cc -o prog prog.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q debug=1</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> keeps track of
|
|
the last values used to build the object files,
|
|
and as a result correctly rebuilds
|
|
the object and executable files
|
|
only when the value of the <TT
|
|
CLASS="literal"
|
|
>debug</TT
|
|
>
|
|
argument has changed.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="varname"
|
|
>ARGUMENTS</CODE
|
|
> dictionary has two minor drawbacks.
|
|
First, because it is a dictionary,
|
|
it can only store one value for each specified keyword,
|
|
and thus only "remembers" the last setting
|
|
for each keyword on the command line.
|
|
This makes the <CODE
|
|
CLASS="varname"
|
|
>ARGUMENTS</CODE
|
|
> dictionary
|
|
inappropriate if users should be able to
|
|
specify multiple values
|
|
on the command line for a given keyword.
|
|
Second, it does not preserve
|
|
the order in which the variable settings
|
|
were specified,
|
|
which is a problem if
|
|
you want the configuration to
|
|
behave differently in response
|
|
to the order in which the build
|
|
variable settings were specified on the command line.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
To accomodate these requirements,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides an <CODE
|
|
CLASS="varname"
|
|
>ARGLIST</CODE
|
|
> variable
|
|
that gives you direct access to
|
|
<CODE
|
|
CLASS="varname"
|
|
>variable</CODE
|
|
>=<CODE
|
|
CLASS="varname"
|
|
>value</CODE
|
|
>
|
|
settings on the command line,
|
|
in the exact order they were specified,
|
|
and without removing any duplicate settings.
|
|
Each element in the <CODE
|
|
CLASS="varname"
|
|
>ARGLIST</CODE
|
|
> variable
|
|
is itself a two-element list
|
|
containing the keyword and the value
|
|
of the setting,
|
|
and you must loop through,
|
|
or otherwise select from,
|
|
the elements of <CODE
|
|
CLASS="varname"
|
|
>ARGLIST</CODE
|
|
> to
|
|
process the specific settings you want
|
|
in whatever way is appropriate for your configuration.
|
|
For example,
|
|
the following code to let the user
|
|
add to the <CODE
|
|
CLASS="varname"
|
|
>CPPDEFINES</CODE
|
|
> construction variable
|
|
by specifying multiple
|
|
<CODE
|
|
CLASS="varname"
|
|
>define=</CODE
|
|
>
|
|
settings on the command line:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> cppdefines = []
|
|
for key, value in ARGLIST:
|
|
if key == 'define':
|
|
cppdefines.append(value)
|
|
env = Environment(CPPDEFINES = cppdefines)
|
|
env.Object('prog.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Yields the followig output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q define=FOO</KBD
|
|
>
|
|
cc -o prog.o -c -DFOO prog.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q define=FOO define=BAR</KBD
|
|
>
|
|
cc -o prog.o -c -DFOO -DBAR prog.c
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the <CODE
|
|
CLASS="varname"
|
|
>ARGLIST</CODE
|
|
> and <CODE
|
|
CLASS="varname"
|
|
>ARGUMENTS</CODE
|
|
>
|
|
variables do not interfere with each other,
|
|
but merely provide slightly different views
|
|
into how the user specified
|
|
<CODE
|
|
CLASS="varname"
|
|
>variable</CODE
|
|
>=<CODE
|
|
CLASS="varname"
|
|
>value</CODE
|
|
>
|
|
settings on the command line.
|
|
You can use both variables in the same
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> configuration.
|
|
In general, the <CODE
|
|
CLASS="varname"
|
|
>ARGUMENTS</CODE
|
|
> dictionary
|
|
is more convenient to use,
|
|
(since you can just fetch variable
|
|
settings through a dictionary access),
|
|
and the <CODE
|
|
CLASS="varname"
|
|
>ARGLIST</CODE
|
|
> list
|
|
is more flexible
|
|
(since you can examine the
|
|
specific order in which
|
|
the user's command-line variabe settings).
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2420"
|
|
>12.2.1. Controlling Command-Line Build Variables</A
|
|
></H3
|
|
><P
|
|
>
|
|
Being able to use a command-line build variable like
|
|
<TT
|
|
CLASS="literal"
|
|
>debug=1</TT
|
|
> is handy,
|
|
but it can be a chore to write specific Python code
|
|
to recognize each such variable,
|
|
check for errors and provide appropriate messages,
|
|
and apply the values to a construction variable.
|
|
To help with this,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a class to
|
|
define such build variables easily,
|
|
and a mechanism to apply the
|
|
build variables to a construction environment.
|
|
This allows you to control how the build variables affect
|
|
construction environments.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose that you want users to set
|
|
a <CODE
|
|
CLASS="varname"
|
|
>RELEASE</CODE
|
|
> construction variable on the
|
|
command line whenever the time comes to build
|
|
a program for release,
|
|
and that the value of this variable
|
|
should be added to the command line
|
|
with the appropriate <TT
|
|
CLASS="literal"
|
|
>-D</TT
|
|
> option
|
|
(or other command line option)
|
|
to pass the value to the C compiler.
|
|
Here's how you might do that by setting
|
|
the appropriate value in a dictionary for the
|
|
<A
|
|
HREF="#cv-CPPDEFINES"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
></A
|
|
> construction variable:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables()
|
|
vars.Add('RELEASE', 'Set to 1 to build for release', 0)
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'RELEASE_BUILD' : '${RELEASE}'})
|
|
env.Program(['foo.c', 'bar.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
This <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file first creates a <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object
|
|
(the <TT
|
|
CLASS="literal"
|
|
>vars = Variables()</TT
|
|
> call),
|
|
and then uses the object's <CODE
|
|
CLASS="function"
|
|
>Add</CODE
|
|
>
|
|
method to indicate that the <CODE
|
|
CLASS="varname"
|
|
>RELEASE</CODE
|
|
>
|
|
variable can be set on the command line,
|
|
and that its default value will be <TT
|
|
CLASS="literal"
|
|
>0</TT
|
|
>
|
|
(the third argument to the <CODE
|
|
CLASS="function"
|
|
>Add</CODE
|
|
> method).
|
|
The second argument is a line of help text;
|
|
we'll learn how to use it in the next section.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
We then pass the created <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
>
|
|
object as a <CODE
|
|
CLASS="varname"
|
|
>variables</CODE
|
|
> keyword argument
|
|
to the <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> call
|
|
used to create the construction environment.
|
|
This then allows a user to set the
|
|
<CODE
|
|
CLASS="varname"
|
|
>RELEASE</CODE
|
|
> build variable on the command line
|
|
and have the variable show up in
|
|
the command line used to build each object from
|
|
a C source file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q RELEASE=1</KBD
|
|
>
|
|
cc -o bar.o -c -DRELEASE_BUILD=1 bar.c
|
|
cc -o foo.o -c -DRELEASE_BUILD=1 foo.c
|
|
cc -o foo foo.o bar.o
|
|
</PRE
|
|
><P
|
|
>
|
|
NOTE: Before <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> release 0.98.1, these build variables
|
|
were known as "command-line build options."
|
|
The class was actually named the <CODE
|
|
CLASS="function"
|
|
>Options</CODE
|
|
> class,
|
|
and in the sections below,
|
|
the various functions were named
|
|
<CODE
|
|
CLASS="function"
|
|
>BoolOption</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>EnumOption</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>ListOption</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="function"
|
|
>PathOption</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>PackageOption</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>AddOptions</CODE
|
|
>.
|
|
These older names still work,
|
|
and you may encounter them in older
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> fles,
|
|
but their use is discouraged
|
|
and will be officially deprecated some day.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2456"
|
|
>12.2.2. Providing Help for Command-Line Build Variables</A
|
|
></H3
|
|
><P
|
|
>
|
|
To make command-line build variables most useful,
|
|
you ideally want to provide
|
|
some help text that will describe
|
|
the available variables
|
|
when the user runs <TT
|
|
CLASS="literal"
|
|
>scons -h</TT
|
|
>.
|
|
You could write this text by hand,
|
|
but <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides an easier way.
|
|
<CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> objects support a
|
|
<CODE
|
|
CLASS="function"
|
|
>GenerateHelpText</CODE
|
|
> method
|
|
that will, as its name suggests,
|
|
generate text that describes
|
|
the various variables that
|
|
have been added to it.
|
|
You then pass the output from this method to
|
|
the <CODE
|
|
CLASS="function"
|
|
>Help</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add('RELEASE', 'Set to 1 to build for release', 0)
|
|
env = Environment(variables = vars)
|
|
Help(vars.GenerateHelpText(env))
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will now display some useful text
|
|
when the <TT
|
|
CLASS="literal"
|
|
>-h</TT
|
|
> option is used:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -h</KBD
|
|
>
|
|
|
|
RELEASE: Set to 1 to build for release
|
|
default: 0
|
|
actual: 0
|
|
|
|
Use scons -H for help about command-line options.
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that the help output shows the default value,
|
|
and the current actual value of the build variable.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2471"
|
|
>12.2.3. Reading Build Variables From a File</A
|
|
></H3
|
|
><P
|
|
>
|
|
Giving the user a way to specify the
|
|
value of a build variable on the command line
|
|
is useful,
|
|
but can still be tedious
|
|
if users must specify the variable
|
|
every time they run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
We can let users provide customized build variable settings
|
|
in a local file by providing a
|
|
file name when we create the
|
|
<CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add('RELEASE', 'Set to 1 to build for release', 0)
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'RELEASE_BUILD' : '${RELEASE}'})
|
|
env.Program(['foo.c', 'bar.c'])
|
|
Help(vars.GenerateHelpText(env))
|
|
</PRE
|
|
><P
|
|
>
|
|
This then allows the user to control the <CODE
|
|
CLASS="varname"
|
|
>RELEASE</CODE
|
|
>
|
|
variable by setting it in the <TT
|
|
CLASS="filename"
|
|
>custom.py</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> RELEASE = 1
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that this file is actually executed
|
|
like a Python script.
|
|
Now when we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o bar.o -c -DRELEASE_BUILD=1 bar.c
|
|
cc -o foo.o -c -DRELEASE_BUILD=1 foo.c
|
|
cc -o foo foo.o bar.o
|
|
</PRE
|
|
><P
|
|
>
|
|
And if we change the contents of <TT
|
|
CLASS="filename"
|
|
>custom.py</TT
|
|
> to:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> RELEASE = 0
|
|
</PRE
|
|
><P
|
|
>
|
|
The object files are rebuilt appropriately
|
|
with the new variable:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o bar.o -c -DRELEASE_BUILD=0 bar.c
|
|
cc -o foo.o -c -DRELEASE_BUILD=0 foo.c
|
|
cc -o foo foo.o bar.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2491"
|
|
>12.2.4. Pre-Defined Build Variable Functions</A
|
|
></H3
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a number of functions
|
|
that provide ready-made behaviors
|
|
for various types of command-line build variables.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H4
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2495"
|
|
>12.2.4.1. True/False Values: the <CODE
|
|
CLASS="function"
|
|
>BoolVariable</CODE
|
|
> Build Variable Function</A
|
|
></H4
|
|
><P
|
|
>
|
|
It's often handy to be able to specify a
|
|
variable that controls a simple Boolean variable
|
|
with a <TT
|
|
CLASS="literal"
|
|
>true</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>false</TT
|
|
> value.
|
|
It would be even more handy to accomodate
|
|
users who have different preferences for how to represent
|
|
<TT
|
|
CLASS="literal"
|
|
>true</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>false</TT
|
|
> values.
|
|
The <CODE
|
|
CLASS="function"
|
|
>BoolVariable</CODE
|
|
> function
|
|
makes it easy to accomodate these
|
|
common representations of
|
|
<TT
|
|
CLASS="literal"
|
|
>true</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>false</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>BoolVariable</CODE
|
|
> function takes three arguments:
|
|
the name of the build variable,
|
|
the default value of the build variable,
|
|
and the help string for the variable.
|
|
It then returns appropriate information for
|
|
passing to the <CODE
|
|
CLASS="function"
|
|
>Add</CODE
|
|
> method of a <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object, like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(BoolVariable('RELEASE', 'Set to build for release', 0))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'RELEASE_BUILD' : '${RELEASE}'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
With this build variable,
|
|
the <CODE
|
|
CLASS="varname"
|
|
>RELEASE</CODE
|
|
> variable can now be enabled by
|
|
setting it to the value <TT
|
|
CLASS="literal"
|
|
>yes</TT
|
|
>
|
|
or <TT
|
|
CLASS="literal"
|
|
>t</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q RELEASE=yes foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DRELEASE_BUILD=True foo.c
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q RELEASE=t foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DRELEASE_BUILD=True foo.c
|
|
</PRE
|
|
><P
|
|
>
|
|
Other values that equate to <TT
|
|
CLASS="literal"
|
|
>true</TT
|
|
> include
|
|
<TT
|
|
CLASS="literal"
|
|
>y</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>1</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>on</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="literal"
|
|
>all</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Conversely, <CODE
|
|
CLASS="varname"
|
|
>RELEASE</CODE
|
|
> may now be given a <TT
|
|
CLASS="literal"
|
|
>false</TT
|
|
>
|
|
value by setting it to
|
|
<TT
|
|
CLASS="literal"
|
|
>no</TT
|
|
>
|
|
or
|
|
<TT
|
|
CLASS="literal"
|
|
>f</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q RELEASE=no foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DRELEASE_BUILD=False foo.c
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q RELEASE=f foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DRELEASE_BUILD=False foo.c
|
|
</PRE
|
|
><P
|
|
>
|
|
Other values that equate to <TT
|
|
CLASS="literal"
|
|
>false</TT
|
|
> include
|
|
<TT
|
|
CLASS="literal"
|
|
>n</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>0</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>off</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="literal"
|
|
>none</TT
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Lastly, if a user tries to specify
|
|
any other value,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supplies an appropriate error message:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q RELEASE=bad_value foo.o</KBD
|
|
>
|
|
|
|
scons: *** Error converting option: RELEASE
|
|
Invalid value for boolean option: bad_value
|
|
File "/home/my/project/SConstruct", line 4, in <module>
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H4
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2544"
|
|
>12.2.4.2. Single Value From a List: the <CODE
|
|
CLASS="function"
|
|
>EnumVariable</CODE
|
|
> Build Variable Function</A
|
|
></H4
|
|
><P
|
|
>
|
|
Suppose that we want a user to be able to
|
|
set a <CODE
|
|
CLASS="varname"
|
|
>COLOR</CODE
|
|
> variable
|
|
that selects a background color to be
|
|
displayed by an application,
|
|
but that we want to restrict the
|
|
choices to a specific set of allowed colors.
|
|
This can be set up quite easily
|
|
using the <CODE
|
|
CLASS="function"
|
|
>EnumVariable</CODE
|
|
>,
|
|
which takes a list of <CODE
|
|
CLASS="varname"
|
|
>allowed_values</CODE
|
|
> in addition to the variable name,
|
|
default value,
|
|
and help text arguments:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(EnumVariable('COLOR', 'Set background color', 'red',
|
|
allowed_values=('red', 'green', 'blue')))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'COLOR' : '"${COLOR}"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
The user can now explicity set the <CODE
|
|
CLASS="varname"
|
|
>COLOR</CODE
|
|
> build variable
|
|
to any of the specified allowed values:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=red foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="red" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=blue foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="blue" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=green foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="green" foo.c
|
|
</PRE
|
|
><P
|
|
>
|
|
But, almost more importantly,
|
|
an attempt to set <CODE
|
|
CLASS="varname"
|
|
>COLOR</CODE
|
|
>
|
|
to a value that's not in the list
|
|
generates an error message:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=magenta foo.o</KBD
|
|
>
|
|
|
|
scons: *** Invalid value for option COLOR: magenta
|
|
File "/home/my/project/SConstruct", line 5, in <module>
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>EnumVariable</CODE
|
|
> function also supports a way
|
|
to map alternate names to allowed values.
|
|
Suppose, for example,
|
|
that we want to allow the user
|
|
to use the word <TT
|
|
CLASS="literal"
|
|
>navy</TT
|
|
> as a synonym for
|
|
<TT
|
|
CLASS="literal"
|
|
>blue</TT
|
|
>.
|
|
We do this by adding a <CODE
|
|
CLASS="varname"
|
|
>map</CODE
|
|
> dictionary
|
|
that will map its key values
|
|
to the desired legal value:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(EnumVariable('COLOR', 'Set background color', 'red',
|
|
allowed_values=('red', 'green', 'blue'),
|
|
map={'navy':'blue'}))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'COLOR' : '"${COLOR}"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
As desired, the user can then use
|
|
<TT
|
|
CLASS="literal"
|
|
>navy</TT
|
|
> on the command line,
|
|
and <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will translate it into <TT
|
|
CLASS="literal"
|
|
>blue</TT
|
|
>
|
|
when it comes time to use the <CODE
|
|
CLASS="varname"
|
|
>COLOR</CODE
|
|
>
|
|
variable to build a target:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=navy foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="blue" foo.c
|
|
</PRE
|
|
><P
|
|
>
|
|
By default, when using the <CODE
|
|
CLASS="function"
|
|
>EnumVariable</CODE
|
|
> function,
|
|
arguments that differ
|
|
from the legal values
|
|
only in case
|
|
are treated as illegal values:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=Red foo.o</KBD
|
|
>
|
|
|
|
scons: *** Invalid value for option COLOR: Red
|
|
File "/home/my/project/SConstruct", line 5, in <module>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=BLUE foo.o</KBD
|
|
>
|
|
|
|
scons: *** Invalid value for option COLOR: BLUE
|
|
File "/home/my/project/SConstruct", line 5, in <module>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=nAvY foo.o</KBD
|
|
>
|
|
|
|
scons: *** Invalid value for option COLOR: nAvY
|
|
File "/home/my/project/SConstruct", line 5, in <module>
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>EnumVariable</CODE
|
|
> function can take an additional
|
|
<CODE
|
|
CLASS="varname"
|
|
>ignorecase</CODE
|
|
> keyword argument that,
|
|
when set to <TT
|
|
CLASS="literal"
|
|
>1</TT
|
|
>,
|
|
tells <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to allow case differences
|
|
when the values are specified:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(EnumVariable('COLOR', 'Set background color', 'red',
|
|
allowed_values=('red', 'green', 'blue'),
|
|
map={'navy':'blue'},
|
|
ignorecase=1))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'COLOR' : '"${COLOR}"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Which yields the output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=Red foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="Red" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=BLUE foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="BLUE" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=nAvY foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="blue" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=green foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="green" foo.c
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that an <CODE
|
|
CLASS="varname"
|
|
>ignorecase</CODE
|
|
> value of <TT
|
|
CLASS="literal"
|
|
>1</TT
|
|
>
|
|
preserves the case-spelling that the user supplied.
|
|
If you want <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to translate the names
|
|
into lower-case,
|
|
regardless of the case used by the user,
|
|
specify an <CODE
|
|
CLASS="varname"
|
|
>ignorecase</CODE
|
|
> value of <TT
|
|
CLASS="literal"
|
|
>2</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(EnumVariable('COLOR', 'Set background color', 'red',
|
|
allowed_values=('red', 'green', 'blue'),
|
|
map={'navy':'blue'},
|
|
ignorecase=2))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'COLOR' : '"${COLOR}"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Now <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will use values of
|
|
<TT
|
|
CLASS="literal"
|
|
>red</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>green</TT
|
|
> or
|
|
<TT
|
|
CLASS="literal"
|
|
>blue</TT
|
|
>
|
|
regardless of how the user spells
|
|
those values on the command line:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=Red foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="red" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=nAvY foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="blue" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLOR=GREEN foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLOR="green" foo.c
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H4
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2609"
|
|
>12.2.4.3. Multiple Values From a List: the <CODE
|
|
CLASS="function"
|
|
>ListVariable</CODE
|
|
> Build Variable Function</A
|
|
></H4
|
|
><P
|
|
>
|
|
Another way in which you might want to allow users
|
|
to control a build variable is to
|
|
specify a list of one or more legal values.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports this through the <CODE
|
|
CLASS="function"
|
|
>ListVariable</CODE
|
|
> function.
|
|
If, for example, we want a user to be able to set a
|
|
<CODE
|
|
CLASS="varname"
|
|
>COLORS</CODE
|
|
> variable to one or more of the legal list of values:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(ListVariable('COLORS', 'List of colors', 0,
|
|
['red', 'green', 'blue']))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'COLORS' : '"${COLORS}"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
A user can now specify a comma-separated list
|
|
of legal values,
|
|
which will get translated into a space-separated
|
|
list for passing to the any build commands:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLORS=red,blue foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLORS="red blue" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLORS=blue,green,red foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLORS="blue green red" foo.c
|
|
</PRE
|
|
><P
|
|
>
|
|
In addition, the <CODE
|
|
CLASS="function"
|
|
>ListVariable</CODE
|
|
> function
|
|
allows the user to specify explicit keywords of
|
|
<TT
|
|
CLASS="literal"
|
|
>all</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>none</TT
|
|
>
|
|
to select all of the legal values,
|
|
or none of them, respectively:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLORS=all foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLORS="red green blue" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLORS=none foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCOLORS="" foo.c
|
|
</PRE
|
|
><P
|
|
>
|
|
And, of course, an illegal value
|
|
still generates an error message:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q COLORS=magenta foo.o</KBD
|
|
>
|
|
|
|
scons: *** Error converting option: COLORS
|
|
Invalid value(s) for option: magenta
|
|
File "/home/my/project/SConstruct", line 5, in <module>
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H4
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2631"
|
|
>12.2.4.4. Path Names: the <CODE
|
|
CLASS="function"
|
|
>PathVariable</CODE
|
|
> Build Variable Function</A
|
|
></H4
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a <CODE
|
|
CLASS="function"
|
|
>PathVariable</CODE
|
|
> function
|
|
to make it easy to create a build variable
|
|
to control an expected path name.
|
|
If, for example, you need to
|
|
define a variable in the preprocessor
|
|
that controls the location of a
|
|
configuration file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(PathVariable('CONFIG',
|
|
'Path to configuration file',
|
|
'/etc/my_config'))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'CONFIG_FILE' : '"$CONFIG"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
This then allows the user to
|
|
override the <CODE
|
|
CLASS="varname"
|
|
>CONFIG</CODE
|
|
> build variable
|
|
on the command line as necessary:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DCONFIG_FILE="/etc/my_config" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q CONFIG=/usr/local/etc/other_config foo.o</KBD
|
|
>
|
|
scons: `foo.o' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
By default, <CODE
|
|
CLASS="function"
|
|
>PathVariable</CODE
|
|
> checks to make sure
|
|
that the specified path exists and generates an error if it
|
|
doesn't:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q CONFIG=/does/not/exist foo.o</KBD
|
|
>
|
|
|
|
scons: *** Path for option CONFIG does not exist: /does/not/exist
|
|
File "/home/my/project/SConstruct", line 6, in <module>
|
|
</PRE
|
|
><P
|
|
>
|
|
<CODE
|
|
CLASS="function"
|
|
>PathVariable</CODE
|
|
> provides a number of methods
|
|
that you can use to change this behavior.
|
|
If you want to ensure that any specified paths are,
|
|
in fact, files and not directories,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>PathVariable.PathIsFile</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(PathVariable('CONFIG',
|
|
'Path to configuration file',
|
|
'/etc/my_config',
|
|
PathVariable.PathIsFile))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'CONFIG_FILE' : '"$CONFIG"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Conversely, to ensure that any specified paths are
|
|
directories and not files,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>PathVariable.PathIsDir</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(PathVariable('DBDIR',
|
|
'Path to database directory',
|
|
'/var/my_dbdir',
|
|
PathVariable.PathIsDir))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'DBDIR' : '"$DBDIR"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
If you want to make sure that any specified paths
|
|
are directories,
|
|
and you would like the directory created
|
|
if it doesn't already exist,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>PathVariable.PathIsDirCreate</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(PathVariable('DBDIR',
|
|
'Path to database directory',
|
|
'/var/my_dbdir',
|
|
PathVariable.PathIsDirCreate))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'DBDIR' : '"$DBDIR"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Lastly, if you don't care whether the path exists,
|
|
is a file, or a directory,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>PathVariable.PathAccept</CODE
|
|
> method
|
|
to accept any path that the user supplies:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(PathVariable('OUTPUT',
|
|
'Path to output file or directory',
|
|
None,
|
|
PathVariable.PathAccept))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'OUTPUT' : '"$OUTPUT"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H4
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2660"
|
|
>12.2.4.5. Enabled/Disabled Path Names: the <CODE
|
|
CLASS="function"
|
|
>PackageVariable</CODE
|
|
> Build Variable Function</A
|
|
></H4
|
|
><P
|
|
>
|
|
Sometimes you want to give users
|
|
even more control over a path name variable,
|
|
allowing them to explicitly enable or
|
|
disable the path name
|
|
by using <TT
|
|
CLASS="literal"
|
|
>yes</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>no</TT
|
|
> keywords,
|
|
in addition to allow them
|
|
to supply an explicit path name.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports the <CODE
|
|
CLASS="function"
|
|
>PackageVariable</CODE
|
|
>
|
|
function to support this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables('custom.py')
|
|
vars.Add(PackageVariable('PACKAGE',
|
|
'Location package',
|
|
'/opt/location'))
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'PACKAGE' : '"$PACKAGE"'})
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
When the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file uses the <CODE
|
|
CLASS="function"
|
|
>PackageVariable</CODE
|
|
> funciton,
|
|
user can now still use the default
|
|
or supply an overriding path name,
|
|
but can now explicitly set the
|
|
specified variable to a value
|
|
that indicates the package should be enabled
|
|
(in which case the default should be used)
|
|
or disabled:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DPACKAGE="/opt/location" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q PACKAGE=/usr/local/location foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DPACKAGE="/usr/local/location" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q PACKAGE=yes foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DPACKAGE="True" foo.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q PACKAGE=no foo.o</KBD
|
|
>
|
|
cc -o foo.o -c -DPACKAGE="False" foo.c
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2677"
|
|
>12.2.5. Adding Multiple Command-Line Build Variables at Once</A
|
|
></H3
|
|
><P
|
|
>
|
|
Lastly, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a way to add
|
|
multiple build variables to a <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object at once.
|
|
Instead of having to call the <CODE
|
|
CLASS="function"
|
|
>Add</CODE
|
|
> method
|
|
multiple times,
|
|
you can call the <CODE
|
|
CLASS="function"
|
|
>AddVariables</CODE
|
|
>
|
|
method with a list of build variables
|
|
to be added to the object.
|
|
Each build variable is specified
|
|
as either a tuple of arguments,
|
|
just like you'd pass to the <CODE
|
|
CLASS="function"
|
|
>Add</CODE
|
|
> method itself,
|
|
or as a call to one of the pre-defined
|
|
functions for pre-packaged command-line build variables.
|
|
in any order:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables()
|
|
vars.AddVariables(
|
|
('RELEASE', 'Set to 1 to build for release', 0),
|
|
('CONFIG', 'Configuration file', '/etc/my_config'),
|
|
BoolVariable('warnings', 'compilation with -Wall and similiar', 1),
|
|
EnumVariable('debug', 'debug output and symbols', 'no',
|
|
allowed_values=('yes', 'no', 'full'),
|
|
map={}, ignorecase=0), # case sensitive
|
|
ListVariable('shared',
|
|
'libraries to build as shared libraries',
|
|
'all',
|
|
names = list_of_libs),
|
|
PackageVariable('x11',
|
|
'use X11 installed here (yes = search some places)',
|
|
'yes'),
|
|
PathVariable('qtdir', 'where the root of Qt is installed', qtdir),
|
|
)
|
|
</PRE
|
|
><P
|
|
> </P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2687"
|
|
>12.2.6. Handling Unknown Command-Line Build Variables: the <CODE
|
|
CLASS="function"
|
|
>UnknownVariables</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
Users may, of course,
|
|
occasionally misspell variable names in their command-line settings.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not generate an error or warning
|
|
for any unknown variables the users specifies on the command line.
|
|
(This is in no small part because you may be
|
|
processing the arguments directly using the <CODE
|
|
CLASS="varname"
|
|
>ARGUMENTS</CODE
|
|
> dictionary,
|
|
and therefore <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> can't know in the general case
|
|
whether a given "misspelled" variable is
|
|
really unknown and a potential problem,
|
|
or something that your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file
|
|
will handle directly with some Python code.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If, however, you're using a <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object to
|
|
define a specific set of command-line build variables
|
|
that you expect users to be able to set,
|
|
you may want to provide an error
|
|
message or warning of your own
|
|
if the user supplies a variable setting
|
|
that is <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
> among
|
|
the defined list of variable names known to the <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object.
|
|
You can do this by calling the <CODE
|
|
CLASS="function"
|
|
>UnknownVariables</CODE
|
|
>
|
|
method of the <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> vars = Variables(None)
|
|
vars.Add('RELEASE', 'Set to 1 to build for release', 0)
|
|
env = Environment(variables = vars,
|
|
CPPDEFINES={'RELEASE_BUILD' : '${RELEASE}'})
|
|
unknown = vars.UnknownVariables()
|
|
if unknown:
|
|
print "Unknown variables:", unknown.keys()
|
|
Exit(1)
|
|
env.Program('foo.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>UnknownVariables</CODE
|
|
> method returns a dictionary
|
|
containing the keywords and values
|
|
of any variables the user specified on the command line
|
|
that are <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
among the variables known to the <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object
|
|
(from having been specified using
|
|
the <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object's<CODE
|
|
CLASS="function"
|
|
>Add</CODE
|
|
> method).
|
|
In the examble above,
|
|
we check for whether the dictionary
|
|
returned by the <CODE
|
|
CLASS="function"
|
|
>UnknownVariables</CODE
|
|
> is non-empty,
|
|
and if so print the Python list
|
|
containing the names of the unknwown variables
|
|
and then call the <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> function
|
|
to terminate <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q NOT_KNOWN=foo</KBD
|
|
>
|
|
Unknown variables: ['NOT_KNOWN']
|
|
</PRE
|
|
><P
|
|
>
|
|
Of course, you can process the items in the
|
|
dictionary returned by the <CODE
|
|
CLASS="function"
|
|
>UnknownVariables</CODE
|
|
> function
|
|
in any way appropriate to your bulid configuration,
|
|
including just printing a warning message
|
|
but not exiting,
|
|
logging an error somewhere,
|
|
etc.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that you must delay the call of <CODE
|
|
CLASS="function"
|
|
>UnknownVariables</CODE
|
|
>
|
|
until after you have applied the <CODE
|
|
CLASS="function"
|
|
>Variables</CODE
|
|
> object
|
|
to a construction environment
|
|
with the <TT
|
|
CLASS="literal"
|
|
>variables=</TT
|
|
>
|
|
keyword argument of an <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> call.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="sect-command-line-targets"
|
|
>12.3. Command-Line Targets</A
|
|
></H2
|
|
><DIV
|
|
CLASS="section"
|
|
><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2722"
|
|
>12.3.1. Fetching Command-Line Targets: the <CODE
|
|
CLASS="varname"
|
|
>COMMAND_LINE_TARGETS</CODE
|
|
> Variable</A
|
|
></H3
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a <CODE
|
|
CLASS="varname"
|
|
>COMMAND_LINE_TARGETS</CODE
|
|
> variable
|
|
that lets you fetch the list of targets that the
|
|
user specified on the command line.
|
|
You can use the targets to manipulate the
|
|
build in any way you wish.
|
|
As a simple example,
|
|
suppose that you want to print a reminder
|
|
to the user whenever a specific program is built.
|
|
You can do this by checking for the
|
|
target in the <CODE
|
|
CLASS="varname"
|
|
>COMMAND_LINE_TARGETS</CODE
|
|
> list:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> if 'bar' in COMMAND_LINE_TARGETS:
|
|
print "Don't forget to copy `bar' to the archive!"
|
|
Default(Program('foo.c'))
|
|
Program('bar.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then, running <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> with the default target
|
|
works as it always does,
|
|
but explicity specifying the <SPAN
|
|
CLASS="application"
|
|
>bar</SPAN
|
|
> target
|
|
on the command line generates the warning message:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o foo.o -c foo.c
|
|
cc -o foo foo.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q bar</KBD
|
|
>
|
|
Don't forget to copy `bar' to the archive!
|
|
cc -o bar.o -c bar.c
|
|
cc -o bar bar.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Another practical use for the <CODE
|
|
CLASS="varname"
|
|
>COMMAND_LINE_TARGETS</CODE
|
|
> variable
|
|
might be to speed up a build
|
|
by only reading certain subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>
|
|
files if a specific target is requested.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2739"
|
|
>12.3.2. Controlling the Default Targets: the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> Function</A
|
|
></H3
|
|
><P
|
|
>
|
|
One of the most basic things you can control
|
|
is which targets <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will build by default--that is,
|
|
when there are no targets specified on the command line.
|
|
As mentioned previously,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will normally build every target
|
|
in or below the current directory
|
|
by default--that is, when you don't
|
|
explicitly specify one or more targets
|
|
on the command line.
|
|
Sometimes, however, you may want
|
|
to specify explicitly that only
|
|
certain programs, or programs in certain directories,
|
|
should be built by default.
|
|
You do this with the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
env.Program('goodbye.c')
|
|
Default(hello)
|
|
</PRE
|
|
><P
|
|
>
|
|
This <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file knows how to build two programs,
|
|
<SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> and <SPAN
|
|
CLASS="application"
|
|
>goodbye</SPAN
|
|
>,
|
|
but only builds the
|
|
<SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program by default:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `hello' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q goodbye</KBD
|
|
>
|
|
cc -o goodbye.o -c goodbye.c
|
|
cc -o goodbye goodbye.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that, even when you use the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
>
|
|
function in your <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file,
|
|
you can still explicitly specify the current directory
|
|
(<TT
|
|
CLASS="literal"
|
|
>.</TT
|
|
>) on the command line
|
|
to tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to build
|
|
everything in (or below) the current directory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q .</KBD
|
|
>
|
|
cc -o goodbye.o -c goodbye.c
|
|
cc -o goodbye goodbye.o
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
You can also call the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
>
|
|
function more than once,
|
|
in which case each call
|
|
adds to the list of targets to be built by default:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
prog1 = env.Program('prog1.c')
|
|
Default(prog1)
|
|
prog2 = env.Program('prog2.c')
|
|
prog3 = env.Program('prog3.c')
|
|
Default(prog3)
|
|
</PRE
|
|
><P
|
|
>
|
|
Or you can specify more than one target
|
|
in a single call to the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
prog1 = env.Program('prog1.c')
|
|
prog2 = env.Program('prog2.c')
|
|
prog3 = env.Program('prog3.c')
|
|
Default(prog1, prog3)
|
|
</PRE
|
|
><P
|
|
>
|
|
Either of these last two examples
|
|
will build only the
|
|
<SPAN
|
|
CLASS="application"
|
|
>prog1</SPAN
|
|
>
|
|
and
|
|
<SPAN
|
|
CLASS="application"
|
|
>prog3</SPAN
|
|
>
|
|
programs by default:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o prog1.o -c prog1.c
|
|
cc -o prog1 prog1.o
|
|
cc -o prog3.o -c prog3.c
|
|
cc -o prog3 prog3.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q .</KBD
|
|
>
|
|
cc -o prog2.o -c prog2.c
|
|
cc -o prog2 prog2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
You can list a directory as
|
|
an argument to <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program(['prog1/main.c', 'prog1/foo.c'])
|
|
env.Program(['prog2/main.c', 'prog2/bar.c'])
|
|
Default('prog1')
|
|
</PRE
|
|
><P
|
|
>
|
|
In which case only the target(s) in that
|
|
directory will be built by default:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o prog1/foo.o -c prog1/foo.c
|
|
cc -o prog1/main.o -c prog1/main.c
|
|
cc -o prog1/main prog1/main.o prog1/foo.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `prog1' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q .</KBD
|
|
>
|
|
cc -o prog2/bar.o -c prog2/bar.c
|
|
cc -o prog2/main.o -c prog2/main.c
|
|
cc -o prog2/main prog2/main.o prog2/bar.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Lastly, if for some reason you don't want
|
|
any targets built by default,
|
|
you can use the Python <TT
|
|
CLASS="literal"
|
|
>None</TT
|
|
>
|
|
variable:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
prog1 = env.Program('prog1.c')
|
|
prog2 = env.Program('prog2.c')
|
|
Default(None)
|
|
</PRE
|
|
><P
|
|
>
|
|
Which would produce build output like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: *** No targets specified and no Default() targets found. Stop.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q .</KBD
|
|
>
|
|
cc -o prog1.o -c prog1.c
|
|
cc -o prog1 prog1.o
|
|
cc -o prog2.o -c prog2.c
|
|
cc -o prog2 prog2.o
|
|
</PRE
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H4
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2790"
|
|
>12.3.2.1. Fetching the List of Default Targets: the <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> Variable</A
|
|
></H4
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> variable
|
|
that lets you get at the current list of default targets.
|
|
The <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> variable has
|
|
two important differences from the <CODE
|
|
CLASS="varname"
|
|
>COMMAND_LINE_TARGETS</CODE
|
|
> variable.
|
|
First, the <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> variable is a list of
|
|
internal <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> nodes,
|
|
so you need to convert the list elements to strings
|
|
if you want to print them or look for a specific target name.
|
|
Fortunately, you can do this easily
|
|
by using the Python <CODE
|
|
CLASS="function"
|
|
>map</CODE
|
|
> function
|
|
to run the list through <CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> prog1 = Program('prog1.c')
|
|
Default(prog1)
|
|
print "DEFAULT_TARGETS is", map(str, DEFAULT_TARGETS)
|
|
</PRE
|
|
><P
|
|
>
|
|
(Keep in mind that all of the manipulation of the
|
|
<CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> list takes place during the
|
|
first phase when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is reading up the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
which is obvious if
|
|
we leave off the <TT
|
|
CLASS="literal"
|
|
>-Q</TT
|
|
> flag when we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>:)
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
DEFAULT_TARGETS is ['prog1']
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cc -o prog1.o -c prog1.c
|
|
cc -o prog1 prog1.o
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
Second,
|
|
the contents of the <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> list change
|
|
in response to calls to the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
>: function,
|
|
as you can see from the following <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> prog1 = Program('prog1.c')
|
|
Default(prog1)
|
|
print "DEFAULT_TARGETS is now", map(str, DEFAULT_TARGETS)
|
|
prog2 = Program('prog2.c')
|
|
Default(prog2)
|
|
print "DEFAULT_TARGETS is now", map(str, DEFAULT_TARGETS)
|
|
</PRE
|
|
><P
|
|
>
|
|
Which yields the output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
DEFAULT_TARGETS is now ['prog1']
|
|
DEFAULT_TARGETS is now ['prog1', 'prog2']
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
cc -o prog1.o -c prog1.c
|
|
cc -o prog1 prog1.o
|
|
cc -o prog2.o -c prog2.c
|
|
cc -o prog2 prog2.o
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
In practice, this simply means that you
|
|
need to pay attention to the order in
|
|
which you call the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> function
|
|
and refer to the <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> list,
|
|
to make sure that you don't examine the
|
|
list before you've added the default targets
|
|
you expect to find in it.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2822"
|
|
>12.3.3. Fetching the List of Build Targets, Regardless of Origin: the <CODE
|
|
CLASS="varname"
|
|
>BUILD_TARGETS</CODE
|
|
> Variable</A
|
|
></H3
|
|
><P
|
|
>
|
|
We've already been introduced to the
|
|
<CODE
|
|
CLASS="varname"
|
|
>COMMAND_LINE_TARGETS</CODE
|
|
> variable,
|
|
which contains a list of targets specified on the command line,
|
|
and the <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> variable,
|
|
which contains a list of targets specified
|
|
via calls to the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> method or function.
|
|
Sometimes, however,
|
|
you want a list of whatever targets
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will try to build,
|
|
regardless of whether the targets came from the
|
|
command line or a <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> call.
|
|
You could code this up by hand, as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> if COMMAND_LINE_TARGETS:
|
|
targets = COMMAND_LINE_TARGETS
|
|
else:
|
|
targets = DEFAULT_TARGETS
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>, however, provides a convenient
|
|
<CODE
|
|
CLASS="varname"
|
|
>BUILD_TARGETS</CODE
|
|
> variable
|
|
that eliminates the need for this by-hand manipulation.
|
|
Essentially, the <CODE
|
|
CLASS="varname"
|
|
>BUILD_TARGETS</CODE
|
|
> variable
|
|
contains a list of the command-line targets,
|
|
if any were specified,
|
|
and if no command-line targets were specified,
|
|
it contains a list of the targets specified
|
|
via the <CODE
|
|
CLASS="function"
|
|
>Default</CODE
|
|
> method or function.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Because <CODE
|
|
CLASS="varname"
|
|
>BUILD_TARGETS</CODE
|
|
> may contain a list of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> nodes,
|
|
you must convert the list elements to strings
|
|
if you want to print them or look for a specific target name,
|
|
just like the <CODE
|
|
CLASS="varname"
|
|
>DEFAULT_TARGETS</CODE
|
|
> list:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> prog1 = Program('prog1.c')
|
|
Program('prog2.c')
|
|
Default(prog1)
|
|
print "BUILD_TARGETS is", map(str, BUILD_TARGETS)
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice how the value of <CODE
|
|
CLASS="varname"
|
|
>BUILD_TARGETS</CODE
|
|
>
|
|
changes depending on whether a target is
|
|
specified on the command line:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
BUILD_TARGETS is ['prog1']
|
|
cc -o prog1.o -c prog1.c
|
|
cc -o prog1 prog1.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q prog2</KBD
|
|
>
|
|
BUILD_TARGETS is ['prog2']
|
|
cc -o prog2.o -c prog2.c
|
|
cc -o prog2 prog2.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c .</KBD
|
|
>
|
|
BUILD_TARGETS is ['.']
|
|
Removed prog1.o
|
|
Removed prog1
|
|
Removed prog2.o
|
|
Removed prog2
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-install"
|
|
></A
|
|
>Chapter 13. Installing Files in Other Directories: the <CODE
|
|
CLASS="function"
|
|
>Install</CODE
|
|
> Builder</H1
|
|
><P
|
|
>
|
|
Once a program is built,
|
|
it is often appropriate to install it in another
|
|
directory for public use.
|
|
You use the <CODE
|
|
CLASS="function"
|
|
>Install</CODE
|
|
> method
|
|
to arrange for a program, or any other file,
|
|
to be copied into a destination directory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
env.Install('/usr/bin', hello)
|
|
</PRE
|
|
><P
|
|
>
|
|
Note, however, that installing a file is
|
|
still considered a type of file "build."
|
|
This is important when you remember that
|
|
the default behavior of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is
|
|
to build files in or below the current directory.
|
|
If, as in the example above,
|
|
you are installing files in a directory
|
|
outside of the top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file's directory tree,
|
|
you must specify that directory
|
|
(or a higher directory, such as <TT
|
|
CLASS="literal"
|
|
>/</TT
|
|
>)
|
|
for it to install anything there:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q /usr/bin</KBD
|
|
>
|
|
Install file: "hello" as "/usr/bin/hello"
|
|
</PRE
|
|
><P
|
|
>
|
|
It can, however, be cumbersome to remember
|
|
(and type) the specific destination directory
|
|
in which the program (or any other file)
|
|
should be installed.
|
|
This is an area where the <CODE
|
|
CLASS="function"
|
|
>Alias</CODE
|
|
>
|
|
function comes in handy,
|
|
allowing you, for example,
|
|
to create a pseudo-target named <TT
|
|
CLASS="literal"
|
|
>install</TT
|
|
>
|
|
that can expand to the specified destination directory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
env.Install('/usr/bin', hello)
|
|
env.Alias('install', '/usr/bin')
|
|
</PRE
|
|
><P
|
|
>
|
|
This then yields the more natural
|
|
ability to install the program
|
|
in its destination as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install</KBD
|
|
>
|
|
Install file: "hello" as "/usr/bin/hello"
|
|
</PRE
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2869"
|
|
>13.1. Installing Multiple Files in a Directory</A
|
|
></H2
|
|
><P
|
|
>
|
|
You can install multiple files into a directory
|
|
simply by calling the <CODE
|
|
CLASS="function"
|
|
>Install</CODE
|
|
> function multiple times:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
goodbye = env.Program('goodbye.c')
|
|
env.Install('/usr/bin', hello)
|
|
env.Install('/usr/bin', goodbye)
|
|
env.Alias('install', '/usr/bin')
|
|
</PRE
|
|
><P
|
|
>
|
|
Or, more succinctly, listing the multiple input
|
|
files in a list
|
|
(just like you can do with any other builder):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
goodbye = env.Program('goodbye.c')
|
|
env.Install('/usr/bin', [hello, goodbye])
|
|
env.Alias('install', '/usr/bin')
|
|
</PRE
|
|
><P
|
|
>
|
|
Either of these two examples yields:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install</KBD
|
|
>
|
|
cc -o goodbye.o -c goodbye.c
|
|
cc -o goodbye goodbye.o
|
|
Install file: "goodbye" as "/usr/bin/goodbye"
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
Install file: "hello" as "/usr/bin/hello"
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2879"
|
|
>13.2. Installing a File Under a Different Name</A
|
|
></H2
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Install</CODE
|
|
> method preserves the name
|
|
of the file when it is copied into the
|
|
destination directory.
|
|
If you need to change the name of the file
|
|
when you copy it, use the <CODE
|
|
CLASS="function"
|
|
>InstallAs</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
env.InstallAs('/usr/bin/hello-new', hello)
|
|
env.Alias('install', '/usr/bin')
|
|
</PRE
|
|
><P
|
|
>
|
|
This installs the <TT
|
|
CLASS="literal"
|
|
>hello</TT
|
|
>
|
|
program with the name <TT
|
|
CLASS="literal"
|
|
>hello-new</TT
|
|
>
|
|
as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
Install file: "hello" as "/usr/bin/hello-new"
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2890"
|
|
>13.3. Installing Multiple Files Under Different Names</A
|
|
></H2
|
|
><P
|
|
>
|
|
Lastly, if you have multiple files that all
|
|
need to be installed with different file names,
|
|
you can either call the <CODE
|
|
CLASS="function"
|
|
>InstallAs</CODE
|
|
> function
|
|
multiple times, or as a shorthand,
|
|
you can supply same-length lists
|
|
for both the target and source arguments:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
goodbye = env.Program('goodbye.c')
|
|
env.InstallAs(['/usr/bin/hello-new',
|
|
'/usr/bin/goodbye-new'],
|
|
[hello, goodbye])
|
|
env.Alias('install', '/usr/bin')
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case, the <CODE
|
|
CLASS="function"
|
|
>InstallAs</CODE
|
|
> function
|
|
loops through both lists simultaneously,
|
|
and copies each source file into its corresponding
|
|
target file name:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install</KBD
|
|
>
|
|
cc -o goodbye.o -c goodbye.c
|
|
cc -o goodbye goodbye.o
|
|
Install file: "goodbye" as "/usr/bin/goodbye-new"
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
Install file: "hello" as "/usr/bin/hello-new"
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-factories"
|
|
></A
|
|
>Chapter 14. Platform-Independent File System Manipulation</H1
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a number of platform-independent functions,
|
|
called <TT
|
|
CLASS="literal"
|
|
>factories</TT
|
|
>,
|
|
that perform common file system manipulations
|
|
like copying, moving or deleting files and directories,
|
|
or making directories.
|
|
These functions are <TT
|
|
CLASS="literal"
|
|
>factories</TT
|
|
>
|
|
because they don't perform the action
|
|
at the time they're called,
|
|
they each return an <CODE
|
|
CLASS="classname"
|
|
>Action</CODE
|
|
> object
|
|
that can be executed at the appropriate time.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2906"
|
|
>14.1. Copying Files or Directories: The <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> Factory</A
|
|
></H2
|
|
><P
|
|
>
|
|
Suppose you want to arrange to make a copy of a file,
|
|
and don't have a suitable pre-existing builder.
|
|
<A
|
|
NAME="AEN2910"
|
|
HREF="#FTN.AEN2910"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[4]</SPAN
|
|
></A
|
|
>
|
|
One way would be to use the <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> action factory
|
|
in conjunction with the <CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> builder:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in", Copy("$TARGET", "$SOURCE"))
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that the action returned by the <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> factory
|
|
will expand the <A
|
|
HREF="#cv-TARGET"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARGET</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-SOURCE"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SOURCE</CODE
|
|
></A
|
|
> strings
|
|
at the time <TT
|
|
CLASS="filename"
|
|
>file.out</TT
|
|
> is built,
|
|
and that the order of the arguments
|
|
is the same as that of a builder itself--that is,
|
|
target first, followed by source:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Copy("file.out", "file.in")
|
|
</PRE
|
|
><P
|
|
>
|
|
You can, of course, name a file explicitly
|
|
instead of using <CODE
|
|
CLASS="envar"
|
|
>$TARGET</CODE
|
|
> or <CODE
|
|
CLASS="envar"
|
|
>$SOURCE</CODE
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", [], Copy("$TARGET", "file.in"))
|
|
</PRE
|
|
><P
|
|
>
|
|
Which executes as:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Copy("file.out", "file.in")
|
|
</PRE
|
|
><P
|
|
>
|
|
The usefulness of the <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> factory
|
|
becomes more apparent when
|
|
you use it in a list of actions
|
|
passed to the <CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> builder.
|
|
For example, suppose you needed to run a
|
|
file through a utility that only modifies files in-place,
|
|
and can't "pipe" input to output.
|
|
One solution is to copy the source file
|
|
to a temporary file name,
|
|
run the utility,
|
|
and then copy the modified temporary file to the target,
|
|
which the <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> factory makes extremely easy:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in",
|
|
[
|
|
Copy("tempfile", "$SOURCE"),
|
|
"modify tempfile",
|
|
Copy("$TARGET", "tempfile"),
|
|
])
|
|
</PRE
|
|
><P
|
|
>
|
|
The output then looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Copy("tempfile", "file.in")
|
|
modify tempfile
|
|
Copy("file.out", "tempfile")
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2940"
|
|
>14.2. Deleting Files or Directories: The <CODE
|
|
CLASS="function"
|
|
>Delete</CODE
|
|
> Factory</A
|
|
></H2
|
|
><P
|
|
>
|
|
If you need to delete a file,
|
|
then the <CODE
|
|
CLASS="function"
|
|
>Delete</CODE
|
|
> factory
|
|
can be used in much the same way as
|
|
the <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> factory.
|
|
For example, if we want to make sure that
|
|
the temporary file
|
|
in our last example doesn't exist before
|
|
we copy to it,
|
|
we could add <CODE
|
|
CLASS="function"
|
|
>Delete</CODE
|
|
> to the beginning
|
|
of the command list:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in",
|
|
[
|
|
Delete("tempfile"),
|
|
Copy("tempfile", "$SOURCE"),
|
|
"modify tempfile",
|
|
Copy("$TARGET", "tempfile"),
|
|
])
|
|
</PRE
|
|
><P
|
|
>
|
|
When then executes as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Delete("tempfile")
|
|
Copy("tempfile", "file.in")
|
|
modify tempfile
|
|
Copy("file.out", "tempfile")
|
|
</PRE
|
|
><P
|
|
>
|
|
Of course, like all of these <CODE
|
|
CLASS="classname"
|
|
>Action</CODE
|
|
> factories,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Delete</CODE
|
|
> factory also expands
|
|
<A
|
|
HREF="#cv-TARGET"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARGET</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-SOURCE"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SOURCE</CODE
|
|
></A
|
|
> variables appropriately.
|
|
For example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in",
|
|
[
|
|
Delete("$TARGET"),
|
|
Copy("$TARGET", "$SOURCE")
|
|
])
|
|
</PRE
|
|
><P
|
|
>
|
|
Executes as:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Delete("file.out")
|
|
Copy("file.out", "file.in")
|
|
</PRE
|
|
><P
|
|
>
|
|
Note, however, that you typically don't need to
|
|
call the <CODE
|
|
CLASS="function"
|
|
>Delete</CODE
|
|
> factory explicitly in this way;
|
|
by default, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> deletes its target(s)
|
|
for you before executing any action.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One word of caution about using the <CODE
|
|
CLASS="function"
|
|
>Delete</CODE
|
|
> factory:
|
|
it has the same variable expansions available
|
|
as any other factory, including the <CODE
|
|
CLASS="envar"
|
|
>$SOURCE</CODE
|
|
> variable.
|
|
Specifying <TT
|
|
CLASS="literal"
|
|
>Delete("$SOURCE")</TT
|
|
>
|
|
is not something you usually want to do!
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2969"
|
|
>14.3. Moving (Renaming) Files or Directories: The <CODE
|
|
CLASS="function"
|
|
>Move</CODE
|
|
> Factory</A
|
|
></H2
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Move</CODE
|
|
> factory
|
|
allows you to rename a file or directory.
|
|
For example, if we don't want to copy the temporary file,
|
|
we could use:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in",
|
|
[
|
|
Copy("tempfile", "$SOURCE"),
|
|
"modify tempfile",
|
|
Move("$TARGET", "tempfile"),
|
|
])
|
|
</PRE
|
|
><P
|
|
>
|
|
Which would execute as:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Copy("tempfile", "file.in")
|
|
modify tempfile
|
|
Move("file.out", "tempfile")
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2978"
|
|
>14.4. Updating the Modification Time of a File: The <CODE
|
|
CLASS="function"
|
|
>Touch</CODE
|
|
> Factory</A
|
|
></H2
|
|
><P
|
|
>
|
|
If you just need to update the
|
|
recorded modification time for a file,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>Touch</CODE
|
|
> factory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in",
|
|
[
|
|
Copy("$TARGET", "$SOURCE"),
|
|
Touch("$TARGET"),
|
|
])
|
|
</PRE
|
|
><P
|
|
>
|
|
Which executes as:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Copy("file.out", "file.in")
|
|
Touch("file.out")
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2987"
|
|
>14.5. Creating a Directory: The <CODE
|
|
CLASS="function"
|
|
>Mkdir</CODE
|
|
> Factory</A
|
|
></H2
|
|
><P
|
|
>
|
|
If you need to create a directory,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>Mkdir</CODE
|
|
> factory.
|
|
For example, if we need to process
|
|
a file in a temporary directory
|
|
in which the processing tool
|
|
will create other files that we don't care about,
|
|
you could use:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in",
|
|
[
|
|
Delete("tempdir"),
|
|
Mkdir("tempdir"),
|
|
Copy("tempdir/${SOURCE.file}", "$SOURCE"),
|
|
"process tempdir",
|
|
Move("$TARGET", "tempdir/output_file"),
|
|
Delete("tempdir"),
|
|
])
|
|
</PRE
|
|
><P
|
|
>
|
|
Which executes as:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Delete("tempdir")
|
|
Mkdir("tempdir")
|
|
Copy("tempdir/file.in", "file.in")
|
|
process tempdir
|
|
Move("file.out", "tempdir/output_file")
|
|
scons: *** [file.out] No such file or directory
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN2996"
|
|
>14.6. Changing File or Directory Permissions: The <CODE
|
|
CLASS="function"
|
|
>Chmod</CODE
|
|
> Factory</A
|
|
></H2
|
|
><P
|
|
>
|
|
To change permissions on a file or directory,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>Chmod</CODE
|
|
> factory.
|
|
The permission argument uses POSIX-style
|
|
permission bits and should typically
|
|
be expressed as an octal,
|
|
not decimal, number:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Command("file.out", "file.in",
|
|
[
|
|
Copy("$TARGET", "$SOURCE"),
|
|
Chmod("$TARGET", 0755),
|
|
])
|
|
</PRE
|
|
><P
|
|
>
|
|
Which executes:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Copy("file.out", "file.in")
|
|
Chmod("file.out", 0755)
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3005"
|
|
>14.7. Executing an action immediately: the <CODE
|
|
CLASS="function"
|
|
>Execute</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
We've been showing you how to use <CODE
|
|
CLASS="classname"
|
|
>Action</CODE
|
|
> factories
|
|
in the <CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> function.
|
|
You can also execute an <CODE
|
|
CLASS="classname"
|
|
>Action</CODE
|
|
> returned by a factory
|
|
(or actually, any <CODE
|
|
CLASS="classname"
|
|
>Action</CODE
|
|
>)
|
|
at the time the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file is read
|
|
by using the <CODE
|
|
CLASS="function"
|
|
>Execute</CODE
|
|
> function.
|
|
For example, if we need to make sure that
|
|
a directory exists before we build any targets,
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Execute(Mkdir('/tmp/my_temp_directory'))
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that this will
|
|
create the directory while
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file is being read:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
Mkdir("/tmp/my_temp_directory")
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
scons: `.' is up to date.
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
If you're familiar with Python,
|
|
you may wonder why you would want to use this
|
|
instead of just calling the native Python
|
|
<CODE
|
|
CLASS="function"
|
|
>os.mkdir()</CODE
|
|
> function.
|
|
The advantage here is that the <CODE
|
|
CLASS="function"
|
|
>Mkdir</CODE
|
|
>
|
|
action will behave appropriately if the user
|
|
specifies the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> <CODE
|
|
CLASS="option"
|
|
>-n</CODE
|
|
> or
|
|
<CODE
|
|
CLASS="option"
|
|
>-q</CODE
|
|
> options--that is,
|
|
it will print the action but not actually
|
|
make the directory when <CODE
|
|
CLASS="option"
|
|
>-n</CODE
|
|
> is specified,
|
|
or make the directory but not print the action
|
|
when <CODE
|
|
CLASS="option"
|
|
>-q</CODE
|
|
> is specified.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Execute</CODE
|
|
> function returns the exit status
|
|
or return value of the underlying action being executed.
|
|
It will also print an error message if the action
|
|
fails and returns a non-zero value.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>, however,
|
|
actually stop the build if the action fails.
|
|
If you want the build to stop
|
|
in response to a failure in an action called by <CODE
|
|
CLASS="function"
|
|
>Execute</CODE
|
|
>,
|
|
you must do so by explicitly
|
|
checking the return value
|
|
and calling the <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> function
|
|
(or a Python equivalent):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> if Execute(Mkdir('/tmp/my_temp_directory')):
|
|
# A problem occurred while making the temp directory.
|
|
Exit(1)
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-file-removal"
|
|
></A
|
|
>Chapter 15. Controlling Removal of Targets</H1
|
|
><P
|
|
>
|
|
There are two occasions when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will,
|
|
by default, remove target files.
|
|
The first is when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> determines that
|
|
an target file needs to be rebuilt
|
|
and removes the existing version of the target
|
|
before executing
|
|
The second is when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is invoked with the
|
|
<TT
|
|
CLASS="literal"
|
|
>-c</TT
|
|
> option to "clean"
|
|
a tree of its built targets.
|
|
|
|
These behaviours can be suppressed with the
|
|
<CODE
|
|
CLASS="function"
|
|
>Precious</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>NoClean</CODE
|
|
> functions, respectively.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3044"
|
|
>15.1. Preventing target removal during build: the <CODE
|
|
CLASS="function"
|
|
>Precious</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
By default, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> removes targets before building them.
|
|
Sometimes, however, this is not what you want.
|
|
For example, you may want to update a library incrementally,
|
|
not by having it deleted and then rebuilt from all
|
|
of the constituent object files.
|
|
In such cases, you can use the
|
|
<CODE
|
|
CLASS="function"
|
|
>Precious</CODE
|
|
> method to prevent
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> from removing the target before it is built:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(RANLIBCOM='')
|
|
lib = env.Library('foo', ['f1.c', 'f2.c', 'f3.c'])
|
|
env.Precious(lib)
|
|
</PRE
|
|
><P
|
|
>
|
|
Although the output doesn't look any different,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not, in fact,
|
|
delete the target library before rebuilding it:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o f1.o -c f1.c
|
|
cc -o f2.o -c f2.c
|
|
cc -o f3.o -c f3.c
|
|
ar rc libfoo.a f1.o f2.o f3.o
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will, however, still delete files marked as <CODE
|
|
CLASS="function"
|
|
>Precious</CODE
|
|
>
|
|
when the <TT
|
|
CLASS="literal"
|
|
>-c</TT
|
|
> option is used.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3060"
|
|
>15.2. Preventing target removal during clean: the <CODE
|
|
CLASS="function"
|
|
>NoClean</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
By default, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> removes all built targets when invoked
|
|
with the <TT
|
|
CLASS="literal"
|
|
>-c</TT
|
|
> option to clean a source tree
|
|
of built targets.
|
|
Sometimes, however, this is not what you want.
|
|
For example, you may want to remove only intermediate generated files
|
|
(such as object files),
|
|
but leave the final targets
|
|
(the libraries)
|
|
untouched.
|
|
|
|
In such cases, you can use the <CODE
|
|
CLASS="function"
|
|
>NoClean</CODE
|
|
> method to prevent <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
from removing a target during a clean:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(RANLIBCOM='')
|
|
lib = env.Library('foo', ['f1.c', 'f2.c', 'f3.c'])
|
|
env.NoClean(lib)
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that the <TT
|
|
CLASS="filename"
|
|
>libfoo.a</TT
|
|
>
|
|
is not listed as a removed file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o f1.o -c f1.c
|
|
cc -o f2.o -c f2.c
|
|
cc -o f3.o -c f3.c
|
|
ar rc libfoo.a f1.o f2.o f3.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -c</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
scons: done reading SConscript files.
|
|
scons: Cleaning targets ...
|
|
Removed f1.o
|
|
Removed f2.o
|
|
Removed f3.o
|
|
scons: done cleaning targets.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3074"
|
|
>15.3. Removing additional files during clean: the <CODE
|
|
CLASS="function"
|
|
>Clean</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
There may be additional files that you want removed
|
|
when the <TT
|
|
CLASS="literal"
|
|
>-c</TT
|
|
> option is used,
|
|
but which <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> doesn't know about
|
|
because they're not normal target files.
|
|
For example, perhaps a command you invoke
|
|
creates a log file as
|
|
part of building the target file you want.
|
|
You would like the log file cleaned,
|
|
but you don't want to have to teach
|
|
SCons that the command
|
|
"builds" two files.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
You can use the <CODE
|
|
CLASS="function"
|
|
>Clean</CODE
|
|
> function to arrange for additional files
|
|
to be removed when the <TT
|
|
CLASS="literal"
|
|
>-c</TT
|
|
> option is used.
|
|
Notice, however, that the <CODE
|
|
CLASS="function"
|
|
>Clean</CODE
|
|
> function takes two arguments,
|
|
and the <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>second</I
|
|
></SPAN
|
|
> argument
|
|
is the name of the additional file you want cleaned
|
|
(<TT
|
|
CLASS="filename"
|
|
>foo.log</TT
|
|
> in this example):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> t = Command('foo.out', 'foo.in', 'build -o $TARGET $SOURCE')
|
|
Clean(t, 'foo.log')
|
|
</PRE
|
|
><P
|
|
>
|
|
The first argument is the target with which you want
|
|
the cleaning of this additional file associated.
|
|
In the above example,
|
|
we've used the return value from the
|
|
<CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> function,
|
|
which represents the
|
|
<TT
|
|
CLASS="filename"
|
|
>foo.out</TT
|
|
>
|
|
target.
|
|
Now whenever the
|
|
<TT
|
|
CLASS="filename"
|
|
>foo.out</TT
|
|
> target is cleaned
|
|
by the <TT
|
|
CLASS="literal"
|
|
>-c</TT
|
|
> option,
|
|
the <TT
|
|
CLASS="filename"
|
|
>foo.log</TT
|
|
> file
|
|
will be removed as well:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
build -o foo.out foo.in
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed foo.out
|
|
Removed foo.log
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-hierarchical"
|
|
></A
|
|
>Chapter 16. Hierarchical Builds</H1
|
|
><P
|
|
>
|
|
The source code for large software projects
|
|
rarely stays in a single directory,
|
|
but is nearly always divided into a
|
|
hierarchy of directories.
|
|
Organizing a large software build using <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
involves creating a hierarchy of build scripts
|
|
using the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3101"
|
|
>16.1. <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
As we've already seen,
|
|
the build script at the top of the tree is called <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
>.
|
|
The top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file can
|
|
use the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function to
|
|
include other subsidiary scripts in the build.
|
|
These subsidiary scripts can, in turn,
|
|
use the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function
|
|
to include still other scripts in the build.
|
|
By convention, these subsidiary scripts are usually
|
|
named <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>.
|
|
For example, a top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file might
|
|
arrange for four subsidiary scripts to be included
|
|
in the build as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript(['drivers/display/SConscript',
|
|
'drivers/mouse/SConscript',
|
|
'parser/SConscript',
|
|
'utilities/SConscript'])
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case, the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
lists all of the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files in the build explicitly.
|
|
(Note, however, that not every directory in the tree
|
|
necessarily has an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file.)
|
|
Alternatively, the <TT
|
|
CLASS="literal"
|
|
>drivers</TT
|
|
>
|
|
subdirectory might contain an intermediate
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file,
|
|
in which case the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> call in
|
|
the top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript(['drivers/SConscript',
|
|
'parser/SConscript',
|
|
'utilities/SConscript'])
|
|
</PRE
|
|
><P
|
|
>
|
|
And the subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file in the
|
|
<TT
|
|
CLASS="literal"
|
|
>drivers</TT
|
|
> subdirectory
|
|
would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript(['display/SConscript',
|
|
'mouse/SConscript'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Whether you list all of the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files in the
|
|
top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file,
|
|
or place a subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file in
|
|
intervening directories,
|
|
or use some mix of the two schemes,
|
|
is up to you and the needs of your software.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3129"
|
|
>16.2. Path Names Are Relative to the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Directory</A
|
|
></H2
|
|
><P
|
|
>
|
|
Subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files make it easy to create a build
|
|
hierarchy because all of the file and directory names
|
|
in a subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files are interpreted
|
|
relative to the directory in which the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file lives.
|
|
Typically, this allows the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file containing the
|
|
instructions to build a target file
|
|
to live in the same directory as the source files
|
|
from which the target will be built,
|
|
making it easy to update how the software is built
|
|
whenever files are added or deleted
|
|
(or other changes are made).
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose we want to build two programs
|
|
<TT
|
|
CLASS="filename"
|
|
>prog1</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>prog2</TT
|
|
> in two separate directories
|
|
with the same names as the programs.
|
|
One typical way to do this would be
|
|
with a top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript(['prog1/SConscript',
|
|
'prog2/SConscript'])
|
|
</PRE
|
|
><P
|
|
>
|
|
And subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files that look like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program('prog1', ['main.c', 'foo1.c', 'foo2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
And this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program('prog2', ['main.c', 'bar1.c', 'bar2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Then, when we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in the top-level directory,
|
|
our build looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o prog1/foo1.o -c prog1/foo1.c
|
|
cc -o prog1/foo2.o -c prog1/foo2.c
|
|
cc -o prog1/main.o -c prog1/main.c
|
|
cc -o prog1/prog1 prog1/main.o prog1/foo1.o prog1/foo2.o
|
|
cc -o prog2/bar1.o -c prog2/bar1.c
|
|
cc -o prog2/bar2.o -c prog2/bar2.c
|
|
cc -o prog2/main.o -c prog2/main.c
|
|
cc -o prog2/prog2 prog2/main.o prog2/bar1.o prog2/bar2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice the following:
|
|
|
|
First, you can have files with the same names
|
|
in multiple directories, like main.c in the above example.
|
|
|
|
Second, unlike standard recursive use of <SPAN
|
|
CLASS="application"
|
|
>Make</SPAN
|
|
>,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> stays in the top-level directory
|
|
(where the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file lives)
|
|
and issues commands that use the path names
|
|
from the top-level directory to the
|
|
target and source files within the hierarchy.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3155"
|
|
>16.3. Top-Level Path Names in Subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
If you need to use a file from another directory,
|
|
it's sometimes more convenient to specify
|
|
the path to a file in another directory
|
|
from the top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> directory,
|
|
even when you're using that file in
|
|
a subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file in a subdirectory.
|
|
You can tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to interpret a path name
|
|
as relative to the top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> directory,
|
|
not the local directory of the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file,
|
|
by appending a <TT
|
|
CLASS="literal"
|
|
>#</TT
|
|
> (hash mark)
|
|
to the beginning of the path name:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program('prog', ['main.c', '#lib/foo1.c', 'foo2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
In this example,
|
|
the <TT
|
|
CLASS="literal"
|
|
>lib</TT
|
|
> directory is
|
|
directly underneath the top-level <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> directory.
|
|
If the above <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file is in a subdirectory
|
|
named <TT
|
|
CLASS="literal"
|
|
>src/prog</TT
|
|
>,
|
|
the output would look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o lib/foo1.o -c lib/foo1.c
|
|
cc -o src/prog/foo2.o -c src/prog/foo2.c
|
|
cc -o src/prog/main.o -c src/prog/main.c
|
|
cc -o src/prog/prog src/prog/main.o lib/foo1.o src/prog/foo2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
(Notice that the <TT
|
|
CLASS="literal"
|
|
>lib/foo1.o</TT
|
|
> object file
|
|
is built in the same directory as its source file.
|
|
See <A
|
|
HREF="#chap-separate"
|
|
>Chapter 17</A
|
|
>, below,
|
|
for information about
|
|
how to build the object file in a different subdirectory.)
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3176"
|
|
>16.4. Absolute Path Names</A
|
|
></H2
|
|
><P
|
|
>
|
|
Of course, you can always specify
|
|
an absolute path name for a file--for example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program('prog', ['main.c', '/usr/joe/lib/foo1.c', 'foo2.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Which, when executed, would yield:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o src/prog/foo2.o -c src/prog/foo2.c
|
|
cc -o src/prog/main.o -c src/prog/main.c
|
|
cc -o /usr/joe/lib/foo1.o -c /usr/joe/lib/foo1.c
|
|
cc -o src/prog/prog src/prog/main.o /usr/joe/lib/foo1.o src/prog/foo2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
(As was the case with top-relative path names,
|
|
notice that the <TT
|
|
CLASS="literal"
|
|
>/usr/joe/lib/foo1.o</TT
|
|
> object file
|
|
is built in the same directory as its source file.
|
|
See <A
|
|
HREF="#chap-separate"
|
|
>Chapter 17</A
|
|
>, below,
|
|
for information about
|
|
how to build the object file in a different subdirectory.)
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3186"
|
|
>16.5. Sharing Environments (and Other Variables) Between <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
In the previous example,
|
|
each of the subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
created its own construction environment
|
|
by calling <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> separately.
|
|
This obviously works fine,
|
|
but if each program must be built
|
|
with the same construction variables,
|
|
it's cumbersome and error-prone to initialize
|
|
separate construction environments
|
|
in the same way over and over in each subsidiary
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports the ability to <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>export</I
|
|
></SPAN
|
|
> variables
|
|
from a parent <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file
|
|
to its subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
which allows you to share common initialized
|
|
values throughout your build hierarchy.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3198"
|
|
>16.5.1. Exporting Variables</A
|
|
></H3
|
|
><P
|
|
>
|
|
There are two ways to export a variable,
|
|
such as a construction environment,
|
|
from an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file,
|
|
so that it may be used by other <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
First, you can call the <CODE
|
|
CLASS="function"
|
|
>Export</CODE
|
|
>
|
|
function with a list of variables,
|
|
or a string of white-space separated variable names.
|
|
Each call to <CODE
|
|
CLASS="function"
|
|
>Export</CODE
|
|
> adds one
|
|
or more variables to a global list
|
|
of variables that are available for import
|
|
by other <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
Export('env')
|
|
</PRE
|
|
><P
|
|
>
|
|
You may export more than one variable name at a time:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
debug = ARGUMENTS['debug']
|
|
Export('env', 'debug')
|
|
</PRE
|
|
><P
|
|
>
|
|
Because white space is not legal in Python variable names,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Export</CODE
|
|
> function will even automatically split
|
|
a string into separate names for you:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Export('env debug')
|
|
</PRE
|
|
><P
|
|
>
|
|
Second, you can specify a list of
|
|
variables to export as a second argument
|
|
to the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function call:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript('src/SConscript', 'env')
|
|
</PRE
|
|
><P
|
|
>
|
|
Or as the <CODE
|
|
CLASS="varname"
|
|
>exports</CODE
|
|
> keyword argument:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript('src/SConscript', exports='env')
|
|
</PRE
|
|
><P
|
|
>
|
|
These calls export the specified variables
|
|
to only the listed <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
You may, however, specify more than one
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file in a list:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript(['src1/SConscript',
|
|
'src2/SConscript'], exports='env')
|
|
</PRE
|
|
><P
|
|
>
|
|
This is functionally equivalent to
|
|
calling the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function
|
|
multiple times with the same <CODE
|
|
CLASS="varname"
|
|
>exports</CODE
|
|
> argument,
|
|
one per <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3226"
|
|
>16.5.2. Importing Variables</A
|
|
></H3
|
|
><P
|
|
>
|
|
Once a variable has been exported from a calling
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file,
|
|
it may be used in other <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
by calling the <CODE
|
|
CLASS="function"
|
|
>Import</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Import('env')
|
|
env.Program('prog', ['prog.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Import</CODE
|
|
> call makes the <TT
|
|
CLASS="literal"
|
|
>env</TT
|
|
> construction
|
|
environment available to the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file,
|
|
after which the variable can be used to build
|
|
programs, libraries, etc.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Like the <CODE
|
|
CLASS="function"
|
|
>Export</CODE
|
|
> function,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Import</CODE
|
|
> function can be used
|
|
with multiple variable names:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Import('env', 'debug')
|
|
env = env.Clone(DEBUG = debug)
|
|
env.Program('prog', ['prog.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
And the <CODE
|
|
CLASS="function"
|
|
>Import</CODE
|
|
> function will similarly
|
|
split a string along white-space
|
|
into separate variable names:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Import('env debug')
|
|
env = env.Clone(DEBUG = debug)
|
|
env.Program('prog', ['prog.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Lastly, as a special case,
|
|
you may import all of the variables that
|
|
have been exported by supplying an asterisk
|
|
to the <CODE
|
|
CLASS="function"
|
|
>Import</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Import('*')
|
|
env = env.Clone(DEBUG = debug)
|
|
env.Program('prog', ['prog.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
If you're dealing with a lot of <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
this can be a lot simpler than keeping
|
|
arbitrary lists of imported variables in each file.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3249"
|
|
>16.5.3. Returning Values From an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> File</A
|
|
></H3
|
|
><P
|
|
>
|
|
Sometimes, you would like to be able to
|
|
use information from a subsidiary
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file in some way.
|
|
For example,
|
|
suppose that you want to create one
|
|
library from source files
|
|
scattered throughout a number
|
|
of subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
You can do this by using the <CODE
|
|
CLASS="function"
|
|
>Return</CODE
|
|
>
|
|
function to return values
|
|
from the subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
to the calling file.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If, for example, we have two subdirectories
|
|
<SPAN
|
|
CLASS="application"
|
|
>foo</SPAN
|
|
> and <SPAN
|
|
CLASS="application"
|
|
>bar</SPAN
|
|
>
|
|
that should each contribute a source
|
|
file to a Library,
|
|
what we'd like to be able to do is
|
|
collect the object files
|
|
from the subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> calls
|
|
like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
Export('env')
|
|
objs = []
|
|
for subdir in ['foo', 'bar']:
|
|
o = SConscript('%s/SConscript' % subdir)
|
|
objs.append(o)
|
|
env.Library('prog', objs)
|
|
</PRE
|
|
><P
|
|
>
|
|
We can do this by using the <CODE
|
|
CLASS="function"
|
|
>Return</CODE
|
|
>
|
|
function in the
|
|
<TT
|
|
CLASS="literal"
|
|
>foo/SConscript</TT
|
|
> file like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Import('env')
|
|
obj = env.Object('foo.c')
|
|
Return('obj')
|
|
</PRE
|
|
><P
|
|
>
|
|
(The corresponding
|
|
<TT
|
|
CLASS="literal"
|
|
>bar/SConscript</TT
|
|
>
|
|
file should be pretty obvious.)
|
|
Then when we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
the object files from the subsidiary subdirectories
|
|
are all correctly archived in the desired library:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o bar/bar.o -c bar/bar.c
|
|
cc -o foo/foo.o -c foo/foo.c
|
|
ar rc libprog.a foo/foo.o bar/bar.o
|
|
ranlib libprog.a
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-separate"
|
|
></A
|
|
>Chapter 17. Separating Source and Build Directories</H1
|
|
><P
|
|
>
|
|
It's often useful to keep any built files completely
|
|
separate from the source files.
|
|
In <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>, this is usually done by creating one or more separate
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>variant directory trees</I
|
|
></SPAN
|
|
>
|
|
that are used to hold the built objects files, libraries,
|
|
and executable programs, etc.
|
|
for a specific flavor, or variant, of build.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides two ways to do this,
|
|
one through the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function that we've already seen,
|
|
and the second through a more flexible <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> function.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
One historical note: the <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> function
|
|
used to be called <CODE
|
|
CLASS="function"
|
|
>BuildDir</CODE
|
|
>.
|
|
That name is still supported
|
|
but has been deprecated
|
|
because the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> functionality
|
|
differs from the model of a "build directory"
|
|
implemented by other build systems like the GNU Autotools.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3283"
|
|
>17.1. Specifying a Variant Directory Tree as Part of an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Call</A
|
|
></H2
|
|
><P
|
|
>
|
|
The most straightforward way to establish a variant directory tree
|
|
uses the fact that the usual way to
|
|
set up a build hierarchy is to have an
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file in the source subdirectory.
|
|
If you then pass a <CODE
|
|
CLASS="varname"
|
|
>variant_dir</CODE
|
|
> argument to the
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function call:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript('src/SConscript', variant_dir='build')
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will then build all of the files in
|
|
the <TT
|
|
CLASS="filename"
|
|
>build</TT
|
|
> subdirectory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>ls src</KBD
|
|
>
|
|
SConscript hello.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o build/hello.o -c build/hello.c
|
|
cc -o build/hello build/hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>ls build</KBD
|
|
>
|
|
SConscript hello hello.c hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
But wait a minute--what's going on here?
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> created the object file
|
|
<TT
|
|
CLASS="filename"
|
|
>build/hello.o</TT
|
|
>
|
|
in the <TT
|
|
CLASS="filename"
|
|
>build</TT
|
|
> subdirectory,
|
|
as expected.
|
|
But even though our <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file lives in the <TT
|
|
CLASS="filename"
|
|
>src</TT
|
|
> subdirectory,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has actually compiled a
|
|
<TT
|
|
CLASS="filename"
|
|
>build/hello.c</TT
|
|
> file
|
|
to create the object file.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
What's happened is that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>duplicated</I
|
|
></SPAN
|
|
>
|
|
the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file from the <TT
|
|
CLASS="filename"
|
|
>src</TT
|
|
> subdirectory
|
|
to the <TT
|
|
CLASS="filename"
|
|
>build</TT
|
|
> subdirectory,
|
|
and built the program from there.
|
|
The next section explains why <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does this.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3313"
|
|
>17.2. Why <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Duplicates Source Files in a Variant Directory Tree</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> duplicates source files in variant directory trees
|
|
because it's the most straightforward way to guarantee a correct build
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>regardless of include-file directory paths,
|
|
relative references between files,
|
|
or tool support for putting files in different locations</I
|
|
></SPAN
|
|
>,
|
|
and the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> philosophy is to, by default,
|
|
guarantee a correct build in all cases.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The most direct reason to duplicate source files
|
|
in variant directories
|
|
is simply that some tools (mostly older vesions)
|
|
are written to only build their output files
|
|
in the same directory as the source files.
|
|
In this case, the choices are either
|
|
to build the output file in the source directory
|
|
and move it to the variant directory,
|
|
or to duplicate the source files in the variant directory.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Additionally,
|
|
relative references between files
|
|
can cause problems if we don't
|
|
just duplicate the hierarchy of source files
|
|
in the variant directory.
|
|
You can see this at work in
|
|
use of the C preprocessor <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
>
|
|
mechanism with double quotes, not angle brackets:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> #include "file.h"
|
|
</PRE
|
|
><P
|
|
>
|
|
The <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>de facto</I
|
|
></SPAN
|
|
> standard behavior
|
|
for most C compilers in this case
|
|
is to first look in the same directory
|
|
as the source file that contains the <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> line,
|
|
then to look in the directories in the preprocessor search path.
|
|
Add to this that the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> implementation of
|
|
support for code repositories
|
|
(described below)
|
|
means not all of the files
|
|
will be found in the same directory hierarchy,
|
|
and the simplest way to make sure
|
|
that the right include file is found
|
|
is to duplicate the source files into the variant directory,
|
|
which provides a correct build
|
|
regardless of the original location(s) of the source files.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Although source-file duplication guarantees a correct build
|
|
even in these end-cases,
|
|
it <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>can</I
|
|
></SPAN
|
|
> usually be safely disabled.
|
|
The next section describes
|
|
how you can disable the duplication of source files
|
|
in the variant directory.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3330"
|
|
>17.3. Telling <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to Not Duplicate Source Files in the Variant Directory Tree</A
|
|
></H2
|
|
><P
|
|
>
|
|
In most cases and with most tool sets,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> can place its target files in a build subdirectory
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>without</I
|
|
></SPAN
|
|
>
|
|
duplicating the source files
|
|
and everything will work just fine.
|
|
You can disable the default <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> behavior
|
|
by specifying <TT
|
|
CLASS="literal"
|
|
>duplicate=0</TT
|
|
>
|
|
when you call the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> SConscript('src/SConscript', variant_dir='build', duplicate=0)
|
|
</PRE
|
|
><P
|
|
>
|
|
When this flag is specified,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses the variant directory
|
|
like most people expect--that is,
|
|
the output files are placed in the variant directory
|
|
while the source files stay in the source directory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>ls src</KBD
|
|
>
|
|
SConscript
|
|
hello.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -c src/hello.c -o build/hello.o
|
|
cc -o build/hello build/hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>ls build</KBD
|
|
>
|
|
hello
|
|
hello.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3346"
|
|
>17.4. The <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Use the <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> function to establish that target
|
|
files should be built in a separate directory
|
|
from the source files:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> VariantDir('build', 'src')
|
|
env = Environment()
|
|
env.Program('build/hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that when you're not using
|
|
an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file in the <TT
|
|
CLASS="filename"
|
|
>src</TT
|
|
> subdirectory,
|
|
you must actually specify that
|
|
the program must be built from
|
|
the <TT
|
|
CLASS="filename"
|
|
>build/hello.c</TT
|
|
>
|
|
file that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will duplicate in the
|
|
<TT
|
|
CLASS="filename"
|
|
>build</TT
|
|
> subdirectory.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
When using the <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> function directly,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> still duplicates the source files
|
|
in the variant directory by default:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>ls src</KBD
|
|
>
|
|
hello.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o build/hello.o -c build/hello.c
|
|
cc -o build/hello build/hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>ls build</KBD
|
|
>
|
|
hello hello.c hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
You can specify the same <TT
|
|
CLASS="literal"
|
|
>duplicate=0</TT
|
|
> argument
|
|
that you can specify for an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> call:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> VariantDir('build', 'src', duplicate=0)
|
|
env = Environment()
|
|
env.Program('build/hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
In which case <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
will disable duplication of the source files:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>ls src</KBD
|
|
>
|
|
hello.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o build/hello.o -c src/hello.c
|
|
cc -o build/hello build/hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>ls build</KBD
|
|
>
|
|
hello hello.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3375"
|
|
>17.5. Using <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> With an <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> File</A
|
|
></H2
|
|
><P
|
|
>
|
|
Even when using the <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
> function,
|
|
it's much more natural to use it with
|
|
a subsidiary <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file.
|
|
For example, if the
|
|
<TT
|
|
CLASS="filename"
|
|
>src/SConscript</TT
|
|
>
|
|
looks like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program('hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then our <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file could look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> VariantDir('build', 'src')
|
|
SConscript('build/SConscript')
|
|
</PRE
|
|
><P
|
|
>
|
|
Yielding the following output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>ls src</KBD
|
|
>
|
|
SConscript hello.c
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o build/hello.o -c build/hello.c
|
|
cc -o build/hello build/hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>ls build</KBD
|
|
>
|
|
SConscript hello hello.c hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that this is completely equivalent
|
|
to the use of <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> that we
|
|
learned about in the previous section.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3394"
|
|
>17.6. Using <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
> with <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
></A
|
|
></H2
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
> file name pattern matching function
|
|
works just as usual when using <CODE
|
|
CLASS="function"
|
|
>VariantDir</CODE
|
|
>.
|
|
For example, if the
|
|
<TT
|
|
CLASS="filename"
|
|
>src/SConscript</TT
|
|
>
|
|
looks like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program('hello', Glob('*.c'))
|
|
</PRE
|
|
><P
|
|
>
|
|
Then with the same <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file as in the previous section,
|
|
and source files <TT
|
|
CLASS="filename"
|
|
>f1.c</TT
|
|
>
|
|
and <TT
|
|
CLASS="filename"
|
|
>f2.c</TT
|
|
> in src,
|
|
we would see the following output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>ls src</KBD
|
|
>
|
|
SConscript f1.c f2.c f2.h
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o build/f1.o -c build/f1.c
|
|
cc -o build/f2.o -c build/f2.c
|
|
cc -o build/hello build/f1.o build/f2.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>ls build</KBD
|
|
>
|
|
SConscript f1.c f1.o f2.c f2.h f2.o hello
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
> function returns Nodes in the
|
|
<TT
|
|
CLASS="filename"
|
|
>build/</TT
|
|
> tree, as you'd expect.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-variants"
|
|
></A
|
|
>Chapter 18. Variant Builds</H1
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="varname"
|
|
>variant_dir</CODE
|
|
> keyword argument of
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> function provides everything
|
|
we need to show how easy it is to create
|
|
variant builds using <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
Suppose, for example, that we want to
|
|
build a program for both Windows and Linux platforms,
|
|
but that we want to build it in a shared directory
|
|
with separate side-by-side build directories
|
|
for the Windows and Linux versions of the program.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> platform = ARGUMENTS.get('OS', Platform())
|
|
|
|
include = "#export/$PLATFORM/include"
|
|
lib = "#export/$PLATFORM/lib"
|
|
bin = "#export/$PLATFORM/bin"
|
|
|
|
env = Environment(PLATFORM = platform,
|
|
BINDIR = bin,
|
|
INCDIR = include,
|
|
LIBDIR = lib,
|
|
CPPPATH = [include],
|
|
LIBPATH = [lib],
|
|
LIBS = 'world')
|
|
|
|
Export('env')
|
|
|
|
env.SConscript('src/SConscript', variant_dir='build/$PLATFORM')
|
|
</PRE
|
|
><P
|
|
>
|
|
This SConstruct file,
|
|
when run on a Linux system, yields:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q OS=linux</KBD
|
|
>
|
|
Install file: "build/linux/world/world.h" as "export/linux/include/world.h"
|
|
cc -o build/linux/hello/hello.o -c -Iexport/linux/include build/linux/hello/hello.c
|
|
cc -o build/linux/world/world.o -c -Iexport/linux/include build/linux/world/world.c
|
|
ar rc build/linux/world/libworld.a build/linux/world/world.o
|
|
ranlib build/linux/world/libworld.a
|
|
Install file: "build/linux/world/libworld.a" as "export/linux/lib/libworld.a"
|
|
cc -o build/linux/hello/hello build/linux/hello/hello.o -Lexport/linux/lib -lworld
|
|
Install file: "build/linux/hello/hello" as "export/linux/bin/hello"
|
|
</PRE
|
|
><P
|
|
>
|
|
The same SConstruct file on Windows would build:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q OS=windows</KBD
|
|
>
|
|
Install file: "build/windows/world/world.h" as "export/windows/include/world.h"
|
|
cl /nologo /Iexport\windows\include /c build\windows\hello\hello.c /Fobuild\windows\hello\hello.obj
|
|
cl /nologo /Iexport\windows\include /c build\windows\world\world.c /Fobuild\windows\world\world.obj
|
|
lib /nologo /OUT:build\windows\world\world.lib build\windows\world\world.obj
|
|
Install file: "build/windows/world/world.lib" as "export/windows/lib/world.lib"
|
|
link /nologo /OUT:build\windows\hello\hello.exe /LIBPATH:export\windows\lib world.lib build\windows\hello\hello.obj
|
|
Install file: "build/windows/hello/hello.exe" as "export/windows/bin/hello.exe"
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-builders-writing"
|
|
></A
|
|
>Chapter 19. Writing Your Own Builders</H1
|
|
><P
|
|
>
|
|
Although <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides many useful methods
|
|
for building common software products:
|
|
programs, libraries, documents.
|
|
you frequently want to be
|
|
able to build some other type of file
|
|
not supported directly by <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
Fortunately, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> makes it very easy
|
|
to define your own <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> objects
|
|
for any custom file types you want to build.
|
|
(In fact, the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> interfaces for creating
|
|
<CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> objects are flexible enough and easy enough to use
|
|
that all of the the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> built-in <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> objects
|
|
are created the mechanisms described in this section.)
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3438"
|
|
>19.1. Writing Builders That Execute External Commands</A
|
|
></H2
|
|
><P
|
|
>
|
|
The simplest <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> to create is
|
|
one that executes an external command.
|
|
For example, if we want to build
|
|
an output file by running the contents
|
|
of the input file through a command named
|
|
<TT
|
|
CLASS="literal"
|
|
>foobuild</TT
|
|
>,
|
|
creating that <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> might look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> bld = Builder(action = 'foobuild < $SOURCE > $TARGET')
|
|
</PRE
|
|
><P
|
|
>
|
|
All the above line does is create a free-standing
|
|
<CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> object.
|
|
The next section will show us how to actually use it.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3447"
|
|
>19.2. Attaching a Builder to a <TT
|
|
CLASS="literal"
|
|
>Construction Environment</TT
|
|
></A
|
|
></H2
|
|
><P
|
|
>
|
|
A <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> object isn't useful
|
|
until it's attached to a <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
so that we can call it to arrange
|
|
for files to be built.
|
|
This is done through the <A
|
|
HREF="#cv-BUILDERS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
></A
|
|
>
|
|
<TT
|
|
CLASS="literal"
|
|
>construction variable</TT
|
|
> in an environment.
|
|
The <CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
> variable is a Python dictionary
|
|
that maps the names by which you want to call
|
|
various <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> objects to the objects themselves.
|
|
For example, if we want to call the
|
|
<CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> we just defined by the name
|
|
<CODE
|
|
CLASS="function"
|
|
>Foo</CODE
|
|
>,
|
|
our <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file might look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> bld = Builder(action = 'foobuild < $SOURCE > $TARGET')
|
|
env = Environment(BUILDERS = {'Foo' : bld})
|
|
</PRE
|
|
><P
|
|
>
|
|
With the <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> so attached to our <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
we can now actually call it like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Foo('file.foo', 'file.input')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then when we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> it looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
foobuild < file.input > file.foo
|
|
</PRE
|
|
><P
|
|
>
|
|
Note, however, that the default <CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
>
|
|
variable in a <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
comes with a default set of <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> objects
|
|
already defined:
|
|
<A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#b-Library"
|
|
><CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
></A
|
|
>, etc.
|
|
And when we explicitly set the <CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
> variable
|
|
when we create the <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>,
|
|
the default <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>s are no longer part of
|
|
the environment:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> bld = Builder(action = 'foobuild < $SOURCE > $TARGET')
|
|
env = Environment(BUILDERS = {'Foo' : bld})
|
|
env.Foo('file.foo', 'file.input')
|
|
env.Program('hello.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
AttributeError: SConsEnvironment instance has no attribute 'Program':
|
|
File "/home/my/project/SConstruct", line 4:
|
|
env.Program('hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
To be able to use both our own defined <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> objects
|
|
and the default <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> objects in the same <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>,
|
|
you can either add to the <CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
> variable
|
|
using the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
bld = Builder(action = 'foobuild < $SOURCE > $TARGET')
|
|
env.Append(BUILDERS = {'Foo' : bld})
|
|
env.Foo('file.foo', 'file.input')
|
|
env.Program('hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Or you can explicitly set the appropriately-named
|
|
key in the <CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
> dictionary:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
bld = Builder(action = 'foobuild < $SOURCE > $TARGET')
|
|
env['BUILDERS']['Foo'] = bld
|
|
env.Foo('file.foo', 'file.input')
|
|
env.Program('hello.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Either way, the same <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
can then use both the newly-defined
|
|
<CODE
|
|
CLASS="function"
|
|
>Foo</CODE
|
|
> <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>
|
|
and the default <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
> <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
foobuild < file.input > file.foo
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3503"
|
|
>19.3. Letting <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Handle The File Suffixes</A
|
|
></H2
|
|
><P
|
|
>
|
|
By supplying additional information
|
|
when you create a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>,
|
|
you can let <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> add appropriate file
|
|
suffixes to the target and/or the source file.
|
|
For example, rather than having to specify
|
|
explicitly that you want the <TT
|
|
CLASS="literal"
|
|
>Foo</TT
|
|
>
|
|
<CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> to build the <TT
|
|
CLASS="literal"
|
|
>file.foo</TT
|
|
>
|
|
target file from the <TT
|
|
CLASS="literal"
|
|
>file.input</TT
|
|
> source file,
|
|
you can give the <TT
|
|
CLASS="literal"
|
|
>.foo</TT
|
|
>
|
|
and <TT
|
|
CLASS="literal"
|
|
>.input</TT
|
|
> suffixes to the <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>,
|
|
making for more compact and readable calls to
|
|
the <TT
|
|
CLASS="literal"
|
|
>Foo</TT
|
|
> <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> bld = Builder(action = 'foobuild < $SOURCE > $TARGET',
|
|
suffix = '.foo',
|
|
src_suffix = '.input')
|
|
env = Environment(BUILDERS = {'Foo' : bld})
|
|
env.Foo('file1')
|
|
env.Foo('file2')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
foobuild < file1.input > file1.foo
|
|
foobuild < file2.input > file2.foo
|
|
</PRE
|
|
><P
|
|
>
|
|
You can also supply a <TT
|
|
CLASS="literal"
|
|
>prefix</TT
|
|
> keyword argument
|
|
if it's appropriate to have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> append a prefix
|
|
to the beginning of target file names.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3524"
|
|
>19.4. Builders That Execute Python Functions</A
|
|
></H2
|
|
><P
|
|
>
|
|
In <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>, you don't have to call an external command
|
|
to build a file.
|
|
You can, instead, define a Python function
|
|
that a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> object can invoke
|
|
to build your target file (or files).
|
|
Such a <TT
|
|
CLASS="literal"
|
|
>builder function</TT
|
|
> definition looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def build_function(target, source, env):
|
|
# Code to build "target" from "source"
|
|
return None
|
|
</PRE
|
|
><P
|
|
>
|
|
The arguments of a <TT
|
|
CLASS="literal"
|
|
>builder function</TT
|
|
> are:
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
>target</DT
|
|
><DD
|
|
><P
|
|
>
|
|
A list of Node objects representing
|
|
the target or targets to be
|
|
built by this builder function.
|
|
The file names of these target(s)
|
|
may be extracted using the Python <CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
> function.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>source</DT
|
|
><DD
|
|
><P
|
|
>
|
|
A list of Node objects representing
|
|
the sources to be
|
|
used by this builder function to build the targets.
|
|
The file names of these source(s)
|
|
may be extracted using the Python <CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
> function.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>env</DT
|
|
><DD
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
> used for building the target(s).
|
|
The builder function may use any of the
|
|
environment's construction variables
|
|
in any way to affect how it builds the targets.
|
|
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
><P
|
|
>
|
|
The builder function must
|
|
return a <TT
|
|
CLASS="literal"
|
|
>0</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>None</TT
|
|
> value
|
|
if the target(s) are built successfully.
|
|
The builder function
|
|
may raise an exception
|
|
or return any non-zero value
|
|
to indicate that the build is unsuccessful,
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Once you've defined the Python function
|
|
that will build your target file,
|
|
defining a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> object for it is as
|
|
simple as specifying the name of the function,
|
|
instead of an external command,
|
|
as the <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>'s
|
|
<TT
|
|
CLASS="literal"
|
|
>action</TT
|
|
>
|
|
argument:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def build_function(target, source, env):
|
|
# Code to build "target" from "source"
|
|
return None
|
|
bld = Builder(action = build_function,
|
|
suffix = '.foo',
|
|
src_suffix = '.input')
|
|
env = Environment(BUILDERS = {'Foo' : bld})
|
|
env.Foo('file')
|
|
</PRE
|
|
><P
|
|
>
|
|
And notice that the output changes slightly,
|
|
reflecting the fact that a Python function,
|
|
not an external command,
|
|
is now called to build the target file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
build_function(["file.foo"], ["file.input"])
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3560"
|
|
>19.5. Builders That Create Actions Using a <TT
|
|
CLASS="literal"
|
|
>Generator</TT
|
|
></A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Builder objects can create an action "on the fly"
|
|
by using a function called a <TT
|
|
CLASS="literal"
|
|
>generator</TT
|
|
>.
|
|
This provides a great deal of flexibility to
|
|
construct just the right list of commands
|
|
to build your target.
|
|
A <TT
|
|
CLASS="literal"
|
|
>generator</TT
|
|
> looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def generate_actions(source, target, env, for_signature):
|
|
return 'foobuild < %s > %s' % (target[0], source[0])
|
|
</PRE
|
|
><P
|
|
>
|
|
The arguments of a <TT
|
|
CLASS="literal"
|
|
>generator</TT
|
|
> are:
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
>source</DT
|
|
><DD
|
|
><P
|
|
>
|
|
A list of Node objects representing
|
|
the sources to be built
|
|
by the command or other action
|
|
generated by this function.
|
|
The file names of these source(s)
|
|
may be extracted using the Python <CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
> function.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>target</DT
|
|
><DD
|
|
><P
|
|
>
|
|
A list of Node objects representing
|
|
the target or targets to be built
|
|
by the command or other action
|
|
generated by this function.
|
|
The file names of these target(s)
|
|
may be extracted using the Python <CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
> function.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>env</DT
|
|
><DD
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
> used for building the target(s).
|
|
The generator may use any of the
|
|
environment's construction variables
|
|
in any way to determine what command
|
|
or other action to return.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>for_signature</DT
|
|
><DD
|
|
><P
|
|
>
|
|
A flag that specifies whether the
|
|
generator is being called to contribute to a build signature,
|
|
as opposed to actually executing the command.
|
|
|
|
|
|
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>generator</TT
|
|
> must return a
|
|
command string or other action that will be used to
|
|
build the specified target(s) from the specified source(s).
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Once you've defined a <TT
|
|
CLASS="literal"
|
|
>generator</TT
|
|
>,
|
|
you create a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> to use it
|
|
by specifying the generator keyword argument
|
|
instead of <TT
|
|
CLASS="literal"
|
|
>action</TT
|
|
>.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def generate_actions(source, target, env, for_signature):
|
|
return 'foobuild < %s > %s' % (source[0], target[0])
|
|
bld = Builder(generator = generate_actions,
|
|
suffix = '.foo',
|
|
src_suffix = '.input')
|
|
env = Environment(BUILDERS = {'Foo' : bld})
|
|
env.Foo('file')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
foobuild < file.input > file.foo
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that it's illegal to specify both an
|
|
<TT
|
|
CLASS="literal"
|
|
>action</TT
|
|
>
|
|
and a
|
|
<TT
|
|
CLASS="literal"
|
|
>generator</TT
|
|
>
|
|
for a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3603"
|
|
>19.6. Builders That Modify the Target or Source Lists Using an <TT
|
|
CLASS="literal"
|
|
>Emitter</TT
|
|
></A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports the ability for a Builder to modify the
|
|
lists of target(s) from the specified source(s).
|
|
You do this by defining an <TT
|
|
CLASS="literal"
|
|
>emitter</TT
|
|
> function
|
|
that takes as its arguments
|
|
the list of the targets passed to the builder,
|
|
the list of the sources passed to the builder,
|
|
and the construction environment.
|
|
The emitter function should return the modified
|
|
lists of targets that should be built
|
|
and sources from which the targets will be built.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, suppose you want to define a Builder
|
|
that always calls a <TT
|
|
CLASS="filename"
|
|
>foobuild</TT
|
|
> program,
|
|
and you want to automatically add
|
|
a new target file named
|
|
<TT
|
|
CLASS="filename"
|
|
>new_target</TT
|
|
>
|
|
and a new source file named
|
|
<TT
|
|
CLASS="filename"
|
|
>new_source</TT
|
|
>
|
|
whenever it's called.
|
|
The <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file might look like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def modify_targets(target, source, env):
|
|
target.append('new_target')
|
|
source.append('new_source')
|
|
return target, source
|
|
bld = Builder(action = 'foobuild $TARGETS - $SOURCES',
|
|
suffix = '.foo',
|
|
src_suffix = '.input',
|
|
emitter = modify_targets)
|
|
env = Environment(BUILDERS = {'Foo' : bld})
|
|
env.Foo('file')
|
|
</PRE
|
|
><P
|
|
>
|
|
And would yield the following output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
foobuild file.foo new_target - file.input new_source
|
|
</PRE
|
|
><P
|
|
>
|
|
One very flexible thing that you can is specify
|
|
use a construction variable to specify
|
|
different emitter functions for different
|
|
construction variable.
|
|
To do this, specify a string
|
|
containing a construction variable
|
|
expansion as the emitter when you call
|
|
the <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> function,
|
|
and set that construction variable to
|
|
the desired emitter function
|
|
in different construction environments:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> bld = Builder(action = 'my_command $SOURCES > $TARGET',
|
|
suffix = '.foo',
|
|
src_suffix = '.input',
|
|
emitter = '$MY_EMITTER')
|
|
def modify1(target, source, env):
|
|
return target, source + ['modify1.in']
|
|
def modify2(target, source, env):
|
|
return target, source + ['modify2.in']
|
|
env1 = Environment(BUILDERS = {'Foo' : bld},
|
|
MY_EMITTER = modify1)
|
|
env2 = Environment(BUILDERS = {'Foo' : bld},
|
|
MY_EMITTER = modify2)
|
|
env1.Foo('file1')
|
|
env2.Foo('file2')
|
|
import os
|
|
env1['ENV']['PATH'] = env2['ENV']['PATH'] + os.pathsep + os.getcwd()
|
|
env2['ENV']['PATH'] = env2['ENV']['PATH'] + os.pathsep + os.getcwd()
|
|
|
|
|
|
</PRE
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> bld = Builder(action = 'my_command $SOURCES > $TARGET',
|
|
suffix = '.foo',
|
|
src_suffix = '.input',
|
|
emitter = '$MY_EMITTER')
|
|
def modify1(target, source, env):
|
|
return target, source + ['modify1.in']
|
|
def modify2(target, source, env):
|
|
return target, source + ['modify2.in']
|
|
env1 = Environment(BUILDERS = {'Foo' : bld},
|
|
MY_EMITTER = modify1)
|
|
env2 = Environment(BUILDERS = {'Foo' : bld},
|
|
MY_EMITTER = modify2)
|
|
env1.Foo('file1')
|
|
env2.Foo('file2')
|
|
|
|
</PRE
|
|
><P
|
|
>
|
|
In this example, the <TT
|
|
CLASS="filename"
|
|
>modify1.in</TT
|
|
>
|
|
and <TT
|
|
CLASS="filename"
|
|
>modify2.in</TT
|
|
> files
|
|
get added to the source lists
|
|
of the different commands:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
my_command file1.input modify1.in > file1.foo
|
|
my_command file2.input modify2.in > file2.foo
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3627"
|
|
>19.7. Where To Put Your Custom Builders and Tools</A
|
|
></H2
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="filename"
|
|
>site_scons</TT
|
|
> directory gives you a place to
|
|
put Python modules you can import into your SConscripts
|
|
(site_scons), add-on tools that can integrate into <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
(site_scons/site_tools), and a site_scons/site_init.py file that
|
|
gets read before any <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> or <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>, allowing you to
|
|
change <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>'s default behavior.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you get a tool from somewhere (the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> wiki or a third party,
|
|
for instance) and you'd like to use it in your project, the
|
|
<TT
|
|
CLASS="filename"
|
|
>site_scons</TT
|
|
> dir is the simplest place to put it.
|
|
Tools come in two flavors; either a Python function that operates on
|
|
an <CODE
|
|
CLASS="function"
|
|
>Environment</CODE
|
|
> or a Python file containing two functions, exists()
|
|
and generate().
|
|
|
|
</P
|
|
><P
|
|
>
|
|
A single-function Tool can just be included in your
|
|
<TT
|
|
CLASS="filename"
|
|
>site_scons/site_init.py</TT
|
|
> file where it will be
|
|
parsed and made available for use. For instance, you could have a
|
|
<TT
|
|
CLASS="filename"
|
|
>site_scons/site_init.py</TT
|
|
> file like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def TOOL_ADD_HEADER(env):
|
|
"""A Tool to add a header from $HEADER to the source file"""
|
|
add_header = Builder(action=['echo "$HEADER" > $TARGET',
|
|
'cat $SOURCE >> $TARGET'])
|
|
env.Append(BUILDERS = {'AddHeader' : add_header})
|
|
env['HEADER'] = '' # set default value
|
|
</PRE
|
|
><P
|
|
>
|
|
and a <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Use TOOL_ADD_HEADER from site_scons/site_init.py
|
|
env=Environment(tools=['default', TOOL_ADD_HEADER], HEADER="=====")
|
|
env.AddHeader('tgt', 'src')
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>TOOL_ADD_HEADER</CODE
|
|
> tool method will be
|
|
called to add the <CODE
|
|
CLASS="function"
|
|
>AddHeader</CODE
|
|
> tool to the
|
|
environment.
|
|
|
|
</P
|
|
><P
|
|
> Similarly, a more full-fledged tool with
|
|
<CODE
|
|
CLASS="function"
|
|
>exists()</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>generate()</CODE
|
|
>
|
|
methods can be installed in
|
|
<TT
|
|
CLASS="filename"
|
|
>site_scons/site_tools/toolname.py</TT
|
|
>. Since
|
|
<TT
|
|
CLASS="filename"
|
|
>site_scons/site_tools</TT
|
|
> is automatically added
|
|
to the head of the tool search path, any tool found there will be
|
|
available to all environments. Furthermore, a tool found there
|
|
will override a built-in tool of the same name, so if you need to
|
|
change the behavior of a built-in tool, site_scons gives you the
|
|
hook you need.
|
|
</P
|
|
><P
|
|
> Many people have a library of utility Python functions they'd like
|
|
to include in <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>s; just put that module in
|
|
<TT
|
|
CLASS="filename"
|
|
>site_scons/my_utils.py</TT
|
|
> or any valid Python module name of your
|
|
choice. For instance you can do something like this in
|
|
<TT
|
|
CLASS="filename"
|
|
>site_scons/my_utils.py</TT
|
|
> to add a build_id method:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def build_id():
|
|
"""Return a build ID (stub version)"""
|
|
return "100"
|
|
</PRE
|
|
><P
|
|
>
|
|
And then in your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> or any sub-<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> anywhere in
|
|
your build, you can import <TT
|
|
CLASS="filename"
|
|
>my_utils</TT
|
|
> and use it:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import my_utils
|
|
print "build_id=" + my_utils.build_id()
|
|
</PRE
|
|
><P
|
|
>
|
|
If you have a machine-wide site dir you'd like to use instead of
|
|
<TT
|
|
CLASS="filename"
|
|
>./site_scons</TT
|
|
>, use the
|
|
<TT
|
|
CLASS="literal"
|
|
>--site-dir</TT
|
|
> option to point to your dir.
|
|
<TT
|
|
CLASS="filename"
|
|
>site_init.py</TT
|
|
> and
|
|
<TT
|
|
CLASS="filename"
|
|
>site_tools</TT
|
|
> will be located under that dir.
|
|
To avoid using a <TT
|
|
CLASS="filename"
|
|
>site_scons</TT
|
|
> dir at all, even
|
|
if it exists, use the <TT
|
|
CLASS="literal"
|
|
>--no-site-dir</TT
|
|
> option.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-builders-commands"
|
|
></A
|
|
>Chapter 20. Not Writing a Builder: the <CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> Builder</H1
|
|
><P
|
|
>
|
|
Creating a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> and attaching it to a <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
allows for a lot of flexibility when you
|
|
want to re-use actions
|
|
to build multiple files of the same type.
|
|
This can, however, be cumbersome
|
|
if you only need to execute one specific command
|
|
to build a single file (or group of files).
|
|
For these situations, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a
|
|
<CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> that arranges
|
|
for a specific action to be executed
|
|
to build a specific file or files.
|
|
This looks a lot like the other builders
|
|
(like <A
|
|
HREF="#b-Program"
|
|
><CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#b-Object"
|
|
><CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
></A
|
|
>, etc.),
|
|
but takes as an additional argument
|
|
the command to be executed to build the file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Command('foo.out', 'foo.in', "sed 's/x/y/' < $SOURCE > $TARGET")
|
|
</PRE
|
|
><P
|
|
>
|
|
When executed,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> runs the specified command,
|
|
substituting <A
|
|
HREF="#cv-SOURCE"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SOURCE</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-TARGET"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARGET</CODE
|
|
></A
|
|
>
|
|
as expected:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
sed 's/x/y/' < foo.in > foo.out
|
|
</PRE
|
|
><P
|
|
>
|
|
This is often more convenient than
|
|
creating a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> object
|
|
and adding it to the <A
|
|
HREF="#cv-BUILDERS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
></A
|
|
> variable
|
|
of a <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
>
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that the action you specify to the
|
|
<CODE
|
|
CLASS="function"
|
|
>Command</CODE
|
|
> <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> can be any legal <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> <CODE
|
|
CLASS="classname"
|
|
>Action</CODE
|
|
>,
|
|
such as a Python function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
def build(target, source, env):
|
|
# Whatever it takes to build
|
|
return None
|
|
env.Command('foo.out', 'foo.in', build)
|
|
</PRE
|
|
><P
|
|
>
|
|
Which executes as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
build(["foo.out"], ["foo.in"])
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-add-method"
|
|
></A
|
|
>Chapter 21. Pseudo-Builders: the AddMethod function</H1
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>AddMethod</CODE
|
|
> function is used to add a method
|
|
to an environment. It's typically used to add a "pseudo-builder,"
|
|
a function that looks like a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> but
|
|
wraps up calls to multiple other <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>s
|
|
or otherwise processes its arguments
|
|
before calling one or more <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>s.
|
|
In the following example,
|
|
we want to install the program into the standard
|
|
<TT
|
|
CLASS="filename"
|
|
>/usr/bin</TT
|
|
> directory hierarchy,
|
|
but also copy it into a local <TT
|
|
CLASS="filename"
|
|
>install/bin</TT
|
|
>
|
|
directory from which a package might be built:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def install_in_bin_dirs(env, source):
|
|
"""Install source in both bin dirs"""
|
|
i1 = env.Install("$BIN", source)
|
|
i2 = env.Install("$LOCALBIN", source)
|
|
return [i1[0], i2[0]] # Return a list, like a normal builder
|
|
env = Environment(BIN='/usr/bin', LOCALBIN='#install/bin')
|
|
env.AddMethod(install_in_bin_dirs, "InstallInBinDirs")
|
|
env.InstallInBinDirs(Program('hello.c')) # installs hello in both bin dirs
|
|
</PRE
|
|
><P
|
|
> This produces the following:
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q /</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
Install file: "hello" as "/usr/bin/hello"
|
|
Install file: "hello" as "install/bin/hello"
|
|
</PRE
|
|
><P
|
|
>
|
|
As mentioned, a psuedo-builder also provides more flexibility
|
|
in parsing arguments than you can get with a <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>.
|
|
The next example shows a pseudo-builder with a
|
|
named argument that modifies the filename, and a separate argument
|
|
for the resource file (rather than having the builder figure it out
|
|
by file extension). This example also demonstrates using the global
|
|
<CODE
|
|
CLASS="function"
|
|
>AddMethod</CODE
|
|
> function to add a method to the global Environment class,
|
|
so it will be used in all subsequently created environments.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def BuildTestProg(env, testfile, resourcefile, testdir="tests"):
|
|
"""Build the test program;
|
|
prepends "test_" to src and target,
|
|
and puts target into testdir."""
|
|
srcfile = "test_%s.c" % testfile
|
|
target = "%s/test_%s" % (testdir, testfile)
|
|
if env['PLATFORM'] == 'win32':
|
|
resfile = env.RES(resourcefile)
|
|
p = env.Program(target, [srcfile, resfile])
|
|
else:
|
|
p = env.Program(target, srcfile)
|
|
return p
|
|
AddMethod(Environment, BuildTestProg)
|
|
|
|
env = Environment()
|
|
env.BuildTestProg('stuff', resourcefile='res.rc')
|
|
</PRE
|
|
><P
|
|
> This produces the following on Linux:
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o test_stuff.o -c test_stuff.c
|
|
cc -o tests/test_stuff test_stuff.o
|
|
</PRE
|
|
><P
|
|
> And the following on Windows:
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
rc /fores.res res.rc
|
|
cl /nologo /c test_stuff.c /Fotest_stuff.obj
|
|
link /nologo /OUT:tests\test_stuff.exe test_stuff.obj res.res
|
|
</PRE
|
|
><P
|
|
> Using <CODE
|
|
CLASS="function"
|
|
>AddMethod</CODE
|
|
> is better than just adding an instance method
|
|
to a <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
> because it gets called as a proper method,
|
|
and because <CODE
|
|
CLASS="function"
|
|
>AddMethod</CODE
|
|
> provides for copying the method
|
|
to any clones of the <TT
|
|
CLASS="literal"
|
|
>construction environment</TT
|
|
> instance.
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-scanners"
|
|
></A
|
|
>Chapter 22. Writing Scanners</H1
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has built-in scanners that know how to look in
|
|
C, Fortran and IDL source files for information about
|
|
other files that targets built from those files depend on--for example,
|
|
in the case of files that use the C preprocessor,
|
|
the <TT
|
|
CLASS="filename"
|
|
>.h</TT
|
|
> files that are specified
|
|
using <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> lines in the source.
|
|
You can use the same mechanisms that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses to create
|
|
its built-in scanners to write scanners of your own for file types
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not know how to scan "out of the box."
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3743"
|
|
>22.1. A Simple Scanner Example</A
|
|
></H2
|
|
><P
|
|
>
|
|
Suppose, for example, that we want to create a simple scanner
|
|
for <TT
|
|
CLASS="filename"
|
|
>.foo</TT
|
|
> files.
|
|
A <TT
|
|
CLASS="filename"
|
|
>.foo</TT
|
|
> file contains some text that
|
|
will be processed,
|
|
and can include other files on lines that begin
|
|
with <TT
|
|
CLASS="literal"
|
|
>include</TT
|
|
>
|
|
followed by a file name:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> include filename.foo
|
|
</PRE
|
|
><P
|
|
>
|
|
Scanning a file will be handled by a Python function
|
|
that you must supply.
|
|
Here is a function that will use the Python
|
|
<TT
|
|
CLASS="filename"
|
|
>re</TT
|
|
> module
|
|
to scan for the <TT
|
|
CLASS="literal"
|
|
>include</TT
|
|
> lines in our example:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import re
|
|
|
|
include_re = re.compile(r'^include\s+(\S+)$', re.M)
|
|
|
|
def kfile_scan(node, env, path, arg):
|
|
contents = node.get_contents()
|
|
return include_re.findall(contents)
|
|
</PRE
|
|
><P
|
|
>
|
|
The scanner function must
|
|
accept the four specified arguments
|
|
and return a list of implicit dependencies.
|
|
Presumably, these would be dependencies found
|
|
from examining the contents of the file,
|
|
although the function can perform any
|
|
manipulation at all to generate the list of
|
|
dependencies.
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
>node</DT
|
|
><DD
|
|
><P
|
|
>
|
|
An <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> node object representing the file being scanned.
|
|
The path name to the file can be
|
|
used by converting the node to a string
|
|
using the <TT
|
|
CLASS="literal"
|
|
>str()</TT
|
|
> function,
|
|
or an internal <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> <TT
|
|
CLASS="literal"
|
|
>get_contents()</TT
|
|
>
|
|
object method can be used to fetch the contents.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>env</DT
|
|
><DD
|
|
><P
|
|
>
|
|
The construction environment in effect for this scan.
|
|
The scanner function may choose to use construction
|
|
variables from this environment to affect its behavior.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>path</DT
|
|
><DD
|
|
><P
|
|
>
|
|
A list of directories that form the search path for included files
|
|
for this scanner.
|
|
This is how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> handles the <A
|
|
HREF="#cv-CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
>
|
|
variables.
|
|
|
|
</P
|
|
></DD
|
|
><DT
|
|
>arg</DT
|
|
><DD
|
|
><P
|
|
>
|
|
An optional argument that you can choose to
|
|
have passed to this scanner function by
|
|
various scanner instances.
|
|
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
><P
|
|
>
|
|
A Scanner object is created using the <CODE
|
|
CLASS="classname"
|
|
>Scanner</CODE
|
|
> function,
|
|
which typically takes an <TT
|
|
CLASS="literal"
|
|
>skeys</TT
|
|
> argument
|
|
to associate the type of file suffix with this scanner.
|
|
The Scanner object must then be associated with the
|
|
<A
|
|
HREF="#cv-SCANNERS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SCANNERS</CODE
|
|
></A
|
|
> construction variable of a construction environment,
|
|
typically by using the <CODE
|
|
CLASS="function"
|
|
>Append</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> kscan = Scanner(function = kfile_scan,
|
|
skeys = ['.k'])
|
|
env.Append(SCANNERS = kscan)
|
|
</PRE
|
|
><P
|
|
>
|
|
When we put it all together, it looks like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import re
|
|
|
|
include_re = re.compile(r'^include\s+(\S+)$', re.M)
|
|
|
|
def kfile_scan(node, env, path):
|
|
contents = node.get_contents()
|
|
includes = include_re.findall(contents)
|
|
return includes
|
|
|
|
kscan = Scanner(function = kfile_scan,
|
|
skeys = ['.k'])
|
|
|
|
env = Environment(ENV = {'PATH' : '/usr/local/bin'})
|
|
env.Append(SCANNERS = kscan)
|
|
|
|
env.Command('foo', 'foo.k', 'kprocess < $SOURCES > $TARGET')
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-repositories"
|
|
></A
|
|
>Chapter 23. Building From Code Repositories</H1
|
|
><P
|
|
>
|
|
Often, a software project will have
|
|
one or more central repositories,
|
|
directory trees that contain
|
|
source code, or derived files, or both.
|
|
You can eliminate additional unnecessary
|
|
rebuilds of files by having <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
use files from one or more code repositories
|
|
to build files in your local build tree.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3794"
|
|
>23.1. The <CODE
|
|
CLASS="function"
|
|
>Repository</CODE
|
|
> Method</A
|
|
></H2
|
|
><P
|
|
>
|
|
It's often useful to allow multiple programmers working
|
|
on a project to build software from
|
|
source files and/or derived files that
|
|
are stored in a centrally-accessible repository,
|
|
a directory copy of the source code tree.
|
|
(Note that this is not the sort of repository
|
|
maintained by a source code management system
|
|
like BitKeeper, CVS, or Subversion.)
|
|
|
|
You use the <CODE
|
|
CLASS="function"
|
|
>Repository</CODE
|
|
> method
|
|
to tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to search one or more
|
|
central code repositories (in order)
|
|
for any source files and derived files
|
|
that are not present in the local build tree:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Program('hello.c')
|
|
Repository('/usr/repository1', '/usr/repository2')
|
|
</PRE
|
|
><P
|
|
>
|
|
Multiple calls to the <CODE
|
|
CLASS="function"
|
|
>Repository</CODE
|
|
> method
|
|
will simply add repositories to the global list
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> maintains,
|
|
with the exception that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will automatically eliminate
|
|
the current directory and any non-existent
|
|
directories from the list.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3805"
|
|
>23.2. Finding source files in repositories</A
|
|
></H2
|
|
><P
|
|
>
|
|
The above example
|
|
specifies that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
will first search for files under
|
|
the <TT
|
|
CLASS="filename"
|
|
>/usr/repository1</TT
|
|
> tree
|
|
and next under the <TT
|
|
CLASS="filename"
|
|
>/usr/repository2</TT
|
|
> tree.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> expects that any files it searches
|
|
for will be found in the same position
|
|
relative to the top-level directory.
|
|
In the above example, if the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file is not
|
|
found in the local build tree,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will search first for
|
|
a <TT
|
|
CLASS="filename"
|
|
>/usr/repository1/hello.c</TT
|
|
> file
|
|
and then for a <TT
|
|
CLASS="filename"
|
|
>/usr/repository2/hello.c</TT
|
|
> file
|
|
to use in its place.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
So given the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file above,
|
|
if the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file exists in the local
|
|
build directory,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will rebuild the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program
|
|
as normal:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
If, however, there is no local <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file,
|
|
but one exists in <TT
|
|
CLASS="filename"
|
|
>/usr/repository1</TT
|
|
>,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will recompile the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program
|
|
from the source file it finds in the repository:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c /usr/repository1/hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
And similarly, if there is no local <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file
|
|
and no <TT
|
|
CLASS="filename"
|
|
>/usr/repository1/hello.c</TT
|
|
>,
|
|
but one exists in <TT
|
|
CLASS="filename"
|
|
>/usr/repository2</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c /usr/repository2/hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3837"
|
|
>23.3. Finding <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files in repositories</A
|
|
></H2
|
|
><P
|
|
>
|
|
We've already seen that SCons will scan the contents of
|
|
a source file for <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> file names
|
|
and realize that targets built from that source file
|
|
also depend on the <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> file(s).
|
|
For each directory in the <A
|
|
HREF="#cv-CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
></A
|
|
> list,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will actually search the corresponding directories
|
|
in any repository trees and establish the
|
|
correct dependencies on any
|
|
<TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files that it finds
|
|
in repository directory.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Unless the C compiler also knows about these directories
|
|
in the repository trees, though,
|
|
it will be unable to find the <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files.
|
|
If, for example, the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file in
|
|
our previous example includes the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
>.h;
|
|
in its current directory,
|
|
and the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
>.h; only exists in the repository:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
hello.c:1: hello.h: No such file or directory
|
|
</PRE
|
|
><P
|
|
>
|
|
In order to inform the C compiler about the repositories,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will add appropriate
|
|
<TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
> flags to the compilation commands
|
|
for each directory in the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> list.
|
|
So if we add the current directory to the
|
|
construction environment <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CPPPATH = ['.'])
|
|
env.Program('hello.c')
|
|
Repository('/usr/repository1')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then re-executing <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> yields:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c -I. -I/usr/repository1 hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
The order of the <TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
> options replicates,
|
|
for the C preprocessor,
|
|
the same repository-directory search path
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses for its own dependency analysis.
|
|
If there are multiple repositories and multiple <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
>
|
|
directories, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will add the repository directories
|
|
to the beginning of each <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> directory,
|
|
rapidly multiplying the number of <TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
> flags.
|
|
If, for example, the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> contains three directories
|
|
(and shorter repository path names!):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CPPPATH = ['dir1', 'dir2', 'dir3'])
|
|
env.Program('hello.c')
|
|
Repository('/r1', '/r2')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then we'll end up with nine <TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
> options
|
|
on the command line,
|
|
three (for each of the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> directories)
|
|
times three (for the local directory plus the two repositories):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c -Idir1 -I/r1/dir1 -I/r2/dir1 -Idir2 -I/r1/dir2 -I/r2/dir2 -Idir3 -I/r1/dir3 -I/r2/dir3 hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H3
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3878"
|
|
>23.3.1. Limitations on <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files in repositories</A
|
|
></H3
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> relies on the C compiler's
|
|
<TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
> options to control the order in which
|
|
the preprocessor will search the repository directories
|
|
for <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files.
|
|
This causes a problem, however, with how the C preprocessor
|
|
handles <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> lines with
|
|
the file name included in double-quotes.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
As we've seen,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will compile the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file from
|
|
the repository if it doesn't exist in
|
|
the local directory.
|
|
If, however, the <TT
|
|
CLASS="filename"
|
|
>hello.c</TT
|
|
> file in the repository contains
|
|
a <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> line with the file name in
|
|
double quotes:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> #include "hello.h"
|
|
int
|
|
main(int argc, char *argv[])
|
|
{
|
|
printf(HELLO_MESSAGE);
|
|
return (0);
|
|
}
|
|
</PRE
|
|
><P
|
|
>
|
|
Then the C preprocessor will <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>always</I
|
|
></SPAN
|
|
>
|
|
use a <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file from the repository directory first,
|
|
even if there is a <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file in the local directory,
|
|
despite the fact that the command line specifies
|
|
<TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
> as the first option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c -I. -I/usr/repository1 /usr/repository1/hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
This behavior of the C preprocessor--always search
|
|
for a <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> file in double-quotes
|
|
first in the same directory as the source file,
|
|
and only then search the <TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
>--can
|
|
not, in general, be changed.
|
|
In other words, it's a limitation
|
|
that must be lived with if you want to use
|
|
code repositories in this way.
|
|
There are three ways you can possibly
|
|
work around this C preprocessor behavior:
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><OL
|
|
TYPE="1"
|
|
><LI
|
|
><P
|
|
>
|
|
Some modern versions of C compilers do have an option
|
|
to disable or control this behavior.
|
|
If so, add that option to <A
|
|
HREF="#cv-CFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFLAGS</CODE
|
|
></A
|
|
>
|
|
(or <A
|
|
HREF="#cv-CXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFLAGS</CODE
|
|
></A
|
|
> or both) in your construction environment(s).
|
|
Make sure the option is used for all construction
|
|
environments that use C preprocessing!
|
|
|
|
</P
|
|
></LI
|
|
><LI
|
|
><P
|
|
>
|
|
Change all occurrences of <TT
|
|
CLASS="literal"
|
|
>#include "file.h"</TT
|
|
>
|
|
to <TT
|
|
CLASS="literal"
|
|
>#include <file.h></TT
|
|
>.
|
|
Use of <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> with angle brackets
|
|
does not have the same behavior--the <TT
|
|
CLASS="literal"
|
|
>-I</TT
|
|
>
|
|
directories are searched first
|
|
for <TT
|
|
CLASS="literal"
|
|
>#include</TT
|
|
> files--which
|
|
gives <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> direct control over the list of
|
|
directories the C preprocessor will search.
|
|
|
|
</P
|
|
></LI
|
|
><LI
|
|
><P
|
|
>
|
|
Require that everyone working with compilation from
|
|
repositories check out and work on entire directories of files,
|
|
not individual files.
|
|
(If you use local wrapper scripts around
|
|
your source code control system's command,
|
|
you could add logic to enforce this restriction there.
|
|
|
|
</P
|
|
></LI
|
|
></OL
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3919"
|
|
>23.4. Finding the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file in repositories</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will also search in repositories
|
|
for the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file and any specified <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
This poses a problem, though: how can <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> search a
|
|
repository tree for an <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
if the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file itself contains the information
|
|
about the pathname of the repository?
|
|
To solve this problem, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> allows you
|
|
to specify repository directories
|
|
on the command line using the <TT
|
|
CLASS="literal"
|
|
>-Y</TT
|
|
> option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -Y /usr/repository1 -Y /usr/repository2</KBD
|
|
>
|
|
</PRE
|
|
><P
|
|
>
|
|
When looking for source or derived files,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will first search the repositories
|
|
specified on the command line,
|
|
and then search the repositories
|
|
specified in the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> or <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3937"
|
|
>23.5. Finding derived files in repositories</A
|
|
></H2
|
|
><P
|
|
>
|
|
If a repository contains not only source files,
|
|
but also derived files (such as object files,
|
|
libraries, or executables), <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will perform
|
|
its normal MD5 signature calculation to
|
|
decide if a derived file in a repository is up-to-date,
|
|
or the derived file must be rebuilt in the local build directory.
|
|
For the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> signature calculation to work correctly,
|
|
a repository tree must contain the <TT
|
|
CLASS="filename"
|
|
>.sconsign</TT
|
|
> files
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses to keep track of signature information.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Usually, this would be done by a build integrator
|
|
who would run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in the repository
|
|
to create all of its derived files and <TT
|
|
CLASS="filename"
|
|
>.sconsign</TT
|
|
> files,
|
|
or who would run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> in a separate build directory
|
|
and copy the resulting tree to the desired repository:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>cd /usr/repository1</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o file1.o -c file1.c
|
|
cc -o file2.o -c file2.c
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o file1.o file2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
(Note that this is safe even if the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file
|
|
lists <TT
|
|
CLASS="filename"
|
|
>/usr/repository1</TT
|
|
> as a repository,
|
|
because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will remove the current build directory
|
|
from its repository list for that invocation.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Now, with the repository populated,
|
|
we only need to create the one local source file
|
|
we're interested in working with at the moment,
|
|
and use the <TT
|
|
CLASS="literal"
|
|
>-Y</TT
|
|
> option to
|
|
tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to fetch any other files it needs
|
|
from the repository:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>cd $HOME/build</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.c</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -Y /usr/repository1</KBD
|
|
>
|
|
cc -c -o hello.o hello.c
|
|
cc -o hello hello.o /usr/repository1/file1.o /usr/repository1/file2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> realizes that it does not need to
|
|
rebuild local copies <TT
|
|
CLASS="filename"
|
|
>file1.o</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>file2.o</TT
|
|
> files,
|
|
but instead uses the already-compiled files
|
|
from the repository.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN3966"
|
|
>23.6. Guaranteeing local copies of files</A
|
|
></H2
|
|
><P
|
|
>
|
|
If the repository tree contains the complete results of a build,
|
|
and we try to build from the repository
|
|
without any files in our local tree,
|
|
something moderately surprising happens:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>mkdir $HOME/build2</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>cd $HOME/build2</KBD
|
|
>
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -Y /usr/all/repository hello</KBD
|
|
>
|
|
scons: `hello' is up-to-date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Why does <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> say that the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program
|
|
is up-to-date when there is no <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program
|
|
in the local build directory?
|
|
Because the repository (not the local directory)
|
|
contains the up-to-date <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> program,
|
|
and <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> correctly determines that nothing
|
|
needs to be done to rebuild that
|
|
up-to-date copy of the file.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
There are, however, many times when you want to ensure that a
|
|
local copy of a file always exists.
|
|
A packaging or testing script, for example,
|
|
may assume that certain generated files exist locally.
|
|
To tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to make a copy of any up-to-date repository
|
|
file in the local build directory,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>Local</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
Local(hello)
|
|
</PRE
|
|
><P
|
|
>
|
|
If we then run the same command,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will make a local copy of the program
|
|
from the repository copy,
|
|
and tell you that it is doing so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Y /usr/all/repository hello</KBD
|
|
>
|
|
Local copy of hello from /usr/all/repository/hello
|
|
scons: `hello' is up-to-date.
|
|
</PRE
|
|
><P
|
|
>
|
|
(Notice that, because the act of making the local copy
|
|
is not considered a "build" of the <SPAN
|
|
CLASS="application"
|
|
>hello</SPAN
|
|
> file,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> still reports that it is up-to-date.)
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-sconf"
|
|
></A
|
|
>Chapter 24. Multi-Platform Configuration (<SPAN
|
|
CLASS="application"
|
|
>Autoconf</SPAN
|
|
> Functionality)</H1
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> has integrated support for multi-platform build configuration
|
|
similar to that offered by GNU <SPAN
|
|
CLASS="application"
|
|
>Autoconf</SPAN
|
|
>,
|
|
such as
|
|
figuring out what libraries or header files
|
|
are available on the local system.
|
|
This section describes how to use
|
|
this <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> feature.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="note"
|
|
><P
|
|
></P
|
|
><TABLE
|
|
CLASS="note"
|
|
WIDTH="100%"
|
|
BORDER="0"
|
|
><TR
|
|
><TD
|
|
WIDTH="25"
|
|
ALIGN="CENTER"
|
|
VALIGN="TOP"
|
|
><IMG
|
|
SRC="../images/note.gif"
|
|
HSPACE="5"
|
|
ALT="Note"></TD
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
><P
|
|
> This chapter is still under development,
|
|
so not everything is explained as well as it should be.
|
|
See the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> man page for additional information.
|
|
</P
|
|
></TD
|
|
></TR
|
|
></TABLE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4000"
|
|
>24.1. <TT
|
|
CLASS="literal"
|
|
>Configure Contexts</TT
|
|
></A
|
|
></H2
|
|
><P
|
|
>
|
|
The basic framework for multi-platform build configuration
|
|
in <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is to attach a <TT
|
|
CLASS="literal"
|
|
>configure context</TT
|
|
> to a
|
|
construction environment by calling the <CODE
|
|
CLASS="function"
|
|
>Configure</CODE
|
|
> function,
|
|
perform a number of checks for
|
|
libraries, functions, header files, etc.,
|
|
and to then call the configure context's <CODE
|
|
CLASS="function"
|
|
>Finish</CODE
|
|
> method
|
|
to finish off the configuration:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
# Checks for libraries, header files, etc. go here!
|
|
env = conf.Finish()
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides a number of basic checks,
|
|
as well as a mechanism for adding your own custom checks.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses its own dependency
|
|
mechanism to determine when a check
|
|
needs to be run--that is,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not run the checks
|
|
every time it is invoked,
|
|
but caches the values returned by previous checks
|
|
and uses the cached values unless something has changed.
|
|
This saves a tremendous amount
|
|
of developer time while working on
|
|
cross-platform build issues.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The next sections describe
|
|
the basic checks that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports,
|
|
as well as how to add your own custom checks.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4016"
|
|
>24.2. Checking for the Existence of Header Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
Testing the existence of a header file
|
|
requires knowing what language the header file is.
|
|
A configure context has a <CODE
|
|
CLASS="function"
|
|
>CheckCHeader</CODE
|
|
> method
|
|
that checks for the existence of a C header file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
if not conf.CheckCHeader('math.h'):
|
|
print 'Math.h must be installed!'
|
|
Exit(1)
|
|
if conf.CheckCHeader('foo.h'):
|
|
conf.env.Append('-DHAS_FOO_H')
|
|
env = conf.Finish()
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that you can choose to terminate
|
|
the build if a given header file doesn't exist,
|
|
or you can modify the construction environment
|
|
based on the existence of a header file.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you need to check for the existence
|
|
a C++ header file,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>CheckCXXHeader</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
if not conf.CheckCXXHeader('vector.h'):
|
|
print 'vector.h must be installed!'
|
|
Exit(1)
|
|
env = conf.Finish()
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4025"
|
|
>24.3. Checking for the Availability of a Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Check for the availability of a specific function
|
|
using the <CODE
|
|
CLASS="function"
|
|
>CheckFunc</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
if not conf.CheckFunc('strcpy'):
|
|
print 'Did not find strcpy(), using local version'
|
|
conf.env.Append('-Dstrcpy=my_local_strcpy')
|
|
env = conf.Finish()
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4030"
|
|
>24.4. Checking for the Availability of a Library</A
|
|
></H2
|
|
><P
|
|
>
|
|
Check for the availability of a library
|
|
using the <CODE
|
|
CLASS="function"
|
|
>CheckLib</CODE
|
|
> method.
|
|
You only specify the basename of the library,
|
|
you don't need to add a <TT
|
|
CLASS="literal"
|
|
>lib</TT
|
|
>
|
|
prefix or a <TT
|
|
CLASS="literal"
|
|
>.a</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>.lib</TT
|
|
> suffix:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
if not conf.CheckLib('m'):
|
|
print 'Did not find libm.a or m.lib, exiting!'
|
|
Exit(1)
|
|
env = conf.Finish()
|
|
</PRE
|
|
><P
|
|
>
|
|
Because the ability to use a library successfully
|
|
often depends on having access to a header file
|
|
that describes the library's interface,
|
|
you can check for a library
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>and</I
|
|
></SPAN
|
|
> a header file
|
|
at the same time by using the
|
|
<CODE
|
|
CLASS="function"
|
|
>CheckLibWithHeader</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
if not conf.CheckLibWithHeader('m', 'math.h', 'c'):
|
|
print 'Did not find libm.a or m.lib, exiting!'
|
|
Exit(1)
|
|
env = conf.Finish()
|
|
</PRE
|
|
><P
|
|
>
|
|
This is essentially shorthand for
|
|
separate calls to the <CODE
|
|
CLASS="function"
|
|
>CheckHeader</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>CheckLib</CODE
|
|
>
|
|
functions.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4045"
|
|
>24.5. Checking for the Availability of a <TT
|
|
CLASS="literal"
|
|
>typedef</TT
|
|
></A
|
|
></H2
|
|
><P
|
|
>
|
|
Check for the availability of a <TT
|
|
CLASS="literal"
|
|
>typedef</TT
|
|
>
|
|
by using the <CODE
|
|
CLASS="function"
|
|
>CheckType</CODE
|
|
> method:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
if not conf.CheckType('off_t'):
|
|
print 'Did not find off_t typedef, assuming int'
|
|
conf.env.Append(CCFLAGS = '-Doff_t=int')
|
|
env = conf.Finish()
|
|
</PRE
|
|
><P
|
|
>
|
|
You can also add a string that will be
|
|
placed at the beginning of the test file
|
|
that will be used to check for the <TT
|
|
CLASS="literal"
|
|
>typedef</TT
|
|
>.
|
|
This provide a way to specify
|
|
files that must be included to find the <TT
|
|
CLASS="literal"
|
|
>typedef</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env)
|
|
if not conf.CheckType('off_t', '#include <sys/types.h>\n'):
|
|
print 'Did not find off_t typedef, assuming int'
|
|
conf.env.Append(CCFLAGS = '-Doff_t=int')
|
|
env = conf.Finish()
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4056"
|
|
>24.6. Adding Your Own Custom Checks</A
|
|
></H2
|
|
><P
|
|
>
|
|
A custom check is a Python function
|
|
that checks for a certain condition to exist
|
|
on the running system,
|
|
usually using methods that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
supplies to take care of the details
|
|
of checking whether a compilation succeeds,
|
|
a link succeeds,
|
|
a program is runnable,
|
|
etc.
|
|
A simple custom check for the existence of
|
|
a specific library might look as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> mylib_test_source_file = """
|
|
#include <mylib.h>
|
|
int main(int argc, char **argv)
|
|
{
|
|
MyLibrary mylib(argc, argv);
|
|
return 0;
|
|
}
|
|
"""
|
|
|
|
def CheckMyLibrary(context):
|
|
context.Message('Checking for MyLibrary...')
|
|
result = context.TryLink(mylib_test_source_file, '.c')
|
|
context.Result(result)
|
|
return result
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Message</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>Result</CODE
|
|
> methods
|
|
should typically begin and end a custom check to
|
|
let the user know what's going on:
|
|
the <CODE
|
|
CLASS="function"
|
|
>Message</CODE
|
|
> call prints the
|
|
specified message (with no trailing newline)
|
|
and the <CODE
|
|
CLASS="function"
|
|
>Result</CODE
|
|
> call prints
|
|
<TT
|
|
CLASS="literal"
|
|
>ok</TT
|
|
> if the check succeeds and
|
|
<TT
|
|
CLASS="literal"
|
|
>failed</TT
|
|
> if it doesn't.
|
|
The <CODE
|
|
CLASS="function"
|
|
>TryLink</CODE
|
|
> method
|
|
actually tests for whether the
|
|
specified program text
|
|
will successfully link.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
(Note that a custom check can modify
|
|
its check based on any arguments you
|
|
choose to pass it,
|
|
or by using or modifying the configure context environment
|
|
in the <TT
|
|
CLASS="literal"
|
|
>context.env</TT
|
|
> attribute.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
This custom check function is
|
|
then attached to the <TT
|
|
CLASS="literal"
|
|
>configure context</TT
|
|
>
|
|
by passing a dictionary
|
|
to the <CODE
|
|
CLASS="function"
|
|
>Configure</CODE
|
|
> call
|
|
that maps a name of the check
|
|
to the underlying function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
conf = Configure(env, custom_tests = {'CheckMyLibrary' : CheckMyLibrary})
|
|
</PRE
|
|
><P
|
|
>
|
|
You'll typically want to make
|
|
the check and the function name the same,
|
|
as we've done here,
|
|
to avoid potential confusion.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
We can then put these pieces together
|
|
and actually call the <TT
|
|
CLASS="literal"
|
|
>CheckMyLibrary</TT
|
|
> check
|
|
as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> mylib_test_source_file = """
|
|
#include <mylib.h>
|
|
int main(int argc, char **argv)
|
|
{
|
|
MyLibrary mylib(argc, argv);
|
|
return 0;
|
|
}
|
|
"""
|
|
|
|
def CheckMyLibrary(context):
|
|
context.Message('Checking for MyLibrary... ')
|
|
result = context.TryLink(mylib_test_source_file, '.c')
|
|
context.Result(result)
|
|
return result
|
|
|
|
env = Environment()
|
|
conf = Configure(env, custom_tests = {'CheckMyLibrary' : CheckMyLibrary})
|
|
if not conf.CheckMyLibrary():
|
|
print 'MyLibrary is not installed!'
|
|
Exit(1)
|
|
env = conf.Finish()
|
|
|
|
# We would then add actual calls like Program() to build
|
|
# something using the "env" construction environment.
|
|
</PRE
|
|
><P
|
|
>
|
|
If MyLibrary is not installed on the system,
|
|
the output will look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript file ...
|
|
Checking for MyLibrary... failed
|
|
MyLibrary is not installed!
|
|
</PRE
|
|
><P
|
|
>
|
|
If MyLibrary is installed,
|
|
the output will look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript file ...
|
|
Checking for MyLibrary... failed
|
|
scons: done reading SConscript
|
|
scons: Building targets ...
|
|
.
|
|
.
|
|
.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4085"
|
|
>24.7. Not Configuring When Cleaning Targets</A
|
|
></H2
|
|
><P
|
|
>
|
|
Using multi-platform configuration
|
|
as described in the previous sections
|
|
will run the configuration commands
|
|
even when invoking
|
|
<KBD
|
|
CLASS="userinput"
|
|
>scons -c</KBD
|
|
>
|
|
to clean targets:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Checking for MyLibrary... ok
|
|
Removed foo.o
|
|
Removed foo
|
|
</PRE
|
|
><P
|
|
>
|
|
Although running the platform checks
|
|
when removing targets doesn't hurt anything,
|
|
it's usually unnecessary.
|
|
You can avoid this by using the
|
|
<CODE
|
|
CLASS="function"
|
|
>GetOption</CODE
|
|
>(); method to
|
|
check whether the <CODE
|
|
CLASS="option"
|
|
>-c</CODE
|
|
> (clean)
|
|
option has been invoked on the command line:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
if not env.GetOption('clean'):
|
|
conf = Configure(env, custom_tests = {'CheckMyLibrary' : CheckMyLibrary})
|
|
if not conf.CheckMyLibrary():
|
|
print 'MyLibrary is not installed!'
|
|
Exit(1)
|
|
env = conf.Finish()
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed foo.o
|
|
Removed foo
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-caching"
|
|
></A
|
|
>Chapter 25. Caching Built Files</H1
|
|
><P
|
|
>
|
|
On multi-developer software projects,
|
|
you can sometimes speed up every developer's builds a lot by
|
|
allowing them to share the derived files that they build.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> makes this easy, as well as reliable.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4101"
|
|
>25.1. Specifying the Shared Cache Directory</A
|
|
></H2
|
|
><P
|
|
>
|
|
To enable sharing of derived files,
|
|
use the <CODE
|
|
CLASS="function"
|
|
>CacheDir</CODE
|
|
> function
|
|
in any <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> CacheDir('/usr/local/build_cache')
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the directory you specify must already exist
|
|
and be readable and writable by all developers
|
|
who will be sharing derived files.
|
|
It should also be in some central location
|
|
that all builds will be able to access.
|
|
In environments where developers are using separate systems
|
|
(like individual workstations) for builds,
|
|
this directory would typically be
|
|
on a shared or NFS-mounted file system.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Here's what happens:
|
|
When a build has a <CODE
|
|
CLASS="function"
|
|
>CacheDir</CODE
|
|
> specified,
|
|
every time a file is built,
|
|
it is stored in the shared cache directory
|
|
along with its MD5 build signature.
|
|
<A
|
|
NAME="AEN4110"
|
|
HREF="#FTN.AEN4110"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[5]</SPAN
|
|
></A
|
|
>
|
|
On subsequent builds,
|
|
before an action is invoked to build a file,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will check the shared cache directory
|
|
to see if a file with the exact same build
|
|
signature already exists.
|
|
If so, the derived file will not be built locally,
|
|
but will be copied into the local build directory
|
|
from the shared cache directory,
|
|
like so:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed hello.o
|
|
Removed hello
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Retrieved `hello.o' from cache
|
|
Retrieved `hello' from cache
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the <CODE
|
|
CLASS="function"
|
|
>CacheDir</CODE
|
|
> feature still calculates
|
|
MD5 build sigantures for the shared cache file names
|
|
even if you configure <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to use timestamps
|
|
to decide if files are up to date.
|
|
(See the <A
|
|
HREF="#chap-depends"
|
|
>Chapter 6</A
|
|
>
|
|
chapter for information about the <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function.)
|
|
Consequently, using <CODE
|
|
CLASS="function"
|
|
>CacheDir</CODE
|
|
> may reduce or eliminate any
|
|
potential performance improvements
|
|
from using timestamps for up-to-date decisions.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4123"
|
|
>25.2. Keeping Build Output Consistent</A
|
|
></H2
|
|
><P
|
|
>
|
|
One potential drawback to using a shared cache
|
|
is that the output printed by <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
can be inconsistent from invocation to invocation,
|
|
because any given file may be rebuilt one time
|
|
and retrieved from the shared cache the next time.
|
|
This can make analyzing build output more difficult,
|
|
especially for automated scripts that
|
|
expect consistent output each time.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If, however, you use the <TT
|
|
CLASS="literal"
|
|
>--cache-show</TT
|
|
> option,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will print the command line that it
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>would</I
|
|
></SPAN
|
|
> have executed
|
|
to build the file,
|
|
even when it is retrieving the file from the shared cache.
|
|
This makes the build output consistent
|
|
every time the build is run:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed hello.o
|
|
Removed hello
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --cache-show</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
The trade-off, of course, is that you no longer
|
|
know whether or not <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
has retrieved a derived file from cache
|
|
or has rebuilt it locally.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4137"
|
|
>25.3. Not Using the Shared Cache for Specific Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
You may want to disable caching for certain
|
|
specific files in your configuration.
|
|
For example, if you only want to put
|
|
executable files in a central cache,
|
|
but not the intermediate object files,
|
|
you can use the <CODE
|
|
CLASS="function"
|
|
>NoCache</CODE
|
|
>
|
|
function to specify that the
|
|
object files should not be cached:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
obj = env.Object('hello.c')
|
|
env.Program('hello.c')
|
|
CacheDir('cache')
|
|
NoCache('hello.o')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then when you run <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> after cleaning
|
|
the built targets,
|
|
it will recompile the object file locally
|
|
(since it doesn't exist in the shared cache directory),
|
|
but still realize that the shared cache directory
|
|
contains an up-to-date executable program
|
|
that can be retrieved instead of re-linking:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed hello.o
|
|
Removed hello
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
Retrieved `hello' from cache
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4148"
|
|
>25.4. Disabling the Shared Cache</A
|
|
></H2
|
|
><P
|
|
>
|
|
Retrieving an already-built file
|
|
from the shared cache
|
|
is usually a significant time-savings
|
|
over rebuilding the file,
|
|
but how much of a savings
|
|
(or even whether it saves time at all)
|
|
can depend a great deal on your
|
|
system or network configuration.
|
|
For example, retrieving cached files
|
|
from a busy server over a busy network
|
|
might end up being slower than
|
|
rebuilding the files locally.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
In these cases, you can specify
|
|
the <TT
|
|
CLASS="literal"
|
|
>--cache-disable</TT
|
|
>
|
|
command-line option to tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
to not retrieve already-built files from the
|
|
shared cache directory:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed hello.o
|
|
Removed hello
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Retrieved `hello.o' from cache
|
|
Retrieved `hello' from cache
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed hello.o
|
|
Removed hello
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --cache-disable</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4160"
|
|
>25.5. Populating a Shared Cache With Already-Built Files</A
|
|
></H2
|
|
><P
|
|
>
|
|
Sometimes, you may have one or more derived files
|
|
already built in your local build tree
|
|
that you wish to make available to other people doing builds.
|
|
For example, you may find it more effective to perform
|
|
integration builds with the cache disabled
|
|
(per the previous section)
|
|
and only populate the shared cache directory
|
|
with the built files after the integration build
|
|
has completed successfully.
|
|
This way, the cache will only get filled up
|
|
with derived files that are part of a complete, successful build
|
|
not with files that might be later overwritten
|
|
while you debug integration problems.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
In this case, you can use the
|
|
the <TT
|
|
CLASS="literal"
|
|
>--cache-force</TT
|
|
> option
|
|
to tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to put all derived files in the cache,
|
|
even if the files already exist in your local tree
|
|
from having been built by a previous invocation:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --cache-disable</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c</KBD
|
|
>
|
|
Removed hello.o
|
|
Removed hello
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --cache-disable</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --cache-force</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
Notice how the above sample run
|
|
demonstrates that the <TT
|
|
CLASS="literal"
|
|
>--cache-disable</TT
|
|
>
|
|
option avoids putting the built
|
|
<TT
|
|
CLASS="filename"
|
|
>hello.o</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>hello</TT
|
|
> files in the cache,
|
|
but after using the <TT
|
|
CLASS="literal"
|
|
>--cache-force</TT
|
|
> option,
|
|
the files have been put in the cache
|
|
for the next invocation to retrieve.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4177"
|
|
>25.6. Minimizing Cache Contention: the <TT
|
|
CLASS="literal"
|
|
>--random</TT
|
|
> Option</A
|
|
></H2
|
|
><P
|
|
>
|
|
If you allow multiple builds to update the
|
|
shared cache directory simultaneously,
|
|
two builds that occur at the same time
|
|
can sometimes start "racing"
|
|
with one another to build the same files
|
|
in the same order.
|
|
If, for example,
|
|
you are linking multiple files into an executable program:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('prog',
|
|
['f1.c', 'f2.c', 'f3.c', 'f4.c', 'f5.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will normally build the input object files
|
|
on which the program depends in their normal, sorted order:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o f1.o -c f1.c
|
|
cc -o f2.o -c f2.c
|
|
cc -o f3.o -c f3.c
|
|
cc -o f4.o -c f4.c
|
|
cc -o f5.o -c f5.c
|
|
cc -o prog f1.o f2.o f3.o f4.o f5.o
|
|
</PRE
|
|
><P
|
|
>
|
|
But if two such builds take place simultaneously,
|
|
they may each look in the cache at nearly the same
|
|
time and both decide that <TT
|
|
CLASS="filename"
|
|
>f1.o</TT
|
|
>
|
|
must be rebuilt and pushed into the shared cache directory,
|
|
then both decide that <TT
|
|
CLASS="filename"
|
|
>f2.o</TT
|
|
>
|
|
must be rebuilt (and pushed into the shared cache directory),
|
|
then both decide that <TT
|
|
CLASS="filename"
|
|
>f3.o</TT
|
|
>
|
|
must be rebuilt...
|
|
This won't cause any actual build problems--both
|
|
builds will succeed,
|
|
generate correct output files,
|
|
and populate the cache--but
|
|
it does represent wasted effort.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
To alleviate such contention for the cache,
|
|
you can use the <TT
|
|
CLASS="literal"
|
|
>--random</TT
|
|
> command-line option
|
|
to tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to build dependencies
|
|
in a random order:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --random</KBD
|
|
>
|
|
cc -o f3.o -c f3.c
|
|
cc -o f1.o -c f1.c
|
|
cc -o f5.o -c f5.c
|
|
cc -o f2.o -c f2.c
|
|
cc -o f4.o -c f4.c
|
|
cc -o prog f1.o f2.o f3.o f4.o f5.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Multiple builds using the <TT
|
|
CLASS="literal"
|
|
>--random</TT
|
|
> option
|
|
will usually build their dependencies in different,
|
|
random orders,
|
|
which minimizes the chances for a lot of
|
|
contention for same-named files
|
|
in the shared cache directory.
|
|
Multiple simultaneous builds might still race to try to build
|
|
the same target file on occasion,
|
|
but long sequences of inefficient contention
|
|
should be rare.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note, of course,
|
|
the <TT
|
|
CLASS="literal"
|
|
>--random</TT
|
|
> option
|
|
will cause the output that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> prints
|
|
to be inconsistent from invocation to invocation,
|
|
which may be an issue when
|
|
trying to compare output from different build runs.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
If you want to make sure dependencies will be built
|
|
in a random order without having to specify
|
|
the <TT
|
|
CLASS="literal"
|
|
>--random</TT
|
|
> on very command line,
|
|
you can use the <CODE
|
|
CLASS="function"
|
|
>SetOption</CODE
|
|
> function to
|
|
set the <TT
|
|
CLASS="literal"
|
|
>random</TT
|
|
> option
|
|
within any <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('prog',
|
|
['f1.c', 'f2.c', 'f3.c', 'f4.c', 'f5.c'])
|
|
|
|
SetOption('random', 1)
|
|
Program('prog',
|
|
['f1.c', 'f2.c', 'f3.c', 'f4.c', 'f5.c'])
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-alias"
|
|
></A
|
|
>Chapter 26. Alias Targets</H1
|
|
><P
|
|
>
|
|
We've already seen how you can use the <CODE
|
|
CLASS="function"
|
|
>Alias</CODE
|
|
>
|
|
function to create a target named <TT
|
|
CLASS="literal"
|
|
>install</TT
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
hello = env.Program('hello.c')
|
|
env.Install('/usr/bin', hello)
|
|
env.Alias('install', '/usr/bin')
|
|
</PRE
|
|
><P
|
|
>
|
|
You can then use this alias on the command line
|
|
to tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> more naturally that you want to install files:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
Install file: "hello" as "/usr/bin/hello"
|
|
</PRE
|
|
><P
|
|
>
|
|
Like other <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
> methods, though,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Alias</CODE
|
|
> method returns an object
|
|
representing the alias being built.
|
|
You can then use this object as input to anothother <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>.
|
|
This is especially useful if you use such an object
|
|
as input to another call to the <CODE
|
|
CLASS="function"
|
|
>Alias</CODE
|
|
> <CODE
|
|
CLASS="classname"
|
|
>Builder</CODE
|
|
>,
|
|
allowing you to create a hierarchy
|
|
of nested aliases:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
p = env.Program('foo.c')
|
|
l = env.Library('bar.c')
|
|
env.Install('/usr/bin', p)
|
|
env.Install('/usr/lib', l)
|
|
ib = env.Alias('install-bin', '/usr/bin')
|
|
il = env.Alias('install-lib', '/usr/lib')
|
|
env.Alias('install', [ib, il])
|
|
</PRE
|
|
><P
|
|
>
|
|
This example defines separate <TT
|
|
CLASS="literal"
|
|
>install</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>install-bin</TT
|
|
>,
|
|
and <TT
|
|
CLASS="literal"
|
|
>install-lib</TT
|
|
> aliases,
|
|
allowing you finer control over what gets installed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install-bin</KBD
|
|
>
|
|
cc -o foo.o -c foo.c
|
|
cc -o foo foo.o
|
|
Install file: "foo" as "/usr/bin/foo"
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install-lib</KBD
|
|
>
|
|
cc -o bar.o -c bar.c
|
|
ar rc libbar.a bar.o
|
|
ranlib libbar.a
|
|
Install file: "libbar.a" as "/usr/lib/libbar.a"
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c /</KBD
|
|
>
|
|
Removed foo.o
|
|
Removed foo
|
|
Removed /usr/bin/foo
|
|
Removed bar.o
|
|
Removed libbar.a
|
|
Removed /usr/lib/libbar.a
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q install</KBD
|
|
>
|
|
cc -o foo.o -c foo.c
|
|
cc -o foo foo.o
|
|
Install file: "foo" as "/usr/bin/foo"
|
|
cc -o bar.o -c bar.c
|
|
ar rc libbar.a bar.o
|
|
ranlib libbar.a
|
|
Install file: "libbar.a" as "/usr/lib/libbar.a"
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-java"
|
|
></A
|
|
>Chapter 27. Java Builds</H1
|
|
><P
|
|
>
|
|
So far, we've been using examples of
|
|
building C and C++ programs
|
|
to demonstrate the features of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> also supports building Java programs,
|
|
but Java builds are handled slightly differently,
|
|
which reflects the ways in which
|
|
the Java compiler and tools
|
|
build programs differently than
|
|
other languages' tool chains.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4237"
|
|
>27.1. Building Java Class Files: the <CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
> Builder</A
|
|
></H2
|
|
><P
|
|
>
|
|
The basic activity when programming in Java,
|
|
of course, is to take one or more <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files
|
|
containing Java source code
|
|
and to call the Java compiler
|
|
to turn them into one or more
|
|
<TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files.
|
|
In <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>, you do this
|
|
by giving the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> Builder
|
|
a target directory in which
|
|
to put the <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files,
|
|
and a source directory that contains
|
|
the <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Java('classes', 'src')
|
|
</PRE
|
|
><P
|
|
>
|
|
If the <TT
|
|
CLASS="filename"
|
|
>src</TT
|
|
> directory contains
|
|
three <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> source files,
|
|
then running <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> might look like this:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src src/Example1.java src/Example2.java src/Example3.java
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will actually search the <TT
|
|
CLASS="filename"
|
|
>src</TT
|
|
>
|
|
directory tree for all of the <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files.
|
|
The Java compiler will then create the
|
|
necessary class files in the <TT
|
|
CLASS="filename"
|
|
>classes</TT
|
|
> subdirectory,
|
|
based on the class names found in the <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4261"
|
|
>27.2. How <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Handles Java Dependencies</A
|
|
></H2
|
|
><P
|
|
>
|
|
In addition to searching the source directory for
|
|
<TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> actually runs the <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files
|
|
through a stripped-down Java parser that figures out
|
|
what classes are defined.
|
|
In other words, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> knows,
|
|
without you having to tell it,
|
|
what <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files
|
|
will be produced by the <SPAN
|
|
CLASS="application"
|
|
>javac</SPAN
|
|
> call.
|
|
So our one-liner example from the preceding section:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Java('classes', 'src')
|
|
</PRE
|
|
><P
|
|
>
|
|
Will not only tell you reliably
|
|
that the <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files
|
|
in the <TT
|
|
CLASS="filename"
|
|
>classes</TT
|
|
> subdirectory
|
|
are up-to-date:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src src/Example1.java src/Example2.java src/Example3.java
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q classes</KBD
|
|
>
|
|
scons: `classes' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
But it will also remove all of the generated
|
|
<TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files,
|
|
even for inner classes,
|
|
without you having to specify them manually.
|
|
For example, if our
|
|
<TT
|
|
CLASS="filename"
|
|
>Example1.java</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>Example3.java</TT
|
|
>
|
|
files both define additional classes,
|
|
and the class defined in <TT
|
|
CLASS="filename"
|
|
>Example2.java</TT
|
|
>
|
|
has an inner class,
|
|
running <KBD
|
|
CLASS="userinput"
|
|
>scons -c</KBD
|
|
>
|
|
will clean up all of those <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files
|
|
as well:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src src/Example1.java src/Example2.java src/Example3.java
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q -c classes</KBD
|
|
>
|
|
Removed classes/Example1.class
|
|
Removed classes/AdditionalClass1.class
|
|
Removed classes/Example2$Inner2.class
|
|
Removed classes/Example2.class
|
|
Removed classes/Example3.class
|
|
Removed classes/AdditionalClass3.class
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4288"
|
|
>27.3. Building Java Archive (<TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
>) Files: the <CODE
|
|
CLASS="function"
|
|
>Jar</CODE
|
|
> Builder</A
|
|
></H2
|
|
><P
|
|
>
|
|
After building the class files,
|
|
it's common to collect them into
|
|
a Java archive (<TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
>) file,
|
|
which you do by calling the <A
|
|
HREF="#b-Jar"
|
|
><CODE
|
|
CLASS="function"
|
|
>Jar</CODE
|
|
></A
|
|
> Builder method.
|
|
If you want to just collect all of the
|
|
class files within a subdirectory,
|
|
you can just specify that subdirectory
|
|
as the <CODE
|
|
CLASS="function"
|
|
>Jar</CODE
|
|
> source:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Java(target = 'classes', source = 'src')
|
|
Jar(target = 'test.jar', source = 'classes')
|
|
</PRE
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will then pass that directory
|
|
to the <SPAN
|
|
CLASS="application"
|
|
>jar</SPAN
|
|
> command,
|
|
which will collect all of the underlying
|
|
<TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src src/Example1.java src/Example2.java src/Example3.java
|
|
jar cf test.jar classes
|
|
</PRE
|
|
><P
|
|
>
|
|
If you want to keep all of the
|
|
<TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files
|
|
for multiple programs in one location,
|
|
and only archive some of them in
|
|
each <TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
> file,
|
|
you can pass the <CODE
|
|
CLASS="function"
|
|
>Jar</CODE
|
|
> builder a
|
|
list of files as its source.
|
|
It's extremely simple to create multiple
|
|
<TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
> files this way,
|
|
using the lists of target class files created
|
|
by calls to the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> builder
|
|
as sources to the various <CODE
|
|
CLASS="function"
|
|
>Jar</CODE
|
|
> calls:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> prog1_class_files = Java(target = 'classes', source = 'prog1')
|
|
prog2_class_files = Java(target = 'classes', source = 'prog2')
|
|
Jar(target = 'prog1.jar', source = prog1_class_files)
|
|
Jar(target = 'prog2.jar', source = prog2_class_files)
|
|
</PRE
|
|
><P
|
|
>
|
|
This will then create
|
|
<TT
|
|
CLASS="filename"
|
|
>prog1.jar</TT
|
|
>
|
|
and <TT
|
|
CLASS="filename"
|
|
>prog2.jar</TT
|
|
>
|
|
next to the subdirectories
|
|
that contain their <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath prog1 prog1/Example1.java prog1/Example2.java
|
|
javac -d classes -sourcepath prog2 prog2/Example3.java prog2/Example4.java
|
|
jar cf prog1.jar -C classes Example1.class -C classes Example2.class
|
|
jar cf prog2.jar -C classes Example3.class -C classes Example4.class
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4319"
|
|
>27.4. Building C Header and Stub Files: the <CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
> Builder</A
|
|
></H2
|
|
><P
|
|
>
|
|
You can generate C header and source files
|
|
for implementing native methods,
|
|
by using the <A
|
|
HREF="#b-JavaH"
|
|
><CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
></A
|
|
> Builder.
|
|
There are several ways of using the <CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
> Builder.
|
|
One typical invocation might look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> classes = Java(target = 'classes', source = 'src/pkg/sub')
|
|
JavaH(target = 'native', source = classes)
|
|
</PRE
|
|
><P
|
|
>
|
|
The source is a list of class files generated by the
|
|
call to the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> Builder,
|
|
and the target is the output directory in
|
|
which we want the C header files placed.
|
|
The target
|
|
gets converted into the <CODE
|
|
CLASS="option"
|
|
>-d</CODE
|
|
>
|
|
when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> runs <SPAN
|
|
CLASS="application"
|
|
>javah</SPAN
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src/pkg/sub src/pkg/sub/Example1.java src/pkg/sub/Example2.java src/pkg/sub/Example3.java
|
|
javah -d native -classpath classes pkg.sub.Example1 pkg.sub.Example2 pkg.sub.Example3
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case,
|
|
the call to <SPAN
|
|
CLASS="application"
|
|
>javah</SPAN
|
|
>
|
|
will generate the header files
|
|
<TT
|
|
CLASS="filename"
|
|
>native/pkg_sub_Example1.h</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>native/pkg_sub_Example2.h</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>native/pkg_sub_Example3.h</TT
|
|
>.
|
|
Notice that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> remembered that the class
|
|
files were generated with a target directory of
|
|
<TT
|
|
CLASS="filename"
|
|
>classes</TT
|
|
>,
|
|
and that it then specified that target directory
|
|
as the <CODE
|
|
CLASS="option"
|
|
>-classpath</CODE
|
|
> option
|
|
to the call to <SPAN
|
|
CLASS="application"
|
|
>javah</SPAN
|
|
>.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Although it's more convenient to use
|
|
the list of class files returned by
|
|
the <CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
> Builder
|
|
as the source of a call to the <CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
> Builder,
|
|
you <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>can</I
|
|
></SPAN
|
|
>
|
|
specify the list of class files
|
|
by hand, if you prefer.
|
|
If you do,
|
|
you need to set the
|
|
<A
|
|
HREF="#cv-JAVACLASSDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSDIR</CODE
|
|
></A
|
|
> construction variable
|
|
when calling <CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Java(target = 'classes', source = 'src/pkg/sub')
|
|
class_file_list = ['classes/pkg/sub/Example1.class',
|
|
'classes/pkg/sub/Example2.class',
|
|
'classes/pkg/sub/Example3.class']
|
|
JavaH(target = 'native', source = class_file_list, JAVACLASSDIR = 'classes')
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSDIR</CODE
|
|
> value then
|
|
gets converted into the <CODE
|
|
CLASS="option"
|
|
>-classpath</CODE
|
|
>
|
|
when <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> runs <SPAN
|
|
CLASS="application"
|
|
>javah</SPAN
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src/pkg/sub src/pkg/sub/Example1.java src/pkg/sub/Example2.java src/pkg/sub/Example3.java
|
|
javah -d native -classpath classes pkg.sub.Example1 pkg.sub.Example2 pkg.sub.Example3
|
|
</PRE
|
|
><P
|
|
>
|
|
Lastly, if you don't want a separate header file
|
|
generated for each source file,
|
|
you can specify an explicit File Node
|
|
as the target of the <CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
> Builder:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> classes = Java(target = 'classes', source = 'src/pkg/sub')
|
|
JavaH(target = File('native.h'), source = classes)
|
|
</PRE
|
|
><P
|
|
>
|
|
Because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> assumes by default
|
|
that the target of the <CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
> builder is a directory,
|
|
you need to use the <CODE
|
|
CLASS="function"
|
|
>File</CODE
|
|
> function
|
|
to make sure that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> doesn't
|
|
create a directory named <TT
|
|
CLASS="filename"
|
|
>native.h</TT
|
|
>.
|
|
When a file is used, though,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> correctly converts the file name
|
|
into the <SPAN
|
|
CLASS="application"
|
|
>javah</SPAN
|
|
> <CODE
|
|
CLASS="option"
|
|
>-o</CODE
|
|
> option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src/pkg/sub src/pkg/sub/Example1.java src/pkg/sub/Example2.java src/pkg/sub/Example3.java
|
|
javah -o native.h -classpath classes pkg.sub.Example1 pkg.sub.Example2 pkg.sub.Example3
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4373"
|
|
>27.5. Building RMI Stub and Skeleton Class Files: the <CODE
|
|
CLASS="function"
|
|
>RMIC</CODE
|
|
> Builder</A
|
|
></H2
|
|
><P
|
|
>
|
|
You can generate Remote Method Invocation stubs
|
|
by using the <A
|
|
HREF="#b-RMIC"
|
|
><CODE
|
|
CLASS="function"
|
|
>RMIC</CODE
|
|
></A
|
|
> Builder.
|
|
The source is a list of directories,
|
|
typically returned by a call to the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> Builder,
|
|
and the target is an output directory
|
|
where the <TT
|
|
CLASS="filename"
|
|
>_Stub.class</TT
|
|
>
|
|
and <TT
|
|
CLASS="filename"
|
|
>_Skel.class</TT
|
|
> files will
|
|
be placed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> classes = Java(target = 'classes', source = 'src/pkg/sub')
|
|
RMIC(target = 'outdir', source = classes)
|
|
</PRE
|
|
><P
|
|
>
|
|
As it did with the <A
|
|
HREF="#b-JavaH"
|
|
><CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
></A
|
|
> Builder,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> remembers the class directory
|
|
and passes it as the <CODE
|
|
CLASS="option"
|
|
>-classpath</CODE
|
|
> option
|
|
to <SPAN
|
|
CLASS="application"
|
|
>rmic</SPAN
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
javac -d classes -sourcepath src/pkg/sub src/pkg/sub/Example1.java src/pkg/sub/Example2.java
|
|
rmic -d outdir -classpath classes pkg.sub.Example1 pkg.sub.Example2
|
|
</PRE
|
|
><P
|
|
>
|
|
This example would generate the files
|
|
<TT
|
|
CLASS="filename"
|
|
>outdir/pkg/sub/Example1_Skel.class</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>outdir/pkg/sub/Example1_Stub.class</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>outdir/pkg/sub/Example2_Skel.class</TT
|
|
> and
|
|
<TT
|
|
CLASS="filename"
|
|
>outdir/pkg/sub/Example2_Stub.class</TT
|
|
>.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-misc"
|
|
></A
|
|
>Chapter 28. Miscellaneous Functionality</H1
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a lot of additional functionality
|
|
that doesn't readily fit into the other chapters.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4401"
|
|
>28.1. Verifying the Python Version: the <CODE
|
|
CLASS="function"
|
|
>EnsurePythonVersion</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
Although the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> code itself will run
|
|
on any Python version 1.5.2 or later,
|
|
you are perfectly free to make use of
|
|
Python syntax and modules from more modern versions
|
|
(for example, Python 2.4 or 2.5)
|
|
when writing your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
or your own local modules.
|
|
If you do this, it's usually helpful to
|
|
configure <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to exit gracefully with an error message
|
|
if it's being run with a version of Python
|
|
that simply won't work with your code.
|
|
This is especially true if you're going to use <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
to build source code that you plan to distribute publicly,
|
|
where you can't be sure of the Python version
|
|
that an anonymous remote user might use
|
|
to try to build your software.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides an <CODE
|
|
CLASS="function"
|
|
>EnsurePythonVersion</CODE
|
|
> function for this.
|
|
You simply pass it the major and minor versions
|
|
numbers of the version of Python you require:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> EnsurePythonVersion(2, 5)
|
|
</PRE
|
|
><P
|
|
>
|
|
And then <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will exit with the following error
|
|
message when a user runs it with an unsupported
|
|
earlier version of Python:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
Python 2.5 or greater required, but you have Python 2.3.6
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4417"
|
|
>28.2. Verifying the SCons Version: the <CODE
|
|
CLASS="function"
|
|
>EnsureSConsVersion</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
You may, of course, write your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files
|
|
to use features that were only added in
|
|
recent versions of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>.
|
|
When you publicly distribute software that is built using <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>,
|
|
it's helpful to have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
verify the version being used and
|
|
exit gracefully with an error message
|
|
if the user's version of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> won't work
|
|
with your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> provides an <CODE
|
|
CLASS="function"
|
|
>EnsureSConsVersion</CODE
|
|
> function
|
|
that verifies the version of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
in the same
|
|
the <CODE
|
|
CLASS="function"
|
|
>EnsurePythonVersion</CODE
|
|
> function
|
|
verifies the version of Python,
|
|
by passing in the major and minor versions
|
|
numbers of the version of SCons you require:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> EnsureSConsVersion(1, 0)
|
|
</PRE
|
|
><P
|
|
>
|
|
And then <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will exit with the following error
|
|
message when a user runs it with an unsupported
|
|
earlier version of <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
SCons 1.0 or greater required, but you have SCons 0.98.5
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4437"
|
|
>28.3. Explicitly Terminating <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> While Reading <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> Files: the <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports an <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> function
|
|
which can be used to terminate <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
while reading the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files,
|
|
usually because you've detected a condition
|
|
under which it doesn't make sense to proceed:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> if ARGUMENTS.get('FUTURE'):
|
|
print "The FUTURE option is not supported yet!"
|
|
Exit(2)
|
|
env = Environment()
|
|
env.Program('hello.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q FUTURE=1</KBD
|
|
>
|
|
The FUTURE option is not supported yet!
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o hello.o -c hello.c
|
|
cc -o hello hello.o
|
|
</PRE
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> function takes as an argument
|
|
the (numeric) exit status that you want <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to exit with.
|
|
If you don't specify a value,
|
|
the default is to exit with <TT
|
|
CLASS="literal"
|
|
>0</TT
|
|
>,
|
|
which indicates successful execution.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that the <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> function
|
|
is equivalent to calling the Python
|
|
<CODE
|
|
CLASS="function"
|
|
>sys.exit</CODE
|
|
> function
|
|
(which the it actually calls),
|
|
but because <CODE
|
|
CLASS="function"
|
|
>Exit</CODE
|
|
> is a <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> function,
|
|
you don't have to import the Python
|
|
<TT
|
|
CLASS="literal"
|
|
>sys</TT
|
|
> module to use it.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4461"
|
|
>28.4. Searching for Files: the <CODE
|
|
CLASS="function"
|
|
>FindFile</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
The <CODE
|
|
CLASS="function"
|
|
>FindFile</CODE
|
|
> function searches for a file in a list of directories.
|
|
If there is only one directory, it can be given as a simple string.
|
|
The function returns a File node if a matching file exists,
|
|
or None if no file is found.
|
|
(See the documentation for the <CODE
|
|
CLASS="function"
|
|
>Glob</CODE
|
|
> function for an alternative way
|
|
of searching for entries in a directory.)
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # one directory
|
|
print FindFile('missing', '.')
|
|
t = FindFile('exists', '.')
|
|
print t.__class__, t
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
None
|
|
SCons.Node.FS.File exists
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # several directories
|
|
includes = [ '.', 'include', 'src/include']
|
|
headers = [ 'nonesuch.h', 'config.h', 'private.h', 'dist.h']
|
|
for hdr in headers:
|
|
print '%-12s' % ('%s:' % hdr), FindFile(hdr, includes)
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
nonesuch.h: None
|
|
config.h: config.h
|
|
private.h: src/include/private.h
|
|
dist.h: include/dist.h
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
If the file exists in more than one directory,
|
|
only the first occurrence is returned.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> print FindFile('multiple', ['sub1', 'sub2', 'sub3'])
|
|
print FindFile('multiple', ['sub2', 'sub3', 'sub1'])
|
|
print FindFile('multiple', ['sub3', 'sub1', 'sub2'])
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
sub1/multiple
|
|
sub2/multiple
|
|
sub3/multiple
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
><P
|
|
>
|
|
In addition to existing files, <CODE
|
|
CLASS="function"
|
|
>FindFile</CODE
|
|
> will also find derived files
|
|
(that is, non-leaf files) that haven't been built yet.
|
|
(Leaf files should already exist, or the build will fail!)
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Neither file exists, so build will fail
|
|
Command('derived', 'leaf', 'cat >$TARGET $SOURCE')
|
|
print FindFile('leaf', '.')
|
|
print FindFile('derived', '.')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
None
|
|
derived
|
|
scons: *** Source `leaf' not found, needed by target `derived'. Stop.
|
|
</PRE
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Neither file exists, so build will fail
|
|
Command('derived', 'leaf', 'cat >$TARGET $SOURCE')
|
|
print FindFile('leaf', '.')
|
|
print FindFile('derived', '.')
|
|
|
|
# Only 'leaf' exists
|
|
Command('derived', 'leaf', 'cat >$TARGET $SOURCE')
|
|
print FindFile('leaf', '.')
|
|
print FindFile('derived', '.')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
leaf
|
|
derived
|
|
cat > derived leaf
|
|
</PRE
|
|
><P
|
|
>
|
|
If a source file exists, <CODE
|
|
CLASS="function"
|
|
>FindFile</CODE
|
|
> will correctly return the name
|
|
in the build directory.
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Only 'src/leaf' exists
|
|
VariantDir('build', 'src')
|
|
print FindFile('leaf', 'build')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
build/leaf
|
|
scons: `.' is up to date.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4490"
|
|
>28.5. Handling Nested Lists: the <CODE
|
|
CLASS="function"
|
|
>Flatten</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a <CODE
|
|
CLASS="function"
|
|
>Flatten</CODE
|
|
> function
|
|
which takes an input Python sequence
|
|
(list or tuple)
|
|
and returns a flattened list
|
|
containing just the individual elements of
|
|
the sequence.
|
|
This can be handy when trying to examine
|
|
a list composed of the lists
|
|
returned by calls to various Builders.
|
|
For example, you might collect
|
|
object files built in different ways
|
|
into one call to the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
> Builder
|
|
by just enclosing them in a list, as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> objects = [
|
|
Object('prog1.c'),
|
|
Object('prog2.c', CCFLAGS='-DFOO'),
|
|
]
|
|
Program(objects)
|
|
</PRE
|
|
><P
|
|
>
|
|
Because the Builder calls in <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
flatten their input lists,
|
|
this works just fine to build the program:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o prog1.o -c prog1.c
|
|
cc -o prog2.o -c -DFOO prog2.c
|
|
cc -o prog1 prog1.o prog2.o
|
|
</PRE
|
|
><P
|
|
>
|
|
But if you were debugging your build
|
|
and wanted to print the absolute path
|
|
of each object file in the
|
|
<CODE
|
|
CLASS="varname"
|
|
>objects</CODE
|
|
> list,
|
|
you might try the following simple approach,
|
|
trying to print each Node's
|
|
<TT
|
|
CLASS="literal"
|
|
>abspath</TT
|
|
>
|
|
attribute:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> objects = [
|
|
Object('prog1.c'),
|
|
Object('prog2.c', CCFLAGS='-DFOO'),
|
|
]
|
|
Program(objects)
|
|
|
|
for object_file in objects:
|
|
print object_file.abspath
|
|
</PRE
|
|
><P
|
|
>
|
|
This does not work as expected
|
|
because each call to <CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
>
|
|
is operating an embedded list returned by
|
|
each <CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
> call,
|
|
not on the underlying Nodes within those lists:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
AttributeError: NodeList instance has no attribute 'abspath':
|
|
File "/home/my/project/SConstruct", line 8:
|
|
print object_file.abspath
|
|
</PRE
|
|
><P
|
|
>
|
|
The solution is to use the <CODE
|
|
CLASS="function"
|
|
>Flatten</CODE
|
|
> function
|
|
so that you can pass each Node to
|
|
the <CODE
|
|
CLASS="function"
|
|
>str</CODE
|
|
> separately:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> objects = [
|
|
Object('prog1.c'),
|
|
Object('prog2.c', CCFLAGS='-DFOO'),
|
|
]
|
|
Program(objects)
|
|
|
|
for object_file in Flatten(objects):
|
|
print object_file.abspath
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
/home/me/project/prog1.o
|
|
/home/me/project/prog2.o
|
|
cc -o prog1.o -c prog1.c
|
|
cc -o prog2.o -c -DFOO prog2.c
|
|
cc -o prog1 prog1.o prog2.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4517"
|
|
>28.6. Finding the Invocation Directory: the <CODE
|
|
CLASS="function"
|
|
>GetLaunchDir</CODE
|
|
> Function</A
|
|
></H2
|
|
><P
|
|
>
|
|
If you need to find the directory from
|
|
which the user invoked the <SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
> command,
|
|
you can use the <CODE
|
|
CLASS="function"
|
|
>GetLaunchDir</CODE
|
|
> function:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(
|
|
LAUNCHDIR = GetLaunchDir(),
|
|
)
|
|
env.Command('directory_build_info',
|
|
'$LAUNCHDIR/build_info'
|
|
Copy('$TARGET', '$SOURCE'))
|
|
</PRE
|
|
><P
|
|
>
|
|
Because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is usually invoked from the top-level
|
|
directory in which the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file lives,
|
|
the Python <CODE
|
|
CLASS="function"
|
|
>os.getcwd()</CODE
|
|
>
|
|
is often equivalent.
|
|
However, the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
<TT
|
|
CLASS="literal"
|
|
>-u</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>-U</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="literal"
|
|
>-D</TT
|
|
>
|
|
command-line options,
|
|
when invoked from a subdirectory,
|
|
will cause <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to change to the directory
|
|
in which the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file is found.
|
|
When those options are used,
|
|
<CODE
|
|
CLASS="function"
|
|
>GetLaunchDir</CODE
|
|
> will still return the path to the
|
|
user's invoking subdirectory,
|
|
allowing the <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> configuration
|
|
to still get at configuration (or other) files
|
|
from the originating directory.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="chapter"
|
|
><HR><H1
|
|
><A
|
|
NAME="chap-troubleshooting"
|
|
></A
|
|
>Chapter 29. Troubleshooting</H1
|
|
><P
|
|
>
|
|
The experience of configuring any
|
|
software build tool to build a large code base
|
|
usually, at some point,
|
|
involves trying to figure out why
|
|
the tool is behaving a certain way,
|
|
and how to get it to behave the way you want.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is no different.
|
|
This appendix contains a number of
|
|
different ways in which you can
|
|
get some additional insight into <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>' behavior.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Note that we're always interested in trying to
|
|
improve how you can troubleshoot configuration problems.
|
|
If you run into a problem that has
|
|
you scratching your head,
|
|
and which there just doesn't seem to be a good way to debug,
|
|
odds are pretty good that someone else will run into
|
|
the same problem, too.
|
|
If so, please let the SCons development team know
|
|
(preferably by filing a bug report
|
|
or feature request at our project pages at tigris.org)
|
|
so that we can use your feedback
|
|
to try to come up with a better way to help you,
|
|
and others, get the necessary insight into <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> behavior
|
|
to help identify and fix configuration issues.
|
|
|
|
</P
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4543"
|
|
>29.1. Why is That Target Being Rebuilt? the <TT
|
|
CLASS="literal"
|
|
>--debug=explain</TT
|
|
> Option</A
|
|
></H2
|
|
><P
|
|
>
|
|
Let's look at a simple example of
|
|
a misconfigured build
|
|
that causes a target to be rebuilt
|
|
every time <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is run:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Intentionally misspell the output file name in the
|
|
# command used to create the file:
|
|
Command('file.out', 'file.in', 'cp $SOURCE file.oout')
|
|
</PRE
|
|
><P
|
|
>
|
|
(Note to Windows users: The POSIX <SPAN
|
|
CLASS="application"
|
|
>cp</SPAN
|
|
> command
|
|
copies the first file named on the command line
|
|
to the second file.
|
|
In our example, it copies the <TT
|
|
CLASS="filename"
|
|
>file.in</TT
|
|
> file
|
|
to the <TT
|
|
CLASS="filename"
|
|
>file.out</TT
|
|
> file.)
|
|
|
|
</P
|
|
><P
|
|
>
|
|
Now if we run <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> multiple times on this example,
|
|
we see that it re-runs the <SPAN
|
|
CLASS="application"
|
|
>cp</SPAN
|
|
>
|
|
command every time:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cp file.in file.oout
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cp file.in file.oout
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cp file.in file.oout
|
|
</PRE
|
|
><P
|
|
>
|
|
In this example,
|
|
the underlying cause is obvious:
|
|
we've intentionally misspelled the output file name
|
|
in the <SPAN
|
|
CLASS="application"
|
|
>cp</SPAN
|
|
> command,
|
|
so the command doesn't actually
|
|
build the <TT
|
|
CLASS="filename"
|
|
>file.out</TT
|
|
> file that we've told <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to expect.
|
|
But if the problem weren't obvious,
|
|
it would be helpful
|
|
to specify the <TT
|
|
CLASS="literal"
|
|
>--debug=explain</TT
|
|
> option
|
|
on the command line
|
|
to have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> tell us very specifically
|
|
why it's decided to rebuild the target:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --debug=explain</KBD
|
|
>
|
|
scons: building `file.out' because it doesn't exist
|
|
cp file.in file.oout
|
|
</PRE
|
|
><P
|
|
>
|
|
If this had been a more complicated example
|
|
involving a lot of build output,
|
|
having <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> tell us that
|
|
it's trying to rebuild the target file
|
|
because it doesn't exist
|
|
would be an important clue
|
|
that something was wrong with
|
|
the command that we invoked to build it.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>--debug=explain</TT
|
|
> option also comes in handy
|
|
to help figure out what input file changed.
|
|
Given a simple configuration that builds
|
|
a program from three source files,
|
|
changing one of the source files
|
|
and rebuilding with the <TT
|
|
CLASS="literal"
|
|
>--debug=explain</TT
|
|
>
|
|
option shows very specifically
|
|
why <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> rebuilds the files that it does:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o file1.o -c file1.c
|
|
cc -o file2.o -c file2.c
|
|
cc -o file3.o -c file3.c
|
|
cc -o prog file1.o file2.o file3.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit file2.c</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF file2.c]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --debug=explain</KBD
|
|
>
|
|
scons: rebuilding `file2.o' because `file2.c' changed
|
|
cc -o file2.o -c file2.c
|
|
scons: rebuilding `prog' because `file2.o' changed
|
|
cc -o prog file1.o file2.o file3.o
|
|
</PRE
|
|
><P
|
|
>
|
|
This becomes even more helpful
|
|
in identifying when a file is rebuilt
|
|
due to a change in an implicit dependency,
|
|
such as an incuded <TT
|
|
CLASS="filename"
|
|
>.h</TT
|
|
> file.
|
|
If the <TT
|
|
CLASS="filename"
|
|
>file1.c</TT
|
|
>
|
|
and <TT
|
|
CLASS="filename"
|
|
>file3.c</TT
|
|
> files
|
|
in our example
|
|
both included a <TT
|
|
CLASS="filename"
|
|
>hello.h</TT
|
|
> file,
|
|
then changing that included file
|
|
and re-running <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> with the <TT
|
|
CLASS="literal"
|
|
>--debug=explain</TT
|
|
> option
|
|
will pinpoint that it's the change to the included file
|
|
that starts the chain of rebuilds:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
cc -o file1.o -c -I. file1.c
|
|
cc -o file2.o -c -I. file2.c
|
|
cc -o file3.o -c -I. file3.c
|
|
cc -o prog file1.o file2.o file3.o
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>edit hello.h</KBD
|
|
>
|
|
[CHANGE THE CONTENTS OF hello.h]
|
|
% <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --debug=explain</KBD
|
|
>
|
|
scons: rebuilding `file1.o' because `hello.h' changed
|
|
cc -o file1.o -c -I. file1.c
|
|
scons: rebuilding `file3.o' because `hello.h' changed
|
|
cc -o file3.o -c -I. file3.c
|
|
scons: rebuilding `prog' because:
|
|
`file1.o' changed
|
|
`file3.o' changed
|
|
cc -o prog file1.o file2.o file3.o
|
|
</PRE
|
|
><P
|
|
>
|
|
(Note that the <TT
|
|
CLASS="literal"
|
|
>--debug=explain</TT
|
|
> option will only tell you
|
|
why <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> decided to rebuild necessary targets.
|
|
It does not tell you what files it examined
|
|
when deciding <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
to rebuild a target file,
|
|
which is often a more valuable question to answer.)
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4593"
|
|
>29.2. What's in That Construction Environment? the <CODE
|
|
CLASS="function"
|
|
>Dump</CODE
|
|
> Method</A
|
|
></H2
|
|
><P
|
|
>
|
|
When you create a construction environment,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> populates it
|
|
with construction variables that are set up
|
|
for various compilers, linkers and utilities
|
|
that it finds on your system.
|
|
Although this is usually helpful and what you want,
|
|
it might be frustrating if <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
doesn't set certain variables that you
|
|
expect to be set.
|
|
In situations like this,
|
|
it's sometimes helpful to use the
|
|
construction environment <CODE
|
|
CLASS="function"
|
|
>Dump</CODE
|
|
> method
|
|
to print all or some of
|
|
the construction variables.
|
|
Note that the <CODE
|
|
CLASS="function"
|
|
>Dump</CODE
|
|
> method
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>returns</I
|
|
></SPAN
|
|
>
|
|
the representation of the variables
|
|
in the environment
|
|
for you to print (or otherwise manipulate):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
print env.Dump()
|
|
</PRE
|
|
><P
|
|
>
|
|
On a POSIX system with gcc installed,
|
|
this might generate:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
{ 'BUILDERS': {'_InternalInstall': <function InstallBuilderWrapper at 0x700000>, '_InternalInstallAs': <function InstallAsBuilderWrapper at 0x700000>},
|
|
'CONFIGUREDIR': '#/.sconf_temp',
|
|
'CONFIGURELOG': '#/config.log',
|
|
'CPPSUFFIXES': [ '.c',
|
|
'.C',
|
|
'.cxx',
|
|
'.cpp',
|
|
'.c++',
|
|
'.cc',
|
|
'.h',
|
|
'.H',
|
|
'.hxx',
|
|
'.hpp',
|
|
'.hh',
|
|
'.F',
|
|
'.fpp',
|
|
'.FPP',
|
|
'.m',
|
|
'.mm',
|
|
'.S',
|
|
'.spp',
|
|
'.SPP'],
|
|
'DSUFFIXES': ['.d'],
|
|
'Dir': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'Dirs': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'ENV': {'PATH': '/usr/local/bin:/opt/bin:/bin:/usr/bin'},
|
|
'ESCAPE': <function escape at 0x700000>,
|
|
'File': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'IDLSUFFIXES': ['.idl', '.IDL'],
|
|
'INSTALL': <function copyFunc at 0x700000>,
|
|
'LATEXSUFFIXES': ['.tex', '.ltx', '.latex'],
|
|
'LIBPREFIX': 'lib',
|
|
'LIBPREFIXES': ['$LIBPREFIX'],
|
|
'LIBSUFFIX': '.a',
|
|
'LIBSUFFIXES': ['$LIBSUFFIX', '$SHLIBSUFFIX'],
|
|
'MAXLINELENGTH': 128072,
|
|
'OBJPREFIX': '',
|
|
'OBJSUFFIX': '.o',
|
|
'PLATFORM': 'posix',
|
|
'PROGPREFIX': '',
|
|
'PROGSUFFIX': '',
|
|
'PSPAWN': <function piped_env_spawn at 0x700000>,
|
|
'RDirs': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'SCANNERS': [],
|
|
'SHELL': 'sh',
|
|
'SHLIBPREFIX': '$LIBPREFIX',
|
|
'SHLIBSUFFIX': '.so',
|
|
'SHOBJPREFIX': '$OBJPREFIX',
|
|
'SHOBJSUFFIX': '$OBJSUFFIX',
|
|
'SPAWN': <function spawnvpe_spawn at 0x700000>,
|
|
'TEMPFILE': <class SCons.Platform.TempFileMunge at 0x700000>,
|
|
'TEMPFILEPREFIX': '@',
|
|
'TOOLS': ['install', 'install'],
|
|
'_CPPDEFFLAGS': '${_defines(CPPDEFPREFIX, CPPDEFINES, CPPDEFSUFFIX, __env__)}',
|
|
'_CPPINCFLAGS': '$( ${_concat(INCPREFIX, CPPPATH, INCSUFFIX, __env__, RDirs, TARGET, SOURCE)} $)',
|
|
'_LIBDIRFLAGS': '$( ${_concat(LIBDIRPREFIX, LIBPATH, LIBDIRSUFFIX, __env__, RDirs, TARGET, SOURCE)} $)',
|
|
'_LIBFLAGS': '${_concat(LIBLINKPREFIX, LIBS, LIBLINKSUFFIX, __env__)}',
|
|
'__RPATH': '$_RPATH',
|
|
'_concat': <function _concat at 0x700000>,
|
|
'_defines': <function _defines at 0x700000>,
|
|
'_stripixes': <function _stripixes at 0x700000>}
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
scons: `.' is up to date.
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
On a Windows system with Visual C++
|
|
the output might look like:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
{ 'BUILDERS': {'_InternalInstall': <function InstallBuilderWrapper at 0x700000>, 'Object': <SCons.Builder.CompositeBuilder instance at 0x700000>, 'PCH': <SCons.Builder.BuilderBase instance at 0x700000>, 'RES': <SCons.Builder.BuilderBase instance at 0x700000>, 'SharedObject': <SCons.Builder.CompositeBuilder instance at 0x700000>, 'StaticObject': <SCons.Builder.CompositeBuilder instance at 0x700000>, '_InternalInstallAs': <function InstallAsBuilderWrapper at 0x700000>},
|
|
'CC': 'cl',
|
|
'CCCOM': <SCons.Action.FunctionAction instance at 0x700000>,
|
|
'CCCOMFLAGS': '$CPPFLAGS $_CPPDEFFLAGS $_CPPINCFLAGS /c $SOURCES /Fo$TARGET $CCPCHFLAGS $CCPDBFLAGS',
|
|
'CCFLAGS': ['/nologo'],
|
|
'CCPCHFLAGS': ['${(PCH and "/Yu%s /Fp%s"%(PCHSTOP or "",File(PCH))) or ""}'],
|
|
'CCPDBFLAGS': ['${(PDB and "/Z7") or ""}'],
|
|
'CFILESUFFIX': '.c',
|
|
'CFLAGS': [],
|
|
'CONFIGUREDIR': '#/.sconf_temp',
|
|
'CONFIGURELOG': '#/config.log',
|
|
'CPPDEFPREFIX': '/D',
|
|
'CPPDEFSUFFIX': '',
|
|
'CPPSUFFIXES': [ '.c',
|
|
'.C',
|
|
'.cxx',
|
|
'.cpp',
|
|
'.c++',
|
|
'.cc',
|
|
'.h',
|
|
'.H',
|
|
'.hxx',
|
|
'.hpp',
|
|
'.hh',
|
|
'.F',
|
|
'.fpp',
|
|
'.FPP',
|
|
'.m',
|
|
'.mm',
|
|
'.S',
|
|
'.spp',
|
|
'.SPP'],
|
|
'CXX': '$CC',
|
|
'CXXCOM': '$CXX $CXXFLAGS $CCCOMFLAGS',
|
|
'CXXFILESUFFIX': '.cc',
|
|
'CXXFLAGS': ['$CCFLAGS', '$(', '/TP', '$)'],
|
|
'DSUFFIXES': ['.d'],
|
|
'Dir': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'Dirs': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'ENV': { 'INCLUDE': 'C:\\Program Files\\Microsoft Visual Studio/VC98\\include',
|
|
'LIB': 'C:\\Program Files\\Microsoft Visual Studio/VC98\\lib',
|
|
'PATH': 'C:\\Program Files\\Microsoft Visual Studio\\Common\\tools\\WIN95;C:\\Program Files\\Microsoft Visual Studio\\Common\\MSDev98\\bin;C:\\Program Files\\Microsoft Visual Studio\\Common\\tools;C:\\Program Files\\Microsoft Visual Studio/VC98\\bin',
|
|
'PATHEXT': '.COM;.EXE;.BAT;.CMD',
|
|
'SystemRoot': 'C:/WINDOWS'},
|
|
'ESCAPE': <function escape at 0x700000>,
|
|
'File': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'IDLSUFFIXES': ['.idl', '.IDL'],
|
|
'INCPREFIX': '/I',
|
|
'INCSUFFIX': '',
|
|
'INSTALL': <function copyFunc at 0x700000>,
|
|
'LATEXSUFFIXES': ['.tex', '.ltx', '.latex'],
|
|
'LIBPREFIX': '',
|
|
'LIBPREFIXES': ['$LIBPREFIX'],
|
|
'LIBSUFFIX': '.lib',
|
|
'LIBSUFFIXES': ['$LIBSUFFIX'],
|
|
'MAXLINELENGTH': 2048,
|
|
'MSVS': {'VERSION': '6.0', 'VERSIONS': ['6.0']},
|
|
'MSVS_VERSION': '6.0',
|
|
'OBJPREFIX': '',
|
|
'OBJSUFFIX': '.obj',
|
|
'PCHCOM': '$CXX $CXXFLAGS $CPPFLAGS $_CPPDEFFLAGS $_CPPINCFLAGS /c $SOURCES /Fo${TARGETS[1]} /Yc$PCHSTOP /Fp${TARGETS[0]} $CCPDBFLAGS $PCHPDBFLAGS',
|
|
'PCHPDBFLAGS': ['${(PDB and "/Yd") or ""}'],
|
|
'PLATFORM': 'win32',
|
|
'PROGPREFIX': '',
|
|
'PROGSUFFIX': '.exe',
|
|
'PSPAWN': <function piped_spawn at 0x700000>,
|
|
'RC': 'rc',
|
|
'RCCOM': <SCons.Action.FunctionAction instance at 0x700000>,
|
|
'RCFLAGS': [],
|
|
'RDirs': <SCons.Defaults.Variable_Method_Caller instance at 0x700000>,
|
|
'SCANNERS': [],
|
|
'SHCC': '$CC',
|
|
'SHCCCOM': <SCons.Action.FunctionAction instance at 0x700000>,
|
|
'SHCCFLAGS': ['$CCFLAGS'],
|
|
'SHCFLAGS': ['$CFLAGS'],
|
|
'SHCXX': '$CXX',
|
|
'SHCXXCOM': '$SHCXX $SHCXXFLAGS $CCCOMFLAGS',
|
|
'SHCXXFLAGS': ['$CXXFLAGS'],
|
|
'SHELL': None,
|
|
'SHLIBPREFIX': '',
|
|
'SHLIBSUFFIX': '.dll',
|
|
'SHOBJPREFIX': '$OBJPREFIX',
|
|
'SHOBJSUFFIX': '$OBJSUFFIX',
|
|
'SPAWN': <function spawn at 0x700000>,
|
|
'STATIC_AND_SHARED_OBJECTS_ARE_THE_SAME': 1,
|
|
'TEMPFILE': <class SCons.Platform.TempFileMunge at 0x700000>,
|
|
'TEMPFILEPREFIX': '@',
|
|
'TOOLS': ['msvc', 'install', 'install'],
|
|
'_CPPDEFFLAGS': '${_defines(CPPDEFPREFIX, CPPDEFINES, CPPDEFSUFFIX, __env__)}',
|
|
'_CPPINCFLAGS': '$( ${_concat(INCPREFIX, CPPPATH, INCSUFFIX, __env__, RDirs, TARGET, SOURCE)} $)',
|
|
'_LIBDIRFLAGS': '$( ${_concat(LIBDIRPREFIX, LIBPATH, LIBDIRSUFFIX, __env__, RDirs, TARGET, SOURCE)} $)',
|
|
'_LIBFLAGS': '${_concat(LIBLINKPREFIX, LIBS, LIBLINKSUFFIX, __env__)}',
|
|
'_concat': <function _concat at 0x700000>,
|
|
'_defines': <function _defines at 0x700000>,
|
|
'_stripixes': <function _stripixes at 0x700000>}
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
scons: `.' is up to date.
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
The construction environments in these examples have
|
|
actually been restricted to just gcc and Visual C++,
|
|
respectively.
|
|
In a real-life situation,
|
|
the construction environments will
|
|
likely contain a great many more variables.
|
|
Also note that we've massaged the example output above
|
|
to make the memory address of all objects a constant 0x700000.
|
|
In reality, you would see a different hexadecimal
|
|
number for each object.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
To make it easier to see just what you're
|
|
interested in,
|
|
the <CODE
|
|
CLASS="function"
|
|
>Dump</CODE
|
|
> method allows you to
|
|
specify a specific constrcution variable
|
|
that you want to disply.
|
|
For example,
|
|
it's not unusual to want to verify
|
|
the external environment used to execute build commands,
|
|
to make sure that the PATH and other
|
|
environment variables are set up the way they should be.
|
|
You can do this as follows:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
print env.Dump('ENV')
|
|
</PRE
|
|
><P
|
|
>
|
|
Which might display the following when executed on a POSIX system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
{'PATH': '/usr/local/bin:/opt/bin:/bin:/usr/bin'}
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
scons: `.' is up to date.
|
|
scons: done building targets.
|
|
</PRE
|
|
><P
|
|
>
|
|
And the following when executed on a Windows system:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> C:\><KBD
|
|
CLASS="userinput"
|
|
>scons</KBD
|
|
>
|
|
scons: Reading SConscript files ...
|
|
{ 'INCLUDE': 'C:\\Program Files\\Microsoft Visual Studio/VC98\\include',
|
|
'LIB': 'C:\\Program Files\\Microsoft Visual Studio/VC98\\lib',
|
|
'PATH': 'C:\\Program Files\\Microsoft Visual Studio\\Common\\tools\\WIN95;C:\\Program Files\\Microsoft Visual Studio\\Common\\MSDev98\\bin;C:\\Program Files\\Microsoft Visual Studio\\Common\\tools;C:\\Program Files\\Microsoft Visual Studio/VC98\\bin',
|
|
'PATHEXT': '.COM;.EXE;.BAT;.CMD',
|
|
'SystemRoot': 'C:/WINDOWS'}
|
|
scons: done reading SConscript files.
|
|
scons: Building targets ...
|
|
scons: `.' is up to date.
|
|
scons: done building targets.
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4619"
|
|
>29.3. What Dependencies Does <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Know About? the <TT
|
|
CLASS="literal"
|
|
>--tree</TT
|
|
> Option</A
|
|
></H2
|
|
><P
|
|
>
|
|
Sometimes the best way to try to figure out what
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is doing is simply to take a look at the
|
|
dependency graph that it constructs
|
|
based on your <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
> files.
|
|
The <TT
|
|
CLASS="literal"
|
|
>--tree</TT
|
|
> option
|
|
will display all or part of the
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> dependency graph in an
|
|
"ASCII art" graphical format
|
|
that shows the dependency hierarchy.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, given the following input <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CPPPATH = ['.'])
|
|
env.Program('prog', ['f1.c', 'f2.c', 'f3.c'])
|
|
</PRE
|
|
><P
|
|
>
|
|
Running <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> with the <TT
|
|
CLASS="literal"
|
|
>--tree=all</TT
|
|
>
|
|
option yields:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=all</KBD
|
|
>
|
|
cc -o f1.o -c -I. f1.c
|
|
cc -o f2.o -c -I. f2.c
|
|
cc -o f3.o -c -I. f3.c
|
|
cc -o prog f1.o f2.o f3.o
|
|
+-.
|
|
+-SConstruct
|
|
+-f1.c
|
|
+-f1.o
|
|
| +-f1.c
|
|
| +-inc.h
|
|
+-f2.c
|
|
+-f2.o
|
|
| +-f2.c
|
|
| +-inc.h
|
|
+-f3.c
|
|
+-f3.o
|
|
| +-f3.c
|
|
| +-inc.h
|
|
+-inc.h
|
|
+-prog
|
|
+-f1.o
|
|
| +-f1.c
|
|
| +-inc.h
|
|
+-f2.o
|
|
| +-f2.c
|
|
| +-inc.h
|
|
+-f3.o
|
|
+-f3.c
|
|
+-inc.h
|
|
</PRE
|
|
><P
|
|
>
|
|
The tree will also be printed when the
|
|
<TT
|
|
CLASS="literal"
|
|
>-n</TT
|
|
> (no execute) option is used,
|
|
which allows you to examine the dependency graph
|
|
for a configuration without actually
|
|
rebuilding anything in the tree.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>--tree</TT
|
|
> option only prints
|
|
the dependency graph for the specified targets
|
|
(or the default target(s) if none are specified on the command line).
|
|
So if you specify a target like <TT
|
|
CLASS="filename"
|
|
>f2.o</TT
|
|
>
|
|
on the command line,
|
|
the <TT
|
|
CLASS="literal"
|
|
>--tree</TT
|
|
> option will only
|
|
print the dependency graph for that file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=all f2.o</KBD
|
|
>
|
|
cc -o f2.o -c -I. f2.c
|
|
+-f2.o
|
|
+-f2.c
|
|
+-inc.h
|
|
</PRE
|
|
><P
|
|
>
|
|
This is, of course, useful for
|
|
restricting the output from a very large
|
|
build configuration to just a
|
|
portion in which you're interested.
|
|
Multiple targets are fine,
|
|
in which case a tree will be printed
|
|
for each specified target:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=all f1.o f3.o</KBD
|
|
>
|
|
cc -o f1.o -c -I. f1.c
|
|
+-f1.o
|
|
+-f1.c
|
|
+-inc.h
|
|
cc -o f3.o -c -I. f3.c
|
|
+-f3.o
|
|
+-f3.c
|
|
+-inc.h
|
|
</PRE
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>status</TT
|
|
> argument may be used
|
|
to tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> to print status information about
|
|
each file in the dependency graph:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=status</KBD
|
|
>
|
|
cc -o f1.o -c -I. f1.c
|
|
cc -o f2.o -c -I. f2.c
|
|
cc -o f3.o -c -I. f3.c
|
|
cc -o prog f1.o f2.o f3.o
|
|
E = exists
|
|
R = exists in repository only
|
|
b = implicit builder
|
|
B = explicit builder
|
|
S = side effect
|
|
P = precious
|
|
A = always build
|
|
C = current
|
|
N = no clean
|
|
H = no cache
|
|
|
|
[E b ]+-.
|
|
[E C ] +-SConstruct
|
|
[E C ] +-f1.c
|
|
[E B C ] +-f1.o
|
|
[E C ] | +-f1.c
|
|
[E C ] | +-inc.h
|
|
[E C ] +-f2.c
|
|
[E B C ] +-f2.o
|
|
[E C ] | +-f2.c
|
|
[E C ] | +-inc.h
|
|
[E C ] +-f3.c
|
|
[E B C ] +-f3.o
|
|
[E C ] | +-f3.c
|
|
[E C ] | +-inc.h
|
|
[E C ] +-inc.h
|
|
[E B C ] +-prog
|
|
[E B C ] +-f1.o
|
|
[E C ] | +-f1.c
|
|
[E C ] | +-inc.h
|
|
[E B C ] +-f2.o
|
|
[E C ] | +-f2.c
|
|
[E C ] | +-inc.h
|
|
[E B C ] +-f3.o
|
|
[E C ] +-f3.c
|
|
[E C ] +-inc.h
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that <TT
|
|
CLASS="literal"
|
|
>--tree=all,status</TT
|
|
> is equivalent;
|
|
the <TT
|
|
CLASS="literal"
|
|
>all</TT
|
|
>
|
|
is assumed if only <TT
|
|
CLASS="literal"
|
|
>status</TT
|
|
> is present.
|
|
As an alternative to <TT
|
|
CLASS="literal"
|
|
>all</TT
|
|
>,
|
|
you can specify <TT
|
|
CLASS="literal"
|
|
>--tree=derived</TT
|
|
>
|
|
to have <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> only print derived targets
|
|
in the tree output,
|
|
skipping source files
|
|
(like <TT
|
|
CLASS="filename"
|
|
>.c</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>.h</TT
|
|
> files):
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=derived</KBD
|
|
>
|
|
cc -o f1.o -c -I. f1.c
|
|
cc -o f2.o -c -I. f2.c
|
|
cc -o f3.o -c -I. f3.c
|
|
cc -o prog f1.o f2.o f3.o
|
|
+-.
|
|
+-f1.o
|
|
+-f2.o
|
|
+-f3.o
|
|
+-prog
|
|
+-f1.o
|
|
+-f2.o
|
|
+-f3.o
|
|
</PRE
|
|
><P
|
|
>
|
|
You can use the <TT
|
|
CLASS="literal"
|
|
>status</TT
|
|
>
|
|
modifier with <TT
|
|
CLASS="literal"
|
|
>derived</TT
|
|
> as well:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=derived,status</KBD
|
|
>
|
|
cc -o f1.o -c -I. f1.c
|
|
cc -o f2.o -c -I. f2.c
|
|
cc -o f3.o -c -I. f3.c
|
|
cc -o prog f1.o f2.o f3.o
|
|
E = exists
|
|
R = exists in repository only
|
|
b = implicit builder
|
|
B = explicit builder
|
|
S = side effect
|
|
P = precious
|
|
A = always build
|
|
C = current
|
|
N = no clean
|
|
H = no cache
|
|
|
|
[E b ]+-.
|
|
[E B C ] +-f1.o
|
|
[E B C ] +-f2.o
|
|
[E B C ] +-f3.o
|
|
[E B C ] +-prog
|
|
[E B C ] +-f1.o
|
|
[E B C ] +-f2.o
|
|
[E B C ] +-f3.o
|
|
</PRE
|
|
><P
|
|
>
|
|
Note that the order of the <TT
|
|
CLASS="literal"
|
|
>--tree=</TT
|
|
>
|
|
arguments doesn't matter;
|
|
<TT
|
|
CLASS="literal"
|
|
>--tree=status,derived</TT
|
|
> is
|
|
completely equivalent.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The default behavior of the <TT
|
|
CLASS="literal"
|
|
>--tree</TT
|
|
> option
|
|
is to repeat all of the dependencies each time the library dependency
|
|
(or any other dependency file) is encountered in the tree.
|
|
If certain target files share other target files,
|
|
such as two programs that use the same library:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CPPPATH = ['.'],
|
|
LIBS = ['foo'],
|
|
LIBPATH = ['.'])
|
|
env.Library('foo', ['f1.c', 'f2.c', 'f3.c'])
|
|
env.Program('prog1.c')
|
|
env.Program('prog2.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Then there can be a <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>lot</I
|
|
></SPAN
|
|
> of repetition in the
|
|
<TT
|
|
CLASS="literal"
|
|
>--tree=</TT
|
|
> output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=all</KBD
|
|
>
|
|
cc -o f1.o -c -I. f1.c
|
|
cc -o f2.o -c -I. f2.c
|
|
cc -o f3.o -c -I. f3.c
|
|
ar rc libfoo.a f1.o f2.o f3.o
|
|
ranlib libfoo.a
|
|
cc -o prog1.o -c -I. prog1.c
|
|
cc -o prog1 prog1.o -L. -lfoo
|
|
cc -o prog2.o -c -I. prog2.c
|
|
cc -o prog2 prog2.o -L. -lfoo
|
|
+-.
|
|
+-SConstruct
|
|
+-f1.c
|
|
+-f1.o
|
|
| +-f1.c
|
|
| +-inc.h
|
|
+-f2.c
|
|
+-f2.o
|
|
| +-f2.c
|
|
| +-inc.h
|
|
+-f3.c
|
|
+-f3.o
|
|
| +-f3.c
|
|
| +-inc.h
|
|
+-inc.h
|
|
+-libfoo.a
|
|
| +-f1.o
|
|
| | +-f1.c
|
|
| | +-inc.h
|
|
| +-f2.o
|
|
| | +-f2.c
|
|
| | +-inc.h
|
|
| +-f3.o
|
|
| +-f3.c
|
|
| +-inc.h
|
|
+-prog1
|
|
| +-prog1.o
|
|
| | +-prog1.c
|
|
| | +-inc.h
|
|
| +-libfoo.a
|
|
| +-f1.o
|
|
| | +-f1.c
|
|
| | +-inc.h
|
|
| +-f2.o
|
|
| | +-f2.c
|
|
| | +-inc.h
|
|
| +-f3.o
|
|
| +-f3.c
|
|
| +-inc.h
|
|
+-prog1.c
|
|
+-prog1.o
|
|
| +-prog1.c
|
|
| +-inc.h
|
|
+-prog2
|
|
| +-prog2.o
|
|
| | +-prog2.c
|
|
| | +-inc.h
|
|
| +-libfoo.a
|
|
| +-f1.o
|
|
| | +-f1.c
|
|
| | +-inc.h
|
|
| +-f2.o
|
|
| | +-f2.c
|
|
| | +-inc.h
|
|
| +-f3.o
|
|
| +-f3.c
|
|
| +-inc.h
|
|
+-prog2.c
|
|
+-prog2.o
|
|
+-prog2.c
|
|
+-inc.h
|
|
</PRE
|
|
><P
|
|
>
|
|
In a large configuration with many internal libraries
|
|
and include files,
|
|
this can very quickly lead to huge output trees.
|
|
To help make this more manageable,
|
|
a <TT
|
|
CLASS="literal"
|
|
>prune</TT
|
|
> modifier may
|
|
be added to the option list,
|
|
in which case <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
will print the name of a target that has
|
|
already been visited during the tree-printing
|
|
in <TT
|
|
CLASS="literal"
|
|
>[square brackets]</TT
|
|
>
|
|
as an indication that the dependencies
|
|
of the target file may be found
|
|
by looking farther up the tree:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --tree=prune</KBD
|
|
>
|
|
cc -o f1.o -c -I. f1.c
|
|
cc -o f2.o -c -I. f2.c
|
|
cc -o f3.o -c -I. f3.c
|
|
ar rc libfoo.a f1.o f2.o f3.o
|
|
ranlib libfoo.a
|
|
cc -o prog1.o -c -I. prog1.c
|
|
cc -o prog1 prog1.o -L. -lfoo
|
|
cc -o prog2.o -c -I. prog2.c
|
|
cc -o prog2 prog2.o -L. -lfoo
|
|
+-.
|
|
+-SConstruct
|
|
+-f1.c
|
|
+-f1.o
|
|
| +-f1.c
|
|
| +-inc.h
|
|
+-f2.c
|
|
+-f2.o
|
|
| +-f2.c
|
|
| +-inc.h
|
|
+-f3.c
|
|
+-f3.o
|
|
| +-f3.c
|
|
| +-inc.h
|
|
+-inc.h
|
|
+-libfoo.a
|
|
| +-[f1.o]
|
|
| +-[f2.o]
|
|
| +-[f3.o]
|
|
+-prog1
|
|
| +-prog1.o
|
|
| | +-prog1.c
|
|
| | +-inc.h
|
|
| +-[libfoo.a]
|
|
+-prog1.c
|
|
+-[prog1.o]
|
|
+-prog2
|
|
| +-prog2.o
|
|
| | +-prog2.c
|
|
| | +-inc.h
|
|
| +-[libfoo.a]
|
|
+-prog2.c
|
|
+-[prog2.o]
|
|
</PRE
|
|
><P
|
|
>
|
|
Like the <TT
|
|
CLASS="literal"
|
|
>status</TT
|
|
> keyword,
|
|
the <TT
|
|
CLASS="literal"
|
|
>prune</TT
|
|
> argument by itself
|
|
is equivalent to <TT
|
|
CLASS="literal"
|
|
>--tree=all,prune</TT
|
|
>.
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4689"
|
|
>29.4. How is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Constructing the Command Lines It Executes? the <TT
|
|
CLASS="literal"
|
|
>--debug=presub</TT
|
|
> Option</A
|
|
></H2
|
|
><P
|
|
>
|
|
Sometimes it's useful to look at the
|
|
pre-substitution string
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> uses to generate
|
|
the command lines it executes.
|
|
This can be done with the <TT
|
|
CLASS="literal"
|
|
>--debug=presub</TT
|
|
> option:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --debug=presub</KBD
|
|
>
|
|
Building prog.o with action:
|
|
$CC -o $TARGET -c $CFLAGS $CCFLAGS $_CCOMCOM $SOURCES
|
|
cc -o prog.o -c -I. prog.c
|
|
Building prog with action:
|
|
$SMART_LINKCOM
|
|
cc -o prog prog.o
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4698"
|
|
>29.5. Where is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Searching for Libraries? the <TT
|
|
CLASS="literal"
|
|
>--debug=findlibs</TT
|
|
> Option</A
|
|
></H2
|
|
><P
|
|
>
|
|
To get some insight into what library names
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> is searching for,
|
|
and in which directories it is searching,
|
|
Use the <TT
|
|
CLASS="literal"
|
|
>--debug=findlibs</TT
|
|
> option.
|
|
Given the following input <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(LIBPATH = ['libs1', 'libs2'])
|
|
env.Program('prog.c', LIBS=['foo', 'bar'])
|
|
</PRE
|
|
><P
|
|
>
|
|
And the libraries <TT
|
|
CLASS="filename"
|
|
>libfoo.a</TT
|
|
>
|
|
and <TT
|
|
CLASS="filename"
|
|
>libbar.a</TT
|
|
>
|
|
in <TT
|
|
CLASS="filename"
|
|
>libs1</TT
|
|
> and <TT
|
|
CLASS="filename"
|
|
>libs2</TT
|
|
>,
|
|
respectively,
|
|
use of the <TT
|
|
CLASS="literal"
|
|
>--debug=findlibs</TT
|
|
> option yields:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --debug=findlibs</KBD
|
|
>
|
|
findlibs: looking for 'libfoo.a' in 'libs1' ...
|
|
findlibs: ... FOUND 'libfoo.a' in 'libs1'
|
|
findlibs: looking for 'libfoo.so' in 'libs1' ...
|
|
findlibs: looking for 'libfoo.so' in 'libs2' ...
|
|
findlibs: looking for 'libbar.a' in 'libs1' ...
|
|
findlibs: looking for 'libbar.a' in 'libs2' ...
|
|
findlibs: ... FOUND 'libbar.a' in 'libs2'
|
|
findlibs: looking for 'libbar.so' in 'libs1' ...
|
|
findlibs: looking for 'libbar.so' in 'libs2' ...
|
|
cc -o prog.o -c prog.c
|
|
cc -o prog prog.o -Llibs1 -Llibs2 -lfoo -lbar
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4715"
|
|
>29.6. Where is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Blowing Up? the <TT
|
|
CLASS="literal"
|
|
>--debug=stacktrace</TT
|
|
> Option</A
|
|
></H2
|
|
><P
|
|
>
|
|
In general, <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> tries to keep its error
|
|
messages short and informative.
|
|
That means we usually try to avoid showing
|
|
the stack traces that are familiar
|
|
to experienced Python programmers,
|
|
since they usually contain much more
|
|
information than is useful to most people.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
For example, the following <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Program('prog.c')
|
|
</PRE
|
|
><P
|
|
>
|
|
Generates the following error if the
|
|
<TT
|
|
CLASS="filename"
|
|
>prog.c</TT
|
|
> file
|
|
does not exist:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q</KBD
|
|
>
|
|
scons: *** Source `prog.c' not found, needed by target `prog.o'. Stop.
|
|
</PRE
|
|
><P
|
|
>
|
|
In this case,
|
|
the error is pretty obvious.
|
|
But if it weren't,
|
|
and you wanted to try to get more information
|
|
about the error,
|
|
the <TT
|
|
CLASS="literal"
|
|
>--debug=stacktrace</TT
|
|
> option
|
|
would show you exactly where in the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> source code
|
|
the problem occurs:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --debug=stacktrace</KBD
|
|
>
|
|
scons: *** Source `prog.c' not found, needed by target `prog.o'. Stop.
|
|
scons: internal stack trace:
|
|
File "bootstrap/src/engine/SCons/Job.py", line 198, in start
|
|
File "bootstrap/src/engine/SCons/Script/Main.py", line 169, in prepare
|
|
File "bootstrap/src/engine/SCons/Taskmaster.py", line 184, in prepare
|
|
File "bootstrap/src/engine/SCons/Executor.py", line 171, in prepare
|
|
</PRE
|
|
><P
|
|
>
|
|
Of course, if you do need to dive into the <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> source code,
|
|
we'd like to know if, or how,
|
|
the error messages or troubleshooting options
|
|
could have been improved to avoid that.
|
|
Not everyone has the necessary time or
|
|
Python skill to dive into the source code,
|
|
and we'd like to improve <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
>
|
|
for those people as well...
|
|
|
|
</P
|
|
></DIV
|
|
><DIV
|
|
CLASS="section"
|
|
><HR><H2
|
|
CLASS="section"
|
|
><A
|
|
NAME="AEN4736"
|
|
>29.7. How is <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> Making Its Decisions? the <TT
|
|
CLASS="literal"
|
|
>--taskmastertrace</TT
|
|
> Option</A
|
|
></H2
|
|
><P
|
|
>
|
|
The internal <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> subsystem that handles walking
|
|
the dependency graph
|
|
and controls the decision-making about what to rebuild
|
|
is the <TT
|
|
CLASS="literal"
|
|
>Taskmaster</TT
|
|
>.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> supports a <TT
|
|
CLASS="literal"
|
|
>--taskmastertrace</TT
|
|
>
|
|
option that tells the Taskmaster to print
|
|
information about the children (dependencies)
|
|
of the various Nodes on its walk down the graph,
|
|
which specific dependent Nodes are being evaluated,
|
|
and in what order.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>--taskmastertrace</TT
|
|
> option
|
|
takes as an argument the name of a file in
|
|
which to put the trace output,
|
|
with <TT
|
|
CLASS="filename"
|
|
>-</TT
|
|
> (a single hyphen)
|
|
indicating that the trace messages
|
|
should be printed to the standard output:
|
|
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CPPPATH = ['.'])
|
|
env.Program('prog.c')
|
|
</PRE
|
|
><PRE
|
|
CLASS="screen"
|
|
> % <KBD
|
|
CLASS="userinput"
|
|
>scons -Q --taskmastertrace=- prog</KBD
|
|
>
|
|
|
|
Taskmaster: Looking for a node to evaluate
|
|
Taskmaster: Considering node <no_state 0 'prog'> and its children:
|
|
Taskmaster: <no_state 0 'prog.o'>
|
|
Taskmaster: adjusting ref count: <pending 1 'prog'>
|
|
Taskmaster: Considering node <no_state 0 'prog.o'> and its children:
|
|
Taskmaster: <no_state 0 'prog.c'>
|
|
Taskmaster: <no_state 0 'inc.h'>
|
|
Taskmaster: adjusting ref count: <pending 1 'prog.o'>
|
|
Taskmaster: adjusting ref count: <pending 2 'prog.o'>
|
|
Taskmaster: Considering node <no_state 0 'prog.c'> and its children:
|
|
Taskmaster: Evaluating <pending 0 'prog.c'>
|
|
|
|
Taskmaster: Looking for a node to evaluate
|
|
Taskmaster: Considering node <no_state 0 'inc.h'> and its children:
|
|
Taskmaster: Evaluating <pending 0 'inc.h'>
|
|
|
|
Taskmaster: Looking for a node to evaluate
|
|
Taskmaster: Considering node <pending 0 'prog.o'> and its children:
|
|
Taskmaster: <up_to_date 0 'prog.c'>
|
|
Taskmaster: <up_to_date 0 'inc.h'>
|
|
Taskmaster: Evaluating <pending 0 'prog.o'>
|
|
cc -o prog.o -c -I. prog.c
|
|
|
|
Taskmaster: Looking for a node to evaluate
|
|
Taskmaster: Considering node <pending 0 'prog'> and its children:
|
|
Taskmaster: <executed 0 'prog.o'>
|
|
Taskmaster: Evaluating <pending 0 'prog'>
|
|
cc -o prog prog.o
|
|
|
|
Taskmaster: Looking for a node to evaluate
|
|
Taskmaster: No candidate anymore.
|
|
</PRE
|
|
><P
|
|
>
|
|
The <TT
|
|
CLASS="literal"
|
|
>--taskmastertrace</TT
|
|
> option
|
|
doesn't provide information about the actual
|
|
calculations involved in deciding if a file is up-to-date,
|
|
but it does show all of the dependencies
|
|
it knows about for each Node,
|
|
and the order in which those dependencies are evaluated.
|
|
This can be useful as an alternate way to determine
|
|
whether or not your <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> configuration,
|
|
or the implicit dependency scan,
|
|
has actually identified all the correct dependencies
|
|
you want it to.
|
|
|
|
</P
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="appendix"
|
|
><HR><H1
|
|
><A
|
|
NAME="app-variables"
|
|
></A
|
|
>Appendix A. Construction Variables</H1
|
|
><P
|
|
>
|
|
This appendix contains descriptions of all of the
|
|
construction variables that are <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>potentially</I
|
|
></SPAN
|
|
>
|
|
available "out of the box" in this version of SCons.
|
|
Whether or not setting a construction variable
|
|
in a construction environment
|
|
will actually have an effect depends on
|
|
whether any of the Tools and/or Builders
|
|
that use the variable have been
|
|
included in the construction environment.
|
|
|
|
</P
|
|
><P
|
|
>
|
|
In this appendix, we have
|
|
appended the initial <CODE
|
|
CLASS="envar"
|
|
>$</CODE
|
|
>
|
|
(dollar sign) to the beginning of each
|
|
variable name when it appears in the text,
|
|
but left off the dollar sign
|
|
in the left-hand column
|
|
where the name appears for each entry.
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
><A
|
|
NAME="cv-AR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>AR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The static library archiver.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ARCHITECTURE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ARCHITECTURE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specifies the system architecture for which
|
|
the package is being built.
|
|
The default is the system architecture
|
|
of the machine on which SCons is running.
|
|
This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Architecture:</TT
|
|
>
|
|
field in an Ipkg
|
|
<TT
|
|
CLASS="filename"
|
|
>control</TT
|
|
> file,
|
|
and as part of the name of a generated RPM file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ARCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ARCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to generate a static library from object files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ARCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ARCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when an object file
|
|
is generated from an assembly-language source file.
|
|
If this is not set, then <A
|
|
HREF="#cv-ARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(ARCOMSTR = "Archiving $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ARFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ARFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the static library archiver.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-AS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>AS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The assembler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ASCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ASCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to generate an object file
|
|
from an assembly-language source file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ASCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ASCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when an object file
|
|
is generated from an assembly-language source file.
|
|
If this is not set, then <A
|
|
HREF="#cv-ASCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(ASCOMSTR = "Assembling $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ASFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ASFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the assembler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ASPPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ASPPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to assemble an assembly-language
|
|
source file into an object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified
|
|
in the <A
|
|
HREF="#cv-ASFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASFLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ASPPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ASPPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when an object file
|
|
is generated from an assembly-language source file
|
|
after first running the file through the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-ASPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(ASPPCOMSTR = "Assembling $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ASPPFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ASPPFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options when an assembling an assembly-language
|
|
source file into an object file
|
|
after first running the file through the C preprocessor.
|
|
The default is to use the value of <A
|
|
HREF="#cv-ASFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BIBTEX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BIBTEX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The bibliography generator for the TeX formatter and typesetter and the
|
|
LaTeX structured formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BIBTEXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BIBTEXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the bibliography generator for the
|
|
TeX formatter and typesetter and the LaTeX structured formatter and
|
|
typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BIBTEXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BIBTEXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when generating a bibliography
|
|
for TeX or LaTeX.
|
|
If this is not set, then <A
|
|
HREF="#cv-BIBTEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BIBTEXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(BIBTEXCOMSTR = "Generating bibliography $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BIBTEXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BIBTEXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the bibliography generator for the TeX formatter
|
|
and typesetter and the LaTeX structured formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BITKEEPER"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BITKEEPER</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The BitKeeper executable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BITKEEPERCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BITKEEPERCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line for
|
|
fetching source files using BitKeeper.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BITKEEPERCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BITKEEPERCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when fetching
|
|
a source file using BitKeeper.
|
|
If this is not set, then <A
|
|
HREF="#cv-BITKEEPERCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BITKEEPERCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BITKEEPERGET"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BITKEEPERGET</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command (<A
|
|
HREF="#cv-BITKEEPER"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BITKEEPER</CODE
|
|
></A
|
|
>) and subcommand
|
|
for fetching source files using BitKeeper.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BITKEEPERGETFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BITKEEPERGETFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the BitKeeper
|
|
<B
|
|
CLASS="command"
|
|
>get</B
|
|
>
|
|
subcommand.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-BUILDERS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>BUILDERS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A dictionary mapping the names of the builders
|
|
available through this environment
|
|
to underlying Builder objects.
|
|
Builders named
|
|
Alias, CFile, CXXFile, DVI, Library, Object, PDF, PostScript, and Program
|
|
are available by default.
|
|
If you initialize this variable when an
|
|
Environment is created:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(BUILDERS = {'NewBuilder' : foo})
|
|
</PRE
|
|
><P
|
|
> the default Builders will no longer be available.
|
|
To use a new Builder object in addition to the default Builders,
|
|
add your new Builder object like this:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env.Append(BUILDERS = {'NewBuilder' : foo})
|
|
</PRE
|
|
><P
|
|
> or this:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env['BUILDERS]['NewBuilder'] = foo
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The C compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CCCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CCCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a C source file to a (static) object
|
|
file. Any options specified in the <A
|
|
HREF="#cv-CFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables are included on this command
|
|
line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CCCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CCCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a C source file
|
|
is compiled to a (static) object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCCOMSTR = "Compiling static object $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options that are passed to the C and C++ compilers.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CCPCHFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CCPCHFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options added to the compiler command line
|
|
to support building with precompiled headers.
|
|
The default value expands expands to the appropriate
|
|
Microsoft Visual C++ command-line options
|
|
when the <A
|
|
HREF="#cv-PCH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PCH</CODE
|
|
></A
|
|
> construction variable is set.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CCPDBFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CCPDBFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options added to the compiler command line
|
|
to support storing debugging information in a
|
|
Microsoft Visual C++ PDB file.
|
|
The default value expands expands to appropriate
|
|
Microsoft Visual C++ command-line options
|
|
when the <A
|
|
HREF="#cv-PDB"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDB</CODE
|
|
></A
|
|
> construction variable is set.</P
|
|
><P
|
|
>The Visual C++ compiler option that SCons uses by default
|
|
to generate PDB information is <CODE
|
|
CLASS="option"
|
|
>/Z7</CODE
|
|
>.
|
|
This works correctly with parallel (<CODE
|
|
CLASS="option"
|
|
>-j</CODE
|
|
>) builds
|
|
because it embeds the debug information in the intermediate object files,
|
|
as opposed to sharing a single PDB file between multiple object files.
|
|
This is also the only way to get debug information
|
|
embedded into a static library.
|
|
Using the <CODE
|
|
CLASS="option"
|
|
>/Zi</CODE
|
|
> instead may yield improved
|
|
link-time performance,
|
|
although parallel builds will no longer work.</P
|
|
><P
|
|
>You can generate PDB files with the <CODE
|
|
CLASS="option"
|
|
>/Zi</CODE
|
|
>
|
|
switch by overriding the default <A
|
|
HREF="#cv-CCPDBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCPDBFLAGS</CODE
|
|
></A
|
|
> variable as follows:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['CCPDBFLAGS'] = ['${(PDB and "/Zi /Fd%s" % File(PDB)) or ""}']
|
|
</PRE
|
|
><P
|
|
> An alternative would be to use the <CODE
|
|
CLASS="option"
|
|
>/Zi</CODE
|
|
>
|
|
to put the debugging information in a separate <TT
|
|
CLASS="filename"
|
|
>.pdb</TT
|
|
>
|
|
file for each object file by overriding
|
|
the <A
|
|
HREF="#cv-CCPDBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCPDBFLAGS</CODE
|
|
></A
|
|
> variable as follows:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['CCPDBFLAGS'] = '/Zi /Fd${TARGET}.pdb'
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CCVERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CCVERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The version number of the C compiler.
|
|
This may or may not be set,
|
|
depending on the specific C compiler being used.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CFILESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CFILESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix for C source files.
|
|
This is used by the internal CFile builder
|
|
when generating C files from Lex (.l) or YACC (.y) input files.
|
|
The default suffix, of course, is
|
|
<TT
|
|
CLASS="filename"
|
|
>.c</TT
|
|
>
|
|
(lower case).
|
|
On case-insensitive systems (like Windows),
|
|
SCons also treats
|
|
<TT
|
|
CLASS="filename"
|
|
>.C</TT
|
|
>
|
|
(upper case) files
|
|
as C files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options that are passed to the C compiler (C only; not C++).
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CHANGE_SPECFILE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CHANGE_SPECFILE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A hook for modifying the file that controls the packaging build
|
|
(the <TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> for RPM,
|
|
the <TT
|
|
CLASS="filename"
|
|
>control</TT
|
|
> for Ipkg,
|
|
the <TT
|
|
CLASS="filename"
|
|
>.wxs</TT
|
|
> for MSI).
|
|
If set, the function will be called
|
|
after the SCons template for the file has been written.
|
|
XXX
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CHANGELOG"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CHANGELOG</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The name of a file containing the change log text
|
|
to be included in the package.
|
|
This is included as the
|
|
<TT
|
|
CLASS="literal"
|
|
>%changelog</TT
|
|
>
|
|
section of the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_concat"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_concat</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A function used to produce variables like <CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
>. It takes
|
|
four or five
|
|
arguments: a prefix to concatenate onto each element, a list of
|
|
elements, a suffix to concatenate onto each element, an environment
|
|
for variable interpolation, and an optional function that will be
|
|
called to transform the list before concatenation.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['_CPPINCFLAGS'] = '$( ${_concat(INCPREFIX, CPPPATH, INCSUFFIX, __env__, RDirs)} $)',
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CONFIGUREDIR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CONFIGUREDIR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The name of the directory in which
|
|
Configure context test files are written.
|
|
The default is
|
|
<TT
|
|
CLASS="filename"
|
|
>.sconf_temp</TT
|
|
>
|
|
in the top-level directory
|
|
containing the
|
|
<TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
>
|
|
file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CONFIGURELOG"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CONFIGURELOG</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The name of the Configure context log file.
|
|
The default is
|
|
<TT
|
|
CLASS="filename"
|
|
>config.log</TT
|
|
>
|
|
in the top-level directory
|
|
containing the
|
|
<TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
>
|
|
file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_CPPDEFFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_CPPDEFFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the C preprocessor command-line options
|
|
to define values.
|
|
The value of <CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
> is created
|
|
by appending <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
>
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CPPDEFINES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CPPDEFINES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A platform independent specification of C preprocessor definitions.
|
|
The definitions will be added to command lines
|
|
through the automatically-generated
|
|
<CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
> construction variable (see above),
|
|
which is constructed according to
|
|
the type of value of <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
>:</P
|
|
><P
|
|
>If <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
> is a string,
|
|
the values of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
>
|
|
construction variables
|
|
will be added to the beginning and end.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Will add -Dxyz to POSIX compiler command lines,
|
|
# and /Dxyz to Microsoft Visual C++ command lines.
|
|
env = Environment(CPPDEFINES='xyz')
|
|
</PRE
|
|
><P
|
|
> If <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
> is a list,
|
|
the values of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
>
|
|
construction variables
|
|
will be appended to the beginning and end
|
|
of each element in the list.
|
|
If any element is a list or tuple,
|
|
then the first item is the name being
|
|
defined and the second item is its value:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Will add -DB=2 -DA to POSIX compiler command lines,
|
|
# and /DB=2 /DA to Microsoft Visual C++ command lines.
|
|
env = Environment(CPPDEFINES=[('B', 2), 'A'])
|
|
</PRE
|
|
><P
|
|
> If <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
> is a dictionary,
|
|
the values of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
>
|
|
construction variables
|
|
will be appended to the beginning and end
|
|
of each item from the dictionary.
|
|
The key of each dictionary item
|
|
is a name being defined
|
|
to the dictionary item's corresponding value;
|
|
if the value is
|
|
<TT
|
|
CLASS="literal"
|
|
>None</TT
|
|
>,
|
|
then the name is defined without an explicit value.
|
|
Note that the resulting flags are sorted by keyword
|
|
to ensure that the order of the options on the
|
|
command line is consistent each time
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
is run.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Will add -DA -DB=2 to POSIX compiler command lines,
|
|
# and /DA /DB=2 to Microsoft Visual C++ command lines.
|
|
env = Environment(CPPDEFINES={'B':2, 'A':None})
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CPPDEFPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CPPDEFPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used to specify preprocessor definitions
|
|
on the C compiler command line.
|
|
This will be appended to the beginning of each definition
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CPPDEFSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CPPDEFSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify preprocessor definitions
|
|
on the C compiler command line.
|
|
This will be appended to the end of each definition
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$CPPDEFINES</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CPPFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CPPFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> User-specified C preprocessor options.
|
|
These will be included in any command that uses the C preprocessor,
|
|
including not just compilation of C and C++ source files
|
|
via the <A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-SHCCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOM</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-CXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOM</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-SHCXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXCOM</CODE
|
|
></A
|
|
> command lines,
|
|
but also the <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-F77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PPCOM</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-SHF77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77PPCOM</CODE
|
|
></A
|
|
> command lines
|
|
used to compile a Fortran source file,
|
|
and the <A
|
|
HREF="#cv-ASPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOM</CODE
|
|
></A
|
|
> command line
|
|
used to assemble an assembly language source file,
|
|
after first running each file through the C preprocessor.
|
|
Note that this variable does
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
contain
|
|
<CODE
|
|
CLASS="option"
|
|
>-I</CODE
|
|
>
|
|
(or similar) include search path options
|
|
that scons generates automatically from <A
|
|
HREF="#cv-CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
></A
|
|
>.
|
|
See <A
|
|
HREF="#cv-_CPPINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
></A
|
|
>, below,
|
|
for the variable that expands to those options.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_CPPINCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_CPPINCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the C preprocessor command-line options
|
|
for specifying directories to be searched for include files.
|
|
The value of <CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
> is created
|
|
by appending <CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
>
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CPPPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CPPPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of directories that the C preprocessor will search for include
|
|
directories. The C/C++ implicit dependency scanner will search these
|
|
directories for include files. Don't explicitly put include directory
|
|
arguments in CCFLAGS or CXXFLAGS because the result will be non-portable
|
|
and the directories will not be searched by the dependency scanner. Note:
|
|
directory names in CPPPATH will be looked-up relative to the SConscript
|
|
directory when they are used in a command. To force
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to look-up a directory relative to the root of the source tree use #:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CPPPATH='#/include')
|
|
</PRE
|
|
><P
|
|
> The directory look-up can also be forced using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>()
|
|
function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> include = Dir('include')
|
|
env = Environment(CPPPATH=include)
|
|
</PRE
|
|
><P
|
|
> The directory list will be added to command lines
|
|
through the automatically-generated
|
|
<CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
>.
|
|
Any command lines you define that need
|
|
the CPPPATH directory list should
|
|
include <CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CCCOM="my_compiler $_CPPINCFLAGS -c -o $TARGET $SOURCE")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CPPSUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CPPSUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of suffixes of files that will be scanned
|
|
for C preprocessor implicit dependencies
|
|
(#include lines).
|
|
The default list is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> [".c", ".C", ".cxx", ".cpp", ".c++", ".cc",
|
|
".h", ".H", ".hxx", ".hpp", ".hh",
|
|
".F", ".fpp", ".FPP",
|
|
".m", ".mm",
|
|
".S", ".spp", ".SPP"]
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CVS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CVS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The CVS executable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CVSCOFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CVSCOFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the CVS checkout subcommand.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CVSCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CVSCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to
|
|
fetch source files from a CVS repository.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CVSCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CVSCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when fetching
|
|
a source file from a CVS repository.
|
|
If this is not set, then <A
|
|
HREF="#cv-CVSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CVSCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CVSFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CVSFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options that are passed to CVS.
|
|
By default, this is set to
|
|
<TT
|
|
CLASS="literal"
|
|
>-d $CVSREPOSITORY</TT
|
|
>
|
|
to specify from where the files must be fetched.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CVSREPOSITORY"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CVSREPOSITORY</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The path to the CVS repository.
|
|
This is referenced in the default
|
|
<A
|
|
HREF="#cv-CVSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CVSFLAGS</CODE
|
|
></A
|
|
> value.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CXX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CXX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The C++ compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CXXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CXXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a C++ source file to an object file.
|
|
Any options specified in the <A
|
|
HREF="#cv-CXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFLAGS</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CXXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CXXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a C++ source file
|
|
is compiled to a (static) object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-CXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(CXXCOMSTR = "Compiling static object $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CXXFILESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CXXFILESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix for C++ source files.
|
|
This is used by the internal CXXFile builder
|
|
when generating C++ files from Lex (.ll) or YACC (.yy) input files.
|
|
The default suffix is
|
|
<TT
|
|
CLASS="filename"
|
|
>.cc</TT
|
|
>.
|
|
SCons also treats files with the suffixes
|
|
<TT
|
|
CLASS="filename"
|
|
>.cpp</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>.cxx</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>.c++</TT
|
|
>,
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>.C++</TT
|
|
>
|
|
as C++ files,
|
|
and files with
|
|
<TT
|
|
CLASS="filename"
|
|
>.mm</TT
|
|
>
|
|
suffixes as Objective C++ files.
|
|
On case-sensitive systems (Linux, UNIX, and other POSIX-alikes),
|
|
SCons also treats
|
|
<TT
|
|
CLASS="filename"
|
|
>.C</TT
|
|
>
|
|
(upper case) files
|
|
as C++ files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CXXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CXXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options that are passed to the C++ compiler.
|
|
By default, this includes the value of <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>,
|
|
so that setting <CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
> affects both C and C++ compilation.
|
|
If you want to add C++-specific flags,
|
|
you must set or override the value of <A
|
|
HREF="#cv-CXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-CXXVERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>CXXVERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The version number of the C++ compiler.
|
|
This may or may not be set,
|
|
depending on the specific C++ compiler being used.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DESCRIPTION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DESCRIPTION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A long description of the project being packaged.
|
|
This is included in the relevant section
|
|
of the file that controls the packaging build.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DESCRIPTION_lang"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DESCRIPTION_lang</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A language-specific long description for
|
|
the specified <CODE
|
|
CLASS="varname"
|
|
>lang</CODE
|
|
>.
|
|
This is used to populate a
|
|
<TT
|
|
CLASS="literal"
|
|
>%description -l</TT
|
|
>
|
|
section of an RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-Dir"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>Dir</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A function that converts a string
|
|
into a Dir instance relative to the target being built.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-Dirs"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>Dirs</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A function that converts a list of strings
|
|
into a list of Dir instances relative to the target being built.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DSUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DSUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of suffixes of files that will be scanned
|
|
for imported D package files.
|
|
The default list is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> ['.d']
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DVIPDF"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DVIPDF</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The TeX DVI file to PDF file converter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DVIPDFCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DVIPDFCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to convert TeX DVI files into a PDF file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DVIPDFCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DVIPDFCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a TeX DVI file
|
|
is converted into a PDF file.
|
|
If this is not set, then <A
|
|
HREF="#cv-DVIPDFCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPDFCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DVIPDFFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DVIPDFFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the TeX DVI file to PDF file converter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DVIPS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DVIPS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The TeX DVI file to PostScript converter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-DVIPSFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>DVIPSFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the TeX DVI file to PostScript converter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ENV"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ENV</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A dictionary of environment variables
|
|
to use when invoking commands. When
|
|
<CODE
|
|
CLASS="envar"
|
|
>$ENV</CODE
|
|
> is used in a command all list
|
|
values will be joined using the path separator and any other non-string
|
|
values will simply be coerced to a string.
|
|
Note that, by default,
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
does
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
propagate the environment in force when you
|
|
execute
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to the commands used to build target files.
|
|
This is so that builds will be guaranteed
|
|
repeatable regardless of the environment
|
|
variables set at the time
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
is invoked.</P
|
|
><P
|
|
>If you want to propagate your
|
|
environment variables
|
|
to the commands executed
|
|
to build target files,
|
|
you must do so explicitly:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os
|
|
env = Environment(ENV = os.environ)
|
|
</PRE
|
|
><P
|
|
> Note that you can choose only to propagate
|
|
certain environment variables.
|
|
A common example is
|
|
the system
|
|
<CODE
|
|
CLASS="envar"
|
|
>PATH</CODE
|
|
>
|
|
environment variable,
|
|
so that
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
uses the same utilities
|
|
as the invoking shell (or other process):
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os
|
|
env = Environment(ENV = {'PATH' : os.environ['PATH']})
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ESCAPE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ESCAPE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A function that will be called to escape shell special characters in
|
|
command lines. The function should take one argument: the command line
|
|
string to escape; and should return the escaped command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Fortran 77 compiler.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default Fortran compiler
|
|
for all Fortran versions.
|
|
You only need to set <A
|
|
HREF="#cv-F77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77</CODE
|
|
></A
|
|
> if you need to use a specific compiler
|
|
or compiler version for Fortran 77 files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 77 source file to an object file.
|
|
You only need to set <A
|
|
HREF="#cv-F77COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77COM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
command line for Fortran 77 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 77 source file
|
|
is compiled to an object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-F77COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77COM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77FILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77FILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the F77 dialect will be used. By
|
|
default, this is ['.f77']
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General user-specified options that are passed to the Fortran 77 compiler.
|
|
Note that this variable does
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
contain
|
|
<CODE
|
|
CLASS="option"
|
|
>-I</CODE
|
|
>
|
|
(or similar) include search path options
|
|
that scons generates automatically from <A
|
|
HREF="#cv-F77PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PATH</CODE
|
|
></A
|
|
>.
|
|
See
|
|
<A
|
|
HREF="#cv-_F77INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F77INCFLAGS</CODE
|
|
></A
|
|
>
|
|
below,
|
|
for the variable that expands to those options.
|
|
You only need to set <A
|
|
HREF="#cv-F77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77FLAGS</CODE
|
|
></A
|
|
> if you need to define specific
|
|
user options for Fortran 77 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the user-specified options
|
|
passed to the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_F77INCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_F77INCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the Fortran 77 compiler command-line options
|
|
for specifying directories to be searched for include files.
|
|
The value of <A
|
|
HREF="#cv-_F77INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F77INCFLAGS</CODE
|
|
></A
|
|
> is created
|
|
by appending <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-F77PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PATH</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77PATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77PATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of directories that the Fortran 77 compiler will search for include
|
|
directories. The implicit dependency scanner will search these
|
|
directories for include files. Don't explicitly put include directory
|
|
arguments in <A
|
|
HREF="#cv-F77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77FLAGS</CODE
|
|
></A
|
|
> because the result will be non-portable
|
|
and the directories will not be searched by the dependency scanner. Note:
|
|
directory names in <A
|
|
HREF="#cv-F77PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PATH</CODE
|
|
></A
|
|
> will be looked-up relative to the SConscript
|
|
directory when they are used in a command. To force
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to look-up a directory relative to the root of the source tree use #:
|
|
You only need to set <A
|
|
HREF="#cv-F77PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PATH</CODE
|
|
></A
|
|
> if you need to define a specific
|
|
include path for Fortran 77 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the include path
|
|
for the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(F77PATH='#/include')
|
|
</PRE
|
|
><P
|
|
> The directory look-up can also be forced using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>()
|
|
function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> include = Dir('include')
|
|
env = Environment(F77PATH=include)
|
|
</PRE
|
|
><P
|
|
> The directory list will be added to command lines
|
|
through the automatically-generated
|
|
<A
|
|
HREF="#cv-_F77INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F77INCFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-F77PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PATH</CODE
|
|
></A
|
|
>.
|
|
Any command lines you define that need
|
|
the F77PATH directory list should
|
|
include <A
|
|
HREF="#cv-_F77INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F77INCFLAGS</CODE
|
|
></A
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(F77COM="my_compiler $_F77INCFLAGS -c -o $TARGET $SOURCE")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77PPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77PPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 77 source file to an object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified in the <A
|
|
HREF="#cv-F77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77FLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
You only need to set <A
|
|
HREF="#cv-F77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PPCOM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
C-preprocessor command line for Fortran 77 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default C-preprocessor command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77PPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77PPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 77 source file
|
|
is compiled to an object file
|
|
after first running the file through the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-F77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PPCOM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F77PPFILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F77PPFILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the compilation + preprocessor pass for
|
|
F77 dialect will be used. By default, this is empty
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Fortran 90 compiler.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default Fortran compiler
|
|
for all Fortran versions.
|
|
You only need to set <A
|
|
HREF="#cv-F90"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90</CODE
|
|
></A
|
|
> if you need to use a specific compiler
|
|
or compiler version for Fortran 90 files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 90 source file to an object file.
|
|
You only need to set <A
|
|
HREF="#cv-F90COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90COM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
command line for Fortran 90 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 90 source file
|
|
is compiled to an object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-F90COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90COM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90FILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90FILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the F90 dialect will be used. By
|
|
default, this is ['.f90']
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General user-specified options that are passed to the Fortran 90 compiler.
|
|
Note that this variable does
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
contain
|
|
<CODE
|
|
CLASS="option"
|
|
>-I</CODE
|
|
>
|
|
(or similar) include search path options
|
|
that scons generates automatically from <A
|
|
HREF="#cv-F90PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PATH</CODE
|
|
></A
|
|
>.
|
|
See
|
|
<A
|
|
HREF="#cv-_F90INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F90INCFLAGS</CODE
|
|
></A
|
|
>
|
|
below,
|
|
for the variable that expands to those options.
|
|
You only need to set <A
|
|
HREF="#cv-F90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90FLAGS</CODE
|
|
></A
|
|
> if you need to define specific
|
|
user options for Fortran 90 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the user-specified options
|
|
passed to the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_F90INCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_F90INCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the Fortran 90 compiler command-line options
|
|
for specifying directories to be searched for include files.
|
|
The value of <A
|
|
HREF="#cv-_F90INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F90INCFLAGS</CODE
|
|
></A
|
|
> is created
|
|
by appending <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-F90PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PATH</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90PATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90PATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of directories that the Fortran 90 compiler will search for include
|
|
directories. The implicit dependency scanner will search these
|
|
directories for include files. Don't explicitly put include directory
|
|
arguments in <A
|
|
HREF="#cv-F90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90FLAGS</CODE
|
|
></A
|
|
> because the result will be non-portable
|
|
and the directories will not be searched by the dependency scanner. Note:
|
|
directory names in <A
|
|
HREF="#cv-F90PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PATH</CODE
|
|
></A
|
|
> will be looked-up relative to the SConscript
|
|
directory when they are used in a command. To force
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to look-up a directory relative to the root of the source tree use #:
|
|
You only need to set <A
|
|
HREF="#cv-F90PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PATH</CODE
|
|
></A
|
|
> if you need to define a specific
|
|
include path for Fortran 90 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the include path
|
|
for the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(F90PATH='#/include')
|
|
</PRE
|
|
><P
|
|
> The directory look-up can also be forced using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>()
|
|
function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> include = Dir('include')
|
|
env = Environment(F90PATH=include)
|
|
</PRE
|
|
><P
|
|
> The directory list will be added to command lines
|
|
through the automatically-generated
|
|
<A
|
|
HREF="#cv-_F90INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F90INCFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-F90PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PATH</CODE
|
|
></A
|
|
>.
|
|
Any command lines you define that need
|
|
the F90PATH directory list should
|
|
include <A
|
|
HREF="#cv-_F90INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F90INCFLAGS</CODE
|
|
></A
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(F90COM="my_compiler $_F90INCFLAGS -c -o $TARGET $SOURCE")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90PPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90PPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 90 source file to an object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified in the <A
|
|
HREF="#cv-F90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90FLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
You only need to set <A
|
|
HREF="#cv-F90PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PPCOM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
C-preprocessor command line for Fortran 90 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default C-preprocessor command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90PPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90PPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 90 source file
|
|
is compiled after first running the file through the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-F90PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PPCOM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F90PPFILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F90PPFILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the compilation + preprocessor pass for
|
|
F90 dialect will be used. By default, this is empty
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Fortran 95 compiler.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default Fortran compiler
|
|
for all Fortran versions.
|
|
You only need to set <A
|
|
HREF="#cv-F95"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95</CODE
|
|
></A
|
|
> if you need to use a specific compiler
|
|
or compiler version for Fortran 95 files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 95 source file to an object file.
|
|
You only need to set <A
|
|
HREF="#cv-F95COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95COM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
command line for Fortran 95 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 95 source file
|
|
is compiled to an object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-F95COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95COM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95FILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95FILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the F95 dialect will be used. By
|
|
default, this is ['.f95']
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General user-specified options that are passed to the Fortran 95 compiler.
|
|
Note that this variable does
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
contain
|
|
<CODE
|
|
CLASS="option"
|
|
>-I</CODE
|
|
>
|
|
(or similar) include search path options
|
|
that scons generates automatically from <A
|
|
HREF="#cv-F95PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PATH</CODE
|
|
></A
|
|
>.
|
|
See
|
|
<A
|
|
HREF="#cv-_F95INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F95INCFLAGS</CODE
|
|
></A
|
|
>
|
|
below,
|
|
for the variable that expands to those options.
|
|
You only need to set <A
|
|
HREF="#cv-F95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95FLAGS</CODE
|
|
></A
|
|
> if you need to define specific
|
|
user options for Fortran 95 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the user-specified options
|
|
passed to the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_F95INCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_F95INCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the Fortran 95 compiler command-line options
|
|
for specifying directories to be searched for include files.
|
|
The value of <A
|
|
HREF="#cv-_F95INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F95INCFLAGS</CODE
|
|
></A
|
|
> is created
|
|
by appending <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-F95PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PATH</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95PATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95PATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of directories that the Fortran 95 compiler will search for include
|
|
directories. The implicit dependency scanner will search these
|
|
directories for include files. Don't explicitly put include directory
|
|
arguments in <A
|
|
HREF="#cv-F95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95FLAGS</CODE
|
|
></A
|
|
> because the result will be non-portable
|
|
and the directories will not be searched by the dependency scanner. Note:
|
|
directory names in <A
|
|
HREF="#cv-F95PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PATH</CODE
|
|
></A
|
|
> will be looked-up relative to the SConscript
|
|
directory when they are used in a command. To force
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to look-up a directory relative to the root of the source tree use #:
|
|
You only need to set <A
|
|
HREF="#cv-F95PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PATH</CODE
|
|
></A
|
|
> if you need to define a specific
|
|
include path for Fortran 95 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the include path
|
|
for the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(F95PATH='#/include')
|
|
</PRE
|
|
><P
|
|
> The directory look-up can also be forced using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>()
|
|
function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> include = Dir('include')
|
|
env = Environment(F95PATH=include)
|
|
</PRE
|
|
><P
|
|
> The directory list will be added to command lines
|
|
through the automatically-generated
|
|
<A
|
|
HREF="#cv-_F95INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F95INCFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-F95PATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PATH</CODE
|
|
></A
|
|
>.
|
|
Any command lines you define that need
|
|
the F95PATH directory list should
|
|
include <A
|
|
HREF="#cv-_F95INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F95INCFLAGS</CODE
|
|
></A
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(F95COM="my_compiler $_F95INCFLAGS -c -o $TARGET $SOURCE")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95PPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95PPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 95 source file to an object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified in the <A
|
|
HREF="#cv-F95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95FLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
You only need to set <A
|
|
HREF="#cv-F95PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PPCOM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
C-preprocessor command line for Fortran 95 files.
|
|
You should normally set the <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default C-preprocessor command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95PPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95PPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 95 source file
|
|
is compiled to an object file
|
|
after first running the file through the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-F95PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PPCOM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-F95PPFILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>F95PPFILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the compilation + preprocessor pass for
|
|
F95 dialect will be used. By default, this is empty
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-File"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>File</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A function that converts a string into a File instance relative to the
|
|
target being built.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRAN"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRAN</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The default Fortran compiler
|
|
for all versions of Fortran.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran source file to an object file.
|
|
By default, any options specified
|
|
in the <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-_FORTRANMODFLAG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANMODFLAG</CODE
|
|
></A
|
|
>, and
|
|
<A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran source file
|
|
is compiled to an object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANFILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANFILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the FORTRAN dialect will be used. By
|
|
default, this is ['.f', '.for', '.ftn']
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General user-specified options that are passed to the Fortran compiler.
|
|
Note that this variable does
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
contain
|
|
<CODE
|
|
CLASS="option"
|
|
>-I</CODE
|
|
>
|
|
(or similar) include or module search path options
|
|
that scons generates automatically from <A
|
|
HREF="#cv-FORTRANPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
></A
|
|
>.
|
|
See
|
|
<A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-_FORTRANMODFLAG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANMODFLAG</CODE
|
|
></A
|
|
>,
|
|
below,
|
|
for the variables that expand those options.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_FORTRANINCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_FORTRANINCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the Fortran compiler command-line options
|
|
for specifying directories to be searched for include
|
|
files and module files.
|
|
The value of <A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
> is created
|
|
by prepending/appending <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-FORTRANPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANMODDIR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANMODDIR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Directory location where the Fortran compiler should place
|
|
any module files it generates. This variable is empty, by default. Some
|
|
Fortran compilers will internally append this directory in the search path
|
|
for module files, as well.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANMODDIRPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANMODDIRPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used to specify a module directory on the Fortran compiler command
|
|
line.
|
|
This will be appended to the beginning of the directory
|
|
in the <A
|
|
HREF="#cv-FORTRANMODDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIR</CODE
|
|
></A
|
|
> construction variables
|
|
when the <A
|
|
HREF="#cv-_FORTRANMODFLAG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANMODFLAG</CODE
|
|
></A
|
|
> variables is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANMODDIRSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANMODDIRSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify a module directory on the Fortran compiler command
|
|
line.
|
|
This will be appended to the beginning of the directory
|
|
in the <A
|
|
HREF="#cv-FORTRANMODDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIR</CODE
|
|
></A
|
|
> construction variables
|
|
when the <A
|
|
HREF="#cv-_FORTRANMODFLAG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANMODFLAG</CODE
|
|
></A
|
|
> variables is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_FORTRANMODFLAG"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_FORTRANMODFLAG</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the Fortran compiler command-line option
|
|
for specifying the directory location where the Fortran
|
|
compiler should place any module files that happen to get
|
|
generated during compilation.
|
|
The value of <A
|
|
HREF="#cv-_FORTRANMODFLAG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANMODFLAG</CODE
|
|
></A
|
|
> is created
|
|
by prepending/appending <A
|
|
HREF="#cv-FORTRANMODDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIRPREFIX</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-FORTRANMODDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIRSUFFIX</CODE
|
|
></A
|
|
>
|
|
to the beginning and end of the directory in <A
|
|
HREF="#cv-FORTRANMODDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANMODPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANMODPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The module file prefix used by the Fortran compiler. SCons assumes that
|
|
the Fortran compiler follows the quasi-standard naming convention for
|
|
module files of
|
|
<TT
|
|
CLASS="filename"
|
|
>module_name.mod</TT
|
|
>.
|
|
As a result, this variable is left empty, by default. For situations in
|
|
which the compiler does not necessarily follow the normal convention,
|
|
the user may use this variable. Its value will be appended to every
|
|
module file name as scons attempts to resolve dependencies.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANMODSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANMODSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The module file suffix used by the Fortran compiler. SCons assumes that
|
|
the Fortran compiler follows the quasi-standard naming convention for
|
|
module files of
|
|
<TT
|
|
CLASS="filename"
|
|
>module_name.mod</TT
|
|
>.
|
|
As a result, this variable is set to ".mod", by default. For situations
|
|
in which the compiler does not necessarily follow the normal convention,
|
|
the user may use this variable. Its value will be appended to every
|
|
module file name as scons attempts to resolve dependencies.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of directories that the Fortran compiler will search for
|
|
include files and (for some compilers) module files. The Fortran implicit
|
|
dependency scanner will search these directories for include files (but
|
|
not module files since they are autogenerated and, as such, may not
|
|
actually exist at the time the scan takes place). Don't explicitly put
|
|
include directory arguments in FORTRANFLAGS because the result will be
|
|
non-portable and the directories will not be searched by the dependency
|
|
scanner. Note: directory names in FORTRANPATH will be looked-up relative
|
|
to the SConscript directory when they are used in a command. To force
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to look-up a directory relative to the root of the source tree use #:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(FORTRANPATH='#/include')
|
|
</PRE
|
|
><P
|
|
> The directory look-up can also be forced using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>()
|
|
function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> include = Dir('include')
|
|
env = Environment(FORTRANPATH=include)
|
|
</PRE
|
|
><P
|
|
> The directory list will be added to command lines
|
|
through the automatically-generated
|
|
<A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each directory in <A
|
|
HREF="#cv-FORTRANPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
></A
|
|
>.
|
|
Any command lines you define that need
|
|
the FORTRANPATH directory list should
|
|
include <A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(FORTRANCOM="my_compiler $_FORTRANINCFLAGS -c -o $TARGET $SOURCE")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANPPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANPPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran source file to an object file
|
|
after first running the file through the C preprocessor.
|
|
By default, any options specified in the <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-_FORTRANMODFLAG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANMODFLAG</CODE
|
|
></A
|
|
>, and
|
|
<A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variables are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANPPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANPPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran source file
|
|
is compiled to an object file
|
|
after first running the file throught the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANPPFILESUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANPPFILESUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of file extensions for which the compilation + preprocessor pass for
|
|
FORTRAN dialect will be used. By default, this is ['.fpp', '.FPP']
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FORTRANSUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FORTRANSUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of suffixes of files that will be scanned
|
|
for Fortran implicit dependencies
|
|
(INCLUDE lines and USE statements).
|
|
The default list is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> [".f", ".F", ".for", ".FOR", ".ftn", ".FTN", ".fpp", ".FPP",
|
|
".f77", ".F77", ".f90", ".F90", ".f95", ".F95"]
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FRAMEWORKPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Mac OS X with gcc,
|
|
a list containing the paths to search for frameworks.
|
|
Used by the compiler to find framework-style includes like
|
|
#include <Fmwk/Header.h>.
|
|
Used by the linker to find user-specified frameworks when linking (see
|
|
<A
|
|
HREF="#cv-FRAMEWORKS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKS</CODE
|
|
></A
|
|
>).
|
|
For example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.AppendUnique(FRAMEWORKPATH='#myframeworkdir')
|
|
</PRE
|
|
><P
|
|
> will add
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> ... -Fmyframeworkdir
|
|
</PRE
|
|
><P
|
|
> to the compiler and linker command lines.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_FRAMEWORKPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_FRAMEWORKPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Mac OS X with gcc, an automatically-generated construction variable
|
|
containing the linker command-line options corresponding to
|
|
<A
|
|
HREF="#cv-FRAMEWORKPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKPATH</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FRAMEWORKPATHPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKPATHPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Mac OS X with gcc, the prefix to be used for the FRAMEWORKPATH entries.
|
|
(see <A
|
|
HREF="#cv-FRAMEWORKPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKPATH</CODE
|
|
></A
|
|
>).
|
|
The default value is
|
|
<CODE
|
|
CLASS="option"
|
|
>-F</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FRAMEWORKPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Mac OS X with gcc,
|
|
the prefix to be used for linking in frameworks
|
|
(see <A
|
|
HREF="#cv-FRAMEWORKS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKS</CODE
|
|
></A
|
|
>).
|
|
The default value is
|
|
<CODE
|
|
CLASS="option"
|
|
>-framework</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_FRAMEWORKS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_FRAMEWORKS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Mac OS X with gcc,
|
|
an automatically-generated construction variable
|
|
containing the linker command-line options
|
|
for linking with FRAMEWORKS.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FRAMEWORKS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Mac OS X with gcc, a list of the framework names to be linked into a
|
|
program or shared library or bundle.
|
|
The default value is the empty list.
|
|
For example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.AppendUnique(FRAMEWORKS=Split('System Cocoa SystemConfiguration'))
|
|
</PRE
|
|
><P
|
|
> </P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-FRAMEWORKSFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKSFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Mac OS X with gcc,
|
|
general user-supplied frameworks options to be added at
|
|
the end of a command
|
|
line building a loadable module.
|
|
(This has been largely superceded by
|
|
the <A
|
|
HREF="#cv-FRAMEWORKPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FRAMEWORKPATHPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKPATHPREFIX</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-FRAMEWORKPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKPREFIX</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-FRAMEWORKS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKS</CODE
|
|
></A
|
|
> variables
|
|
described above.)
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-GS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>GS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Ghostscript program used to convert PostScript to PDF files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-GSCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>GSCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Ghostscript command line used to convert PostScript to PDF files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-GSCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>GSCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when
|
|
Ghostscript is used to convert
|
|
a PostScript file to a PDF file.
|
|
If this is not set, then <A
|
|
HREF="#cv-GSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$GSCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-GSFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>GSFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the Ghostscript program
|
|
when converting PostScript to PDF files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-IDLSUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>IDLSUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of suffixes of files that will be scanned
|
|
for IDL implicit dependencies
|
|
(#include or import lines).
|
|
The default list is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> [".idl", ".IDL"]
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-IMPLICIT_COMMAND_DEPENDENCIES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>IMPLICIT_COMMAND_DEPENDENCIES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Controls whether or not SCons will
|
|
add implicit dependencies for the commands
|
|
executed to build targets.</P
|
|
><P
|
|
>By default, SCons will add
|
|
to each target
|
|
an implicit dependency on the command
|
|
represented by the first argument on any
|
|
command line it executes.
|
|
The specific file for the dependency is
|
|
found by searching the
|
|
<CODE
|
|
CLASS="varname"
|
|
>PATH</CODE
|
|
>
|
|
variable in the
|
|
<CODE
|
|
CLASS="varname"
|
|
>ENV</CODE
|
|
>
|
|
environment used to execute the command.</P
|
|
><P
|
|
>If the construction variable
|
|
<CODE
|
|
CLASS="envar"
|
|
>$IMPLICIT_COMMAND_DEPENDENCIES</CODE
|
|
>
|
|
is set to a false value
|
|
(<TT
|
|
CLASS="literal"
|
|
>None</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>False</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>0</TT
|
|
>,
|
|
etc.),
|
|
then the implicit dependency will
|
|
not be added to the targets
|
|
built with that construction environment.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(IMPLICIT_COMMAND_DEPENDENCIES = 0)
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-INCPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>INCPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used to specify an include directory on the C compiler command
|
|
line.
|
|
This will be appended to the beginning of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
> construction variables
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
>
|
|
variables are automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-INCSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>INCSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify an include directory on the C compiler command
|
|
line.
|
|
This will be appended to the end of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$FORTRANPATH</CODE
|
|
> construction variables
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
>
|
|
variables are automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-INSTALL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>INSTALL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A function to be called to install a file into a
|
|
destination file name.
|
|
The default function copies the file into the destination
|
|
(and sets the destination file's mode and permission bits
|
|
to match the source file's).
|
|
The function takes the following arguments:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def install(dest, source, env):
|
|
</PRE
|
|
><P
|
|
> <CODE
|
|
CLASS="varname"
|
|
>dest</CODE
|
|
>
|
|
is the path name of the destination file.
|
|
<CODE
|
|
CLASS="varname"
|
|
>source</CODE
|
|
>
|
|
is the path name of the source file.
|
|
<CODE
|
|
CLASS="varname"
|
|
>env</CODE
|
|
>
|
|
is the construction environment
|
|
(a dictionary of construction values)
|
|
in force for this file installation.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-INSTALLSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>INSTALLSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a file is
|
|
installed into a destination file name.
|
|
The default is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Install file: "$SOURCE" as "$TARGET"
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-INTEL_C_COMPILER_VERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>INTEL_C_COMPILER_VERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set by the "intelc" Tool
|
|
to the major version number of the Intel C compiler
|
|
selected for use.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Java archive tool.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JARCHDIR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JARCHDIR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The directory to which the Java archive tool should change
|
|
(using the
|
|
<CODE
|
|
CLASS="option"
|
|
>-C</CODE
|
|
>
|
|
option).
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JARCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JARCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the Java archive tool.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JARCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JARCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when the Java archive tool
|
|
is called
|
|
If this is not set, then <CODE
|
|
CLASS="envar"
|
|
>$JARCOM</CODE
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(JARCOMSTR = "JARchiving $SOURCES into $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JARFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JARFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the Java archive tool.
|
|
By default this is set to
|
|
<CODE
|
|
CLASS="option"
|
|
>cf</CODE
|
|
>
|
|
to create the necessary
|
|
<B
|
|
CLASS="command"
|
|
>jar</B
|
|
>
|
|
file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JARSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JARSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix for Java archives:
|
|
<TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
>
|
|
by default.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVABOOTCLASSPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVABOOTCLASSPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specifies the list of directories that
|
|
will be added to the
|
|
<SPAN
|
|
CLASS="application"
|
|
>javac</SPAN
|
|
> command line
|
|
via the <CODE
|
|
CLASS="option"
|
|
>-bootclasspath</CODE
|
|
> option.
|
|
The individual directory names will be
|
|
separated by the operating system's path separate character
|
|
(<TT
|
|
CLASS="filename"
|
|
>:</TT
|
|
> on UNIX/Linux/POSIX,
|
|
<TT
|
|
CLASS="filename"
|
|
>;</TT
|
|
> on Windows).
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVAC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVAC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Java compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVACCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVACCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a directory tree containing
|
|
Java source files to
|
|
corresponding Java class files.
|
|
Any options specified in the <A
|
|
HREF="#cv-JAVACFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACFLAGS</CODE
|
|
></A
|
|
> construction variable
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVACCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVACCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when compiling
|
|
a directory tree of Java source files to
|
|
corresponding Java class files.
|
|
If this is not set, then <A
|
|
HREF="#cv-JAVACCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(JAVACCOMSTR = "Compiling class files $TARGETS from $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVACFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVACFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options that are passed to the Java compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVACLASSDIR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVACLASSDIR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The directory in which Java class files may be found.
|
|
This is stripped from the beginning of any Java .class
|
|
file names supplied to the
|
|
<TT
|
|
CLASS="literal"
|
|
>JavaH</TT
|
|
>
|
|
builder.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVACLASSPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVACLASSPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specifies the list of directories that
|
|
will be searched for Java
|
|
<TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> file.
|
|
The directories in this list will be added to the
|
|
<SPAN
|
|
CLASS="application"
|
|
>javac</SPAN
|
|
> and <SPAN
|
|
CLASS="application"
|
|
>javah</SPAN
|
|
> command lines
|
|
via the <CODE
|
|
CLASS="option"
|
|
>-classpath</CODE
|
|
> option.
|
|
The individual directory names will be
|
|
separated by the operating system's path separate character
|
|
(<TT
|
|
CLASS="filename"
|
|
>:</TT
|
|
> on UNIX/Linux/POSIX,
|
|
<TT
|
|
CLASS="filename"
|
|
>;</TT
|
|
> on Windows).</P
|
|
><P
|
|
>Note that this currently just adds the specified
|
|
directory via the <CODE
|
|
CLASS="option"
|
|
>-classpath</CODE
|
|
> option.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not currently search the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSPATH</CODE
|
|
> directories for dependency
|
|
<TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVACLASSSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVACLASSSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix for Java class files;
|
|
<TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
>
|
|
by default.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVAH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVAH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Java generator for C header and stub files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVAHCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVAHCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to generate C header and stub files
|
|
from Java classes.
|
|
Any options specified in the <A
|
|
HREF="#cv-JAVAHFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVAHFLAGS</CODE
|
|
></A
|
|
> construction variable
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVAHCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVAHCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when C header and stub files
|
|
are generated from Java classes.
|
|
If this is not set, then <A
|
|
HREF="#cv-JAVAHCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVAHCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(JAVAHCOMSTR = "Generating header/stub file(s) $TARGETS from $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVAHFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVAHFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the C header and stub file generator
|
|
for Java classes.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVASOURCEPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVASOURCEPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specifies the list of directories that
|
|
will be searched for input
|
|
<TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> file.
|
|
The directories in this list will be added to the
|
|
<SPAN
|
|
CLASS="application"
|
|
>javac</SPAN
|
|
> command line
|
|
via the <CODE
|
|
CLASS="option"
|
|
>-sourcepath</CODE
|
|
> option.
|
|
The individual directory names will be
|
|
separated by the operating system's path separate character
|
|
(<TT
|
|
CLASS="filename"
|
|
>:</TT
|
|
> on UNIX/Linux/POSIX,
|
|
<TT
|
|
CLASS="filename"
|
|
>;</TT
|
|
> on Windows).</P
|
|
><P
|
|
>Note that this currently just adds the specified
|
|
directory via the <CODE
|
|
CLASS="option"
|
|
>-sourcepath</CODE
|
|
> option.
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> does not currently search the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$JAVASOURCEPATH</CODE
|
|
> directories for dependency
|
|
<TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVASUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVASUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix for Java files;
|
|
<TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
>
|
|
by default.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-JAVAVERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>JAVAVERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specifies the Java version being used by the <CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
> builder.
|
|
This is <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
> currently used to select one
|
|
version of the Java compiler vs. another.
|
|
Instead, you should set this to specify the version of Java
|
|
supported by your <SPAN
|
|
CLASS="application"
|
|
>javac</SPAN
|
|
> compiler.
|
|
The default is <TT
|
|
CLASS="literal"
|
|
>1.4</TT
|
|
>.</P
|
|
><P
|
|
>This is sometimes necessary because
|
|
Java 1.5 changed the file names that are created
|
|
for nested anonymous inner classes,
|
|
which can cause a mismatch with the files
|
|
that <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> expects will be generated by the <SPAN
|
|
CLASS="application"
|
|
>javac</SPAN
|
|
> compiler.
|
|
Setting <CODE
|
|
CLASS="envar"
|
|
>$JAVAVERSION</CODE
|
|
> to <TT
|
|
CLASS="literal"
|
|
>1.5</TT
|
|
>
|
|
(or <TT
|
|
CLASS="literal"
|
|
>1.6</TT
|
|
>, as appropriate)
|
|
can make <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> realize that a Java 1.5 or 1.6
|
|
build is actually up to date.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LATEX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LATEX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The LaTeX structured formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LATEXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LATEXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the LaTeX structured formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LATEXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LATEXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when calling
|
|
the LaTeX structured formatter and typesetter.
|
|
If this is not set, then <A
|
|
HREF="#cv-LATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(LATEXCOMSTR = "Building $TARGET from LaTeX input $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LATEXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LATEXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the LaTeX structured formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LATEXRETRIES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LATEXRETRIES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The maximum number of times that LaTeX
|
|
will be re-run if the
|
|
<TT
|
|
CLASS="filename"
|
|
>.log</TT
|
|
>
|
|
generated by the <A
|
|
HREF="#cv-LATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOM</CODE
|
|
></A
|
|
> command
|
|
indicates that there are undefined references.
|
|
The default is to try to resolve undefined references
|
|
by re-running LaTeX up to three times.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LATEXSUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LATEXSUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of suffixes of files that will be scanned
|
|
for LaTeX implicit dependencies
|
|
(<TT
|
|
CLASS="literal"
|
|
>\include</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>\import</TT
|
|
> files).
|
|
The default list is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> [".tex", ".ltx", ".latex"]
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LDMODULE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LDMODULE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The linker for building loadable modules.
|
|
By default, this is the same as <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LDMODULECOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LDMODULECOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line for building loadable modules.
|
|
On Mac OS X, this uses the <A
|
|
HREF="#cv-LDMODULE"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULE</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-LDMODULEFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULEFLAGS</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-FRAMEWORKSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKSFLAGS</CODE
|
|
></A
|
|
> variables.
|
|
On other systems, this is the same as <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LDMODULECOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LDMODULECOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when building loadable modules.
|
|
If this is not set, then <A
|
|
HREF="#cv-LDMODULECOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULECOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LDMODULEFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LDMODULEFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General user options passed to the linker for building loadable modules.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LDMODULEPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LDMODULEPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for loadable module file names.
|
|
On Mac OS X, this is null;
|
|
on other systems, this is
|
|
the same as <A
|
|
HREF="#cv-SHLIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLIBPREFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LDMODULESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LDMODULESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for loadable module file names.
|
|
On Mac OS X, this is null;
|
|
on other systems, this is
|
|
the same as $SHLIBSUFFIX.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LEX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LEX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The lexical analyzer generator.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LEXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LEXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the lexical analyzer generator
|
|
to generate a source file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LEXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LEXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when generating a source file
|
|
using the lexical analyzer generator.
|
|
If this is not set, then <A
|
|
HREF="#cv-LEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LEXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(LEXCOMSTR = "Lex'ing $TARGET from $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LEXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LEXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the lexical analyzer generator.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_LIBDIRFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_LIBDIRFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the linker command-line options
|
|
for specifying directories to be searched for library.
|
|
The value of <CODE
|
|
CLASS="envar"
|
|
>$_LIBDIRFLAGS</CODE
|
|
> is created
|
|
by appending <CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
>
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBDIRPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBDIRPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used to specify a library directory on the linker command line.
|
|
This will be appended to the beginning of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_LIBDIRFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBDIRSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBDIRSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify a library directory on the linker command line.
|
|
This will be appended to the end of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_LIBDIRFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_LIBFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_LIBFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the linker command-line options
|
|
for specifying libraries to be linked with the resulting target.
|
|
The value of <CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
> is created
|
|
by appending <CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
>
|
|
to the beginning and end
|
|
of each filename in <CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBLINKPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBLINKPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used to specify a library to link on the linker command line.
|
|
This will be appended to the beginning of each library
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBLINKSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBLINKSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify a library to link on the linker command line.
|
|
This will be appended to the end of each library
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of directories that will be searched for libraries.
|
|
The implicit dependency scanner will search these
|
|
directories for include files. Don't explicitly put include directory
|
|
arguments in <CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
> or <CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
>
|
|
because the result will be non-portable
|
|
and the directories will not be searched by the dependency scanner. Note:
|
|
directory names in LIBPATH will be looked-up relative to the SConscript
|
|
directory when they are used in a command. To force
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to look-up a directory relative to the root of the source tree use #:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(LIBPATH='#/libs')
|
|
</PRE
|
|
><P
|
|
> The directory look-up can also be forced using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>()
|
|
function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> libs = Dir('libs')
|
|
env = Environment(LIBPATH=libs)
|
|
</PRE
|
|
><P
|
|
> The directory list will be added to command lines
|
|
through the automatically-generated
|
|
<CODE
|
|
CLASS="envar"
|
|
>$_LIBDIRFLAGS</CODE
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
>.
|
|
Any command lines you define that need
|
|
the LIBPATH directory list should
|
|
include <CODE
|
|
CLASS="envar"
|
|
>$_LIBDIRFLAGS</CODE
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(LINKCOM="my_linker $_LIBDIRFLAGS $_LIBFLAGS -o $TARGET $SOURCE")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for (static) library file names.
|
|
A default value is set for each platform
|
|
(posix, win32, os2, etc.),
|
|
but the value is overridden by individual tools
|
|
(ar, mslib, sgiar, sunar, tlib, etc.)
|
|
to reflect the names of the libraries they create.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBPREFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBPREFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A list of all legal prefixes for library file names.
|
|
When searching for library dependencies,
|
|
SCons will look for files with these prefixes,
|
|
the base library name,
|
|
and suffixes in the <CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIXES</CODE
|
|
> list.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A list of one or more libraries
|
|
that will be linked with
|
|
any executable programs
|
|
created by this environment.</P
|
|
><P
|
|
>The library list will be added to command lines
|
|
through the automatically-generated
|
|
<CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each filename in <CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
>.
|
|
Any command lines you define that need
|
|
the LIBS library list should
|
|
include <CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(LINKCOM="my_linker $_LIBDIRFLAGS $_LIBFLAGS -o $TARGET $SOURCE")
|
|
</PRE
|
|
><P
|
|
> If you add a
|
|
File
|
|
object to the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
>
|
|
list, the name of that file will be added to
|
|
<CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
>,
|
|
and thus the link line, as is, without
|
|
<CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
>
|
|
or
|
|
<CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
>.
|
|
For example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Append(LIBS=File('/tmp/mylib.so'))
|
|
</PRE
|
|
><P
|
|
> In all cases, scons will add dependencies from the executable program to
|
|
all the libraries in this list.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for (static) library file names.
|
|
A default value is set for each platform
|
|
(posix, win32, os2, etc.),
|
|
but the value is overridden by individual tools
|
|
(ar, mslib, sgiar, sunar, tlib, etc.)
|
|
to reflect the names of the libraries they create.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LIBSUFFIXES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LIBSUFFIXES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A list of all legal suffixes for library file names.
|
|
When searching for library dependencies,
|
|
SCons will look for files with prefixes, in the <CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIXES</CODE
|
|
> list,
|
|
the base library name,
|
|
and these suffixes.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LICENSE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LICENSE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The abbreviated name of the license under which
|
|
this project is released (gpl, lpgl, bsd etc.).
|
|
See http://www.opensource.org/licenses/alphabetical
|
|
for a list of license names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LINK"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LINK</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The linker.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LINKCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LINKCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to link object files into an executable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LINKCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LINKCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when object files
|
|
are linked into an executable.
|
|
If this is not set, then <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(LINKCOMSTR = "Linking $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-LINKFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>LINKFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General user options passed to the linker.
|
|
Note that this variable should
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
contain
|
|
<CODE
|
|
CLASS="option"
|
|
>-l</CODE
|
|
>
|
|
(or similar) options for linking with the libraries listed in <A
|
|
HREF="#cv-LIBS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
></A
|
|
>,
|
|
nor
|
|
<CODE
|
|
CLASS="option"
|
|
>-L</CODE
|
|
>
|
|
(or similar) library search path options
|
|
that scons generates automatically from <A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
>.
|
|
See
|
|
<A
|
|
HREF="#cv-_LIBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
></A
|
|
>
|
|
above,
|
|
for the variable that expands to library-link options,
|
|
and
|
|
<A
|
|
HREF="#cv-_LIBDIRFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_LIBDIRFLAGS</CODE
|
|
></A
|
|
>
|
|
above,
|
|
for the variable that expands to library search path options.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-M4"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>M4</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The M4 macro preprocessor.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-M4COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>M4COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to pass files through the M4 macro preprocessor.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-M4COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>M4COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when
|
|
a file is passed through the M4 macro preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-M4COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$M4COM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-M4FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>M4FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the M4 macro preprocessor.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MAKEINDEX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MAKEINDEX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The makeindex generator for the TeX formatter and typesetter and the
|
|
LaTeX structured formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MAKEINDEXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MAKEINDEXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the makeindex generator for the
|
|
TeX formatter and typesetter and the LaTeX structured formatter and
|
|
typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MAKEINDEXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MAKEINDEXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when calling the makeindex generator for the
|
|
TeX formatter and typesetter
|
|
and the LaTeX structured formatter and typesetter.
|
|
If this is not set, then <A
|
|
HREF="#cv-MAKEINDEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MAKEINDEXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MAKEINDEXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MAKEINDEXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the makeindex generator for the TeX formatter
|
|
and typesetter and the LaTeX structured formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MAXLINELENGTH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MAXLINELENGTH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The maximum number of characters allowed on an external command line.
|
|
On Win32 systems,
|
|
link lines longer than this many characters
|
|
are linked via a temporary file name.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MIDL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MIDL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Microsoft IDL compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MIDLCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MIDLCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to pass files to the Microsoft IDL compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MIDLCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MIDLCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when
|
|
the Microsoft IDL copmiler is called.
|
|
If this is not set, then <A
|
|
HREF="#cv-MIDLCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MIDLCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MIDLFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MIDLFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the Microsoft IDL compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> When the Microsoft Visual Studio tools are initialized, they set up
|
|
this dictionary with the following keys:</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>VERSION</CODE
|
|
>:
|
|
the version of MSVS being used (can be set via
|
|
MSVS_VERSION)</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>VERSIONS</CODE
|
|
>:
|
|
the available versions of MSVS installed</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>VCINSTALLDIR</CODE
|
|
>:
|
|
installed directory of Visual C++</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>VSINSTALLDIR</CODE
|
|
>:
|
|
installed directory of Visual Studio</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKDIR</CODE
|
|
>:
|
|
installed directory of the .NET framework</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKVERSIONS</CODE
|
|
>:
|
|
list of installed versions of the .NET framework, sorted latest to oldest.</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKVERSION</CODE
|
|
>:
|
|
latest installed version of the .NET framework</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>FRAMEWORKSDKDIR</CODE
|
|
>:
|
|
installed location of the .NET SDK.</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>PLATFORMSDKDIR</CODE
|
|
>:
|
|
installed location of the Platform SDK.</P
|
|
><P
|
|
><CODE
|
|
CLASS="envar"
|
|
>PLATFORMSDK_MODULES</CODE
|
|
>:
|
|
dictionary of installed Platform SDK modules,
|
|
where the dictionary keys are keywords for the various modules, and
|
|
the values are 2-tuples where the first is the release date, and the
|
|
second is the version number.</P
|
|
><P
|
|
>If a value isn't set, it wasn't available in the registry.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_IGNORE_IDE_PATHS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_IGNORE_IDE_PATHS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Tells the MS Visual Studio tools to use minimal INCLUDE, LIB, and PATH settings,
|
|
instead of the settings from the IDE.</P
|
|
><P
|
|
>For Visual Studio, SCons will (by default) automatically determine
|
|
where MSVS is installed, and use the LIB, INCLUDE, and PATH variables
|
|
set by the IDE. You can override this behavior by setting these
|
|
variables after Environment initialization, or by setting
|
|
<CODE
|
|
CLASS="envar"
|
|
>MSVS_IGNORE_IDE_PATHS = 1</CODE
|
|
>
|
|
in the Environment initialization.
|
|
Specifying this will not leave these unset, but will set them to a
|
|
minimal set of paths needed to run the tools successfully.</P
|
|
><P
|
|
>For VS6, the mininimal set is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> INCLUDE:'<VSDir>\VC98\ATL\include;<VSDir>\VC98\MFC\include;<VSDir>\VC98\include'
|
|
LIB:'<VSDir>\VC98\MFC\lib;<VSDir>\VC98\lib'
|
|
PATH:'<VSDir>\Common\MSDev98\bin;<VSDir>\VC98\bin'
|
|
</PRE
|
|
><P
|
|
> For VS7, it is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> INCLUDE:'<VSDir>\Vc7\atlmfc\include;<VSDir>\Vc7\include'
|
|
LIB:'<VSDir>\Vc7\atlmfc\lib;<VSDir>\Vc7\lib'
|
|
PATH:'<VSDir>\Common7\Tools\bin;<VSDir>\Common7\Tools;<VSDir>\Vc7\bin'
|
|
</PRE
|
|
><P
|
|
> Where '<VSDir>' is the installed location of Visual Studio.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_PROJECT_BASE_PATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_PROJECT_BASE_PATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string
|
|
placed in a generated Microsoft Visual Studio solution file
|
|
as the value of the
|
|
<TT
|
|
CLASS="literal"
|
|
>SccProjectFilePathRelativizedFromConnection0</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="literal"
|
|
>SccProjectFilePathRelativizedFromConnection1</TT
|
|
>
|
|
attributes of the
|
|
<TT
|
|
CLASS="literal"
|
|
>GlobalSection(SourceCodeControl)</TT
|
|
>
|
|
section.
|
|
There is no default value.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_PROJECT_GUID"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_PROJECT_GUID</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string
|
|
placed in a generated Microsoft Visual Studio project file
|
|
as the value of the
|
|
<TT
|
|
CLASS="literal"
|
|
>ProjectGUID</TT
|
|
>
|
|
attribute.
|
|
The string is also placed in the
|
|
<TT
|
|
CLASS="literal"
|
|
>SolutionUniqueID</TT
|
|
>
|
|
attribute of the
|
|
<TT
|
|
CLASS="literal"
|
|
>GlobalSection(SourceCodeControl)</TT
|
|
>
|
|
section of the Microsoft Visual Studio solution file.
|
|
There is no default value.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_SCC_AUX_PATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_SCC_AUX_PATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The path name
|
|
placed in a generated Microsoft Visual Studio project file
|
|
as the value of the
|
|
<TT
|
|
CLASS="literal"
|
|
>SccAuxPath</TT
|
|
>
|
|
attribute
|
|
if the
|
|
<CODE
|
|
CLASS="envar"
|
|
>MSVS_SCC_PROVIDER</CODE
|
|
>
|
|
construction variable is also set.
|
|
There is no default value.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_SCC_LOCAL_PATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_SCC_LOCAL_PATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The path name
|
|
placed in a generated Microsoft Visual Studio project file
|
|
as the value of the
|
|
<TT
|
|
CLASS="literal"
|
|
>SccLocalPath</TT
|
|
>
|
|
attribute
|
|
if the
|
|
<CODE
|
|
CLASS="envar"
|
|
>MSVS_SCC_PROVIDER</CODE
|
|
>
|
|
construction variable is also set.
|
|
The path name is also placed in the
|
|
<TT
|
|
CLASS="literal"
|
|
>SccLocalPath0</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="literal"
|
|
>SccLocalPath1</TT
|
|
>
|
|
attributes of the
|
|
<TT
|
|
CLASS="literal"
|
|
>GlobalSection(SourceCodeControl)</TT
|
|
>
|
|
section of the Microsoft Visual Studio solution file.
|
|
There is no default value.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_SCC_PROJECT_NAME"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_SCC_PROJECT_NAME</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The project name
|
|
placed in a generated Microsoft Visual Studio project file
|
|
as the value of the
|
|
<TT
|
|
CLASS="literal"
|
|
>SccProjectName</TT
|
|
>
|
|
attribute.
|
|
There is no default value.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_SCC_PROVIDER"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_SCC_PROVIDER</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string
|
|
placed in a generated Microsoft Visual Studio project file
|
|
as the value of the
|
|
<TT
|
|
CLASS="literal"
|
|
>SccProvider</TT
|
|
>
|
|
attribute.
|
|
The string is also placed in the
|
|
<TT
|
|
CLASS="literal"
|
|
>SccProvider1</TT
|
|
>
|
|
attribute of the
|
|
<TT
|
|
CLASS="literal"
|
|
>GlobalSection(SourceCodeControl)</TT
|
|
>
|
|
section of the Microsoft Visual Studio solution file.
|
|
There is no default value.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_USE_MFC_DIRS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_USE_MFC_DIRS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Tells the MS Visual Studio tool(s) to use
|
|
the MFC directories in its default paths
|
|
for compiling and linking.
|
|
The <CODE
|
|
CLASS="envar"
|
|
>$MSVS_USE_MFC_DIRS</CODE
|
|
> variable has no effect if the
|
|
<CODE
|
|
CLASS="envar"
|
|
>INCLUDE</CODE
|
|
>
|
|
or
|
|
<CODE
|
|
CLASS="envar"
|
|
>LIB</CODE
|
|
>
|
|
environment variables are set explictly.</P
|
|
><P
|
|
>Under Visual Studio version 6,
|
|
setting
|
|
<CODE
|
|
CLASS="envar"
|
|
>$MSVS_USE_MFC_DIRS</CODE
|
|
>
|
|
to a non-zero value
|
|
adds the
|
|
<TT
|
|
CLASS="filename"
|
|
>ATL\include</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>MFC\include</TT
|
|
>
|
|
directories to
|
|
the default
|
|
<CODE
|
|
CLASS="envar"
|
|
>INCLUDE</CODE
|
|
>
|
|
external environment variable,
|
|
and adds the
|
|
<TT
|
|
CLASS="filename"
|
|
>MFC\lib</TT
|
|
>
|
|
directory to
|
|
the default
|
|
<CODE
|
|
CLASS="envar"
|
|
>LIB</CODE
|
|
>
|
|
external environment variable.</P
|
|
><P
|
|
>Under Visual Studio version 7,
|
|
setting
|
|
<CODE
|
|
CLASS="envar"
|
|
>$MSVS_USE_MFC_DIRS</CODE
|
|
>
|
|
to a non-zero value
|
|
adds the
|
|
<TT
|
|
CLASS="filename"
|
|
>atlmfc\include</TT
|
|
>
|
|
directory to the default
|
|
<CODE
|
|
CLASS="envar"
|
|
>INCLUDE</CODE
|
|
>
|
|
external environment variable,
|
|
and adds the
|
|
<TT
|
|
CLASS="filename"
|
|
>atlmfc\lib</TT
|
|
>
|
|
directory to the default
|
|
<CODE
|
|
CLASS="envar"
|
|
>LIB</CODE
|
|
>
|
|
external environment variable.</P
|
|
><P
|
|
>Under Visual Studio version 8,
|
|
setting
|
|
<CODE
|
|
CLASS="envar"
|
|
>$MSVS_USE_MFC_DIRS</CODE
|
|
>
|
|
to a non-zero value will,
|
|
by default,
|
|
add the
|
|
<TT
|
|
CLASS="filename"
|
|
>atlmfc\include</TT
|
|
>
|
|
directory to the default
|
|
<CODE
|
|
CLASS="envar"
|
|
>INCLUDE</CODE
|
|
>
|
|
external environment variable,
|
|
and the
|
|
<TT
|
|
CLASS="filename"
|
|
>atlmfc\lib</TT
|
|
>
|
|
directory to the default
|
|
<CODE
|
|
CLASS="envar"
|
|
>LIB</CODE
|
|
>
|
|
external environment variable.
|
|
If, however, the
|
|
<CODE
|
|
CLASS="envar"
|
|
>['MSVS']['PLATFORMSDKDIR']</CODE
|
|
>
|
|
variable is set,
|
|
then the
|
|
<TT
|
|
CLASS="filename"
|
|
>mfc</TT
|
|
>
|
|
and the
|
|
<TT
|
|
CLASS="filename"
|
|
>atl</TT
|
|
>
|
|
subdirectories of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>PLATFORMSDKDIR</CODE
|
|
>
|
|
are added to the default value of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>INCLUDE</CODE
|
|
>
|
|
external environment variable,
|
|
and the default value of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>LIB</CODE
|
|
>
|
|
external environment variable is left untouched.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVS_VERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVS_VERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets the preferred version of MSVS to use.</P
|
|
><P
|
|
>SCons will (by default) select the latest version of MSVS
|
|
installed on your machine.
|
|
So, if you have version 6 and version 7 (MSVS .NET) installed,
|
|
it will prefer version 7.
|
|
You can override this by
|
|
specifying the
|
|
<CODE
|
|
CLASS="envar"
|
|
>MSVS_VERSION</CODE
|
|
>
|
|
variable in the Environment initialization, setting it to the
|
|
appropriate version ('6.0' or '7.0', for example).
|
|
If the given version isn't installed, tool initialization will fail.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSBUILDCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSBUILDCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The build command line placed in
|
|
a generated Microsoft Visual Studio project file.
|
|
The default is to have Visual Studio invoke SCons with any specified
|
|
build targets.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSCLEANCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSCLEANCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The clean command line placed in
|
|
a generated Microsoft Visual Studio project file.
|
|
The default is to have Visual Studio invoke SCons with the -c option
|
|
to remove any specified targets.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSENCODING"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSENCODING</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The encoding string placed in
|
|
a generated Microsoft Visual Studio project file.
|
|
The default is encoding
|
|
<TT
|
|
CLASS="literal"
|
|
>Windows-1252</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSPROJECTCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSPROJECTCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The action used to generate Microsoft Visual Studio project files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSPROJECTSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSPROJECTSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for Microsoft Visual Studio project (DSP) files.
|
|
The default value is
|
|
<TT
|
|
CLASS="filename"
|
|
>.vcproj</TT
|
|
>
|
|
when using Visual Studio version 7.x (.NET)
|
|
or later version,
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>.dsp</TT
|
|
>
|
|
when using earlier versions of Visual Studio.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSREBUILDCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSREBUILDCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The rebuild command line placed in
|
|
a generated Microsoft Visual Studio project file.
|
|
The default is to have Visual Studio invoke SCons with any specified
|
|
rebuild targets.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSSCONS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSSCONS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The SCons used in generated Microsoft Visual Studio project files.
|
|
The default is the version of SCons being
|
|
used to generate the project file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSSCONSCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSSCONSCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The default SCons command used in generated Microsoft Visual Studio
|
|
project files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSSCONSCRIPT"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSSCONSCRIPT</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The sconscript file
|
|
(that is,
|
|
<TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
>
|
|
or
|
|
<TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>
|
|
file)
|
|
that will be invoked by Visual Studio
|
|
project files
|
|
(through the
|
|
<A
|
|
HREF="#cv-MSVSSCONSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSCONSCOM</CODE
|
|
></A
|
|
>
|
|
variable).
|
|
The default is the same sconscript file
|
|
that contains the call to
|
|
<CODE
|
|
CLASS="function"
|
|
>MSVSProject</CODE
|
|
>
|
|
to build the project file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSSCONSFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSSCONSFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The SCons flags used in generated Microsoft Visual Studio
|
|
project files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSSOLUTIONCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSSOLUTIONCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The action used to generate Microsoft Visual Studio solution files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MSVSSOLUTIONSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MSVSSOLUTIONSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for Microsoft Visual Studio solution (DSW) files.
|
|
The default value is
|
|
<TT
|
|
CLASS="filename"
|
|
>.sln</TT
|
|
>
|
|
when using Visual Studio version 7.x (.NET),
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>.dsw</TT
|
|
>
|
|
when using earlier versions of Visual Studio.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MWCW_VERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MWCW_VERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The version number of the MetroWerks CodeWarrior C compiler
|
|
to be used.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-MWCW_VERSIONS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>MWCW_VERSIONS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A list of installed versions of the MetroWerks CodeWarrior C compiler
|
|
on this system.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-NAME"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>NAME</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specfies the name of the project to package.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-no_import_lib"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>no_import_lib</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> When set to non-zero,
|
|
suppresses creation of a corresponding Windows static import lib by the
|
|
<TT
|
|
CLASS="literal"
|
|
>SharedLibrary</TT
|
|
>
|
|
builder when used with
|
|
MinGW, Microsoft Visual Studio or Metrowerks.
|
|
This also suppresses creation
|
|
of an export (.exp) file
|
|
when using Microsoft Visual Studio.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-OBJPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>OBJPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for (static) object file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-OBJSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>OBJSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for (static) object file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-P4"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>P4</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Perforce executable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-P4COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>P4COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to
|
|
fetch source files from Perforce.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-P4COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>P4COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when
|
|
fetching a source file from Perforce.
|
|
If this is not set, then <A
|
|
HREF="#cv-P4COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$P4COM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-P4FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>P4FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options that are passed to Perforce.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PACKAGEROOT"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PACKAGEROOT</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specifies the directory where all files in resulting archive will be
|
|
placed if applicable. The default value is "$NAME-$VERSION".
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PACKAGETYPE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PACKAGETYPE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Selects the package type to build. Currently these are available:</P
|
|
><P
|
|
> * msi - Microsoft Installer
|
|
* rpm - Redhat Package Manger
|
|
* ipkg - Itsy Package Management System
|
|
* tarbz2 - compressed tar
|
|
* targz - compressed tar
|
|
* zip - zip file
|
|
* src_tarbz2 - compressed tar source
|
|
* src_targz - compressed tar source
|
|
* src_zip - zip file source</P
|
|
><P
|
|
>This may be overridden with the "package_type" command line option.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PACKAGEVERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PACKAGEVERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The version of the package (not the underlying project).
|
|
This is currently only used by the rpm packager
|
|
and should reflect changes in the packaging,
|
|
not the underlying project code itself.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PCH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PCH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Microsoft Visual C++ precompiled header that will be used when compiling
|
|
object files. This variable is ignored by tools other than Microsoft Visual C++.
|
|
When this variable is
|
|
defined SCons will add options to the compiler command line to
|
|
cause it to use the precompiled header, and will also set up the
|
|
dependencies for the PCH file.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['PCH'] = 'StdAfx.pch'
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PCHCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PCHCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used by the
|
|
<CODE
|
|
CLASS="function"
|
|
>PCH</CODE
|
|
>
|
|
builder to generated a precompiled header.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PCHCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PCHCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when generating a precompiled header.
|
|
If this is not set, then <A
|
|
HREF="#cv-PCHCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PCHCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PCHPDBFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PCHPDBFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A construction variable that, when expanded,
|
|
adds the <TT
|
|
CLASS="literal"
|
|
>/yD</TT
|
|
> flag to the command line
|
|
only if the <CODE
|
|
CLASS="envar"
|
|
>$PDB</CODE
|
|
> construction variable is set.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PCHSTOP"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PCHSTOP</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This variable specifies how much of a source file is precompiled. This
|
|
variable is ignored by tools other than Microsoft Visual C++, or when
|
|
the PCH variable is not being used. When this variable is define it
|
|
must be a string that is the name of the header that
|
|
is included at the end of the precompiled portion of the source files, or
|
|
the empty string if the "#pragma hrdstop" construct is being used:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['PCHSTOP'] = 'StdAfx.h'
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDB"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDB</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Microsoft Visual C++ PDB file that will store debugging information for
|
|
object files, shared libraries, and programs. This variable is ignored by
|
|
tools other than Microsoft Visual C++.
|
|
When this variable is
|
|
defined SCons will add options to the compiler and linker command line to
|
|
cause them to generate external debugging information, and will also set up the
|
|
dependencies for the PDB file.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['PDB'] = 'hello.pdb'
|
|
</PRE
|
|
><P
|
|
> The Visual C++ compiler switch that SCons uses by default
|
|
to generate PDB information is <CODE
|
|
CLASS="option"
|
|
>/Z7</CODE
|
|
>.
|
|
This works correctly with parallel (<CODE
|
|
CLASS="option"
|
|
>-j</CODE
|
|
>) builds
|
|
because it embeds the debug information in the intermediate object files,
|
|
as opposed to sharing a single PDB file between multiple object files.
|
|
This is also the only way to get debug information
|
|
embedded into a static library.
|
|
Using the <CODE
|
|
CLASS="option"
|
|
>/Zi</CODE
|
|
> instead may yield improved
|
|
link-time performance,
|
|
although parallel builds will no longer work.
|
|
You can generate PDB files with the <CODE
|
|
CLASS="option"
|
|
>/Zi</CODE
|
|
>
|
|
switch by overriding the default <A
|
|
HREF="#cv-CCPDBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCPDBFLAGS</CODE
|
|
></A
|
|
> variable;
|
|
see the entry for that variable for specific examples.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A deprecated synonym for <A
|
|
HREF="#cv-DVIPDFCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPDFCOM</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFLATEX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFLATEX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The <SPAN
|
|
CLASS="application"
|
|
>pdflatex</SPAN
|
|
> utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFLATEXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFLATEXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the <SPAN
|
|
CLASS="application"
|
|
>pdflatex</SPAN
|
|
> utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFLATEXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFLATEXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when calling the <SPAN
|
|
CLASS="application"
|
|
>pdflatex</SPAN
|
|
> utility.
|
|
If this is not set, then <A
|
|
HREF="#cv-PDFLATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(PDFLATEX;COMSTR = "Building $TARGET from LaTeX input $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFLATEXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFLATEXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the <SPAN
|
|
CLASS="application"
|
|
>pdflatex</SPAN
|
|
> utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for PDF file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for PDF file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFTEX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFTEX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The <SPAN
|
|
CLASS="application"
|
|
>pdftex</SPAN
|
|
> utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFTEXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFTEXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the <SPAN
|
|
CLASS="application"
|
|
>pdftex</SPAN
|
|
> utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFTEXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFTEXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when calling the <SPAN
|
|
CLASS="application"
|
|
>pdftex</SPAN
|
|
> utility.
|
|
If this is not set, then <A
|
|
HREF="#cv-PDFTEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFTEXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(PDFTEXCOMSTR = "Building $TARGET from TeX input $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PDFTEXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PDFTEXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the <SPAN
|
|
CLASS="application"
|
|
>pdftex</SPAN
|
|
> utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PKGCHK"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PKGCHK</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Solaris systems,
|
|
the package-checking program that will
|
|
be used (along with <CODE
|
|
CLASS="envar"
|
|
>$PKGINFO</CODE
|
|
>)
|
|
to look for installed versions of
|
|
the Sun PRO C++ compiler.
|
|
The default is
|
|
<TT
|
|
CLASS="filename"
|
|
>/usr/sbin/pgkchk</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PKGINFO"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PKGINFO</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On Solaris systems,
|
|
the package information program that will
|
|
be used (along with <CODE
|
|
CLASS="envar"
|
|
>$PKGCHK</CODE
|
|
>)
|
|
to look for installed versions of
|
|
the Sun PRO C++ compiler.
|
|
The default is
|
|
<TT
|
|
CLASS="filename"
|
|
>pkginfo</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PLATFORM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PLATFORM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The name of the platform used to create the Environment. If no platform is
|
|
specified when the Environment is created,
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
autodetects the platform.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(tools = [])
|
|
if env['PLATFORM'] == 'cygwin':
|
|
Tool('mingw')(env)
|
|
else:
|
|
Tool('msvc')(env)
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PRINT_CMD_LINE_FUNC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PRINT_CMD_LINE_FUNC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A Python function used to print the command lines as they are executed
|
|
(assuming command printing is not disabled by the
|
|
<CODE
|
|
CLASS="option"
|
|
>-q</CODE
|
|
>
|
|
or
|
|
<CODE
|
|
CLASS="option"
|
|
>-s</CODE
|
|
>
|
|
options or their equivalents).
|
|
The function should take four arguments:
|
|
<CODE
|
|
CLASS="varname"
|
|
>s</CODE
|
|
>,
|
|
the command being executed (a string),
|
|
<CODE
|
|
CLASS="varname"
|
|
>target</CODE
|
|
>,
|
|
the target being built (file node, list, or string name(s)),
|
|
<CODE
|
|
CLASS="varname"
|
|
>source</CODE
|
|
>,
|
|
the source(s) used (file node, list, or string name(s)), and
|
|
<CODE
|
|
CLASS="varname"
|
|
>env</CODE
|
|
>,
|
|
the environment being used.</P
|
|
><P
|
|
>The function must do the printing itself. The default implementation,
|
|
used if this variable is not set or is None, is:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def print_cmd_line(s, target, source, env):
|
|
sys.stdout.write(s + "\n")
|
|
</PRE
|
|
><P
|
|
> Here's an example of a more interesting function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def print_cmd_line(s, target, source, env):
|
|
sys.stdout.write("Building %s -> %s...\n" %
|
|
(' and '.join([str(x) for x in source]),
|
|
' and '.join([str(x) for x in target])))
|
|
env=Environment(PRINT_CMD_LINE_FUNC=print_cmd_line)
|
|
env.Program('foo', 'foo.c')
|
|
</PRE
|
|
><P
|
|
> This just prints "Building <CODE
|
|
CLASS="varname"
|
|
>targetname</CODE
|
|
> from <CODE
|
|
CLASS="varname"
|
|
>sourcename</CODE
|
|
>..." instead
|
|
of the actual commands.
|
|
Such a function could also log the actual commands to a log file,
|
|
for example.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PROGPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PROGPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for executable file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PROGSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PROGSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for executable file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PSCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PSCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to convert TeX DVI files into a PostScript file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PSCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PSCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a TeX DVI file
|
|
is converted into a PostScript file.
|
|
If this is not set, then <A
|
|
HREF="#cv-PSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PSCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PSPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PSPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for PostScript file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-PSSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>PSSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for PostScript file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_AUTOSCAN"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_AUTOSCAN</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Turn off scanning for mocable files. Use the Moc Builder to explicitely
|
|
specify files to run moc on.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_BINPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_BINPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The path where the qt binaries are installed.
|
|
The default value is '<A
|
|
HREF="#cv-QTDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QTDIR</CODE
|
|
></A
|
|
>/bin'.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_CPPPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_CPPPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The path where the qt header files are installed.
|
|
The default value is '<A
|
|
HREF="#cv-QTDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QTDIR</CODE
|
|
></A
|
|
>/include'.
|
|
Note: If you set this variable to None,
|
|
the tool won't change the <A
|
|
HREF="#cv-CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_DEBUG"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_DEBUG</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Prints lots of debugging information while scanning for moc files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_LIB"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_LIB</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is 'qt'. You may want to set this to 'qt-mt'. Note: If you set
|
|
this variable to None, the tool won't change the <A
|
|
HREF="#cv-LIBS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
></A
|
|
> variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_LIBPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_LIBPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The path where the qt libraries are installed.
|
|
The default value is '<A
|
|
HREF="#cv-QTDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QTDIR</CODE
|
|
></A
|
|
>/lib'.
|
|
Note: If you set this variable to None,
|
|
the tool won't change the <A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '<A
|
|
HREF="#cv-QT_BINPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_BINPATH</CODE
|
|
></A
|
|
>/moc'.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCCXXPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCCXXPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is ''. Prefix for moc output files, when source is a cxx file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCCXXSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCCXXSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '.moc'. Suffix for moc output files, when source is a cxx
|
|
file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCFROMCXXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCFROMCXXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Command to generate a moc file from a cpp file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCFROMCXXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCFROMCXXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when generating a moc file from a cpp file.
|
|
If this is not set, then <A
|
|
HREF="#cv-QT_MOCFROMCXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCFROMCXXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCFROMCXXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCFROMCXXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '-i'. These flags are passed to moc, when moccing a
|
|
C++ file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCFROMHCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCFROMHCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Command to generate a moc file from a header.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCFROMHCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCFROMHCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when generating a moc file from a cpp file.
|
|
If this is not set, then <A
|
|
HREF="#cv-QT_MOCFROMHCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCFROMHCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCFROMHFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCFROMHFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is ''. These flags are passed to moc, when moccing a header
|
|
file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCHPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCHPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is 'moc_'. Prefix for moc output files, when source is a header.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_MOCHSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_MOCHSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '<A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
>'. Suffix for moc output files, when source is
|
|
a header.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UIC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UIC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '<A
|
|
HREF="#cv-QT_BINPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_BINPATH</CODE
|
|
></A
|
|
>/uic'.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Command to generate header files from .ui files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when generating header files from .ui files.
|
|
If this is not set, then <A
|
|
HREF="#cv-QT_UICCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICDECLFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICDECLFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is ''. These flags are passed to uic, when creating a a h
|
|
file from a .ui file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICDECLPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICDECLPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is ''. Prefix for uic generated header files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICDECLSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICDECLSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '.h'. Suffix for uic generated header files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICIMPLFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICIMPLFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is ''. These flags are passed to uic, when creating a cxx
|
|
file from a .ui file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICIMPLPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICIMPLPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is 'uic_'. Prefix for uic generated implementation files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UICIMPLSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UICIMPLSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '<A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
>'. Suffix for uic generated implementation
|
|
files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QT_UISUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QT_UISUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Default value is '.ui'. Suffix of designer input files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-QTDIR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>QTDIR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The qt tool tries to take this from os.environ.
|
|
It also initializes all QT_*
|
|
construction variables listed below.
|
|
(Note that all paths are constructed
|
|
with python's os.path.join() method,
|
|
but are listed here with the '/' separator
|
|
for easier reading.)
|
|
In addition, the construction environment
|
|
variables <A
|
|
HREF="#cv-CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-LIBS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
></A
|
|
> may be modified
|
|
and the variables
|
|
PROGEMITTER, SHLIBEMITTER and LIBEMITTER
|
|
are modified. Because the build-performance is affected when using this tool,
|
|
you have to explicitly specify it at Environment creation:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> Environment(tools=['default','qt'])
|
|
</PRE
|
|
><P
|
|
> The qt tool supports the following operations:</P
|
|
><P
|
|
><SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>Automatic moc file generation from header files.</I
|
|
></SPAN
|
|
>
|
|
You do not have to specify moc files explicitly, the tool does it for you.
|
|
However, there are a few preconditions to do so: Your header file must have
|
|
the same filebase as your implementation file and must stay in the same
|
|
directory. It must have one of the suffixes .h, .hpp, .H, .hxx, .hh. You
|
|
can turn off automatic moc file generation by setting QT_AUTOSCAN to 0.
|
|
See also the corresponding builder method
|
|
.B Moc()</P
|
|
><P
|
|
><SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>Automatic moc file generation from cxx files.</I
|
|
></SPAN
|
|
>
|
|
As stated in the qt documentation, include the moc file at the end of
|
|
the cxx file. Note that you have to include the file, which is generated
|
|
by the transformation ${QT_MOCCXXPREFIX}<basename>${QT_MOCCXXSUFFIX}, by default
|
|
<basename>.moc. A warning is generated after building the moc file, if you
|
|
do not include the correct file. If you are using VariantDir, you may
|
|
need to specify duplicate=1. You can turn off automatic moc file generation
|
|
by setting QT_AUTOSCAN to 0. See also the corresponding
|
|
<CODE
|
|
CLASS="function"
|
|
>Moc</CODE
|
|
>
|
|
builder method.</P
|
|
><P
|
|
><SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>Automatic handling of .ui files.</I
|
|
></SPAN
|
|
>
|
|
The implementation files generated from .ui files are handled much the same
|
|
as yacc or lex files. Each .ui file given as a source of Program, Library or
|
|
SharedLibrary will generate three files, the declaration file, the
|
|
implementation file and a moc file. Because there are also generated headers,
|
|
you may need to specify duplicate=1 in calls to VariantDir.
|
|
See also the corresponding
|
|
<CODE
|
|
CLASS="function"
|
|
>Uic</CODE
|
|
>
|
|
builder method.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RANLIB"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RANLIB</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The archive indexer.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RANLIBCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RANLIBCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to index a static library archive.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RANLIBCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RANLIBCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a static library archive is indexed.
|
|
If this is not set, then <A
|
|
HREF="#cv-RANLIBCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RANLIBCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(RANLIBCOMSTR = "Indexing $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RANLIBFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RANLIBFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the archive indexer.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The resource compiler used to build
|
|
a Microsoft Visual C++ resource file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to build
|
|
a Microsoft Visual C++ resource file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when invoking the resource compiler
|
|
to build a Microsoft Visual C++ resource file.
|
|
If this is not set, then <A
|
|
HREF="#cv-RCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The flags passed to the resource compiler by the RES builder.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCINCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCINCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the command-line options
|
|
for specifying directories to be searched
|
|
by the resource compiler.
|
|
The value of <CODE
|
|
CLASS="envar"
|
|
>$RCINCFLAGS</CODE
|
|
> is created
|
|
by appending <CODE
|
|
CLASS="envar"
|
|
>$RCINCPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$RCINCSUFFIX</CODE
|
|
>
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCINCPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCINCPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix (flag) used to specify an include directory
|
|
on the resource compiler command line.
|
|
This will be appended to the beginning of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$RCINCFLAGS</CODE
|
|
> variable is expanded.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCINCSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCINCSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify an include directory
|
|
on the resource compiler command line.
|
|
This will be appended to the end of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$RCINCFLAGS</CODE
|
|
> variable is expanded.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The RCS executable.
|
|
Note that this variable is not actually used
|
|
for the command to fetch source files from RCS;
|
|
see the
|
|
<A
|
|
HREF="#cv-RCS_CO"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS_CO</CODE
|
|
></A
|
|
>
|
|
construction variable, below.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCS_CO"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCS_CO</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The RCS "checkout" executable,
|
|
used to fetch source files from RCS.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCS_COCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCS_COCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to
|
|
fetch (checkout) source files from RCS.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCS_COCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCS_COCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when fetching
|
|
a source file from RCS.
|
|
If this is not set, then <A
|
|
HREF="#cv-RCS_COCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS_COCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RCS_COFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RCS_COFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the <A
|
|
HREF="#cv-RCS_CO"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS_CO</CODE
|
|
></A
|
|
> command.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RDirs"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RDirs</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A function that converts a string into a list of Dir instances by
|
|
searching the repositories.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-REGSVR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>REGSVR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The program used on Windows systems
|
|
to register a newly-built DLL library
|
|
whenever the <CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
> builder
|
|
is passed a keyword argument of <TT
|
|
CLASS="literal"
|
|
>register=1</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-REGSVRCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>REGSVRCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used on Windows systems
|
|
to register a newly-built DLL library
|
|
whenever the <CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
> builder
|
|
is passed a keyword argument of <TT
|
|
CLASS="literal"
|
|
>register=1</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-REGSVRCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>REGSVRCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when registering a newly-built DLL file.
|
|
If this is not set, then <A
|
|
HREF="#cv-REGSVRCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVRCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-REGSVRFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>REGSVRFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Flags passed to the DLL registration program
|
|
on Windows systems when a newly-built DLL library is registered.
|
|
By default,
|
|
this includes the <CODE
|
|
CLASS="option"
|
|
>/s</CODE
|
|
>
|
|
that prevents dialog boxes from popping up
|
|
and requiring user attention.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RMIC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RMIC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Java RMI stub compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RMICCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RMICCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile stub
|
|
and skeleton class files
|
|
from Java classes that contain RMI implementations.
|
|
Any options specified in the <A
|
|
HREF="#cv-RMICFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RMICFLAGS</CODE
|
|
></A
|
|
> construction variable
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RMICCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RMICCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when compiling
|
|
stub and skeleton class files
|
|
from Java classes that contain RMI implementations.
|
|
If this is not set, then <A
|
|
HREF="#cv-RMICCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RMICCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(RMICCOMSTR = "Generating stub/skeleton class files $TARGETS from $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RMICFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RMICFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the Java RMI stub compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_RPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_RPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the rpath flags to be used when linking
|
|
a program with shared libraries.
|
|
The value of <CODE
|
|
CLASS="envar"
|
|
>$_RPATH</CODE
|
|
> is created
|
|
by appending <CODE
|
|
CLASS="envar"
|
|
>$RPATHPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$RPATHSUFFIX</CODE
|
|
>
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$RPATH</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A list of paths to search for shared libraries when running programs.
|
|
Currently only used in the GNU (gnulink),
|
|
IRIX (sgilink) and Sun (sunlink) linkers.
|
|
Ignored on platforms and toolchains that don't support it.
|
|
Note that the paths added to RPATH
|
|
are not transformed by
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
in any way: if you want an absolute
|
|
path, you must make it absolute yourself.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPATHPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPATHPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used to specify a directory to be searched for
|
|
shared libraries when running programs.
|
|
This will be appended to the beginning of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$RPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_RPATH</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPATHSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPATHSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify a directory to be searched for
|
|
shared libraries when running programs.
|
|
This will be appended to the end of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$RPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_RPATH</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPCGEN"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPCGEN</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The RPC protocol compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPCGENCLIENTFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPCGENCLIENTFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options passed to the RPC protocol compiler
|
|
when generating client side stubs.
|
|
These are in addition to any flags specified in the
|
|
<A
|
|
HREF="#cv-RPCGENFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPCGENFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPCGENFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the RPC protocol compiler.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPCGENHEADERFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPCGENHEADERFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options passed to the RPC protocol compiler
|
|
when generating a header file.
|
|
These are in addition to any flags specified in the
|
|
<A
|
|
HREF="#cv-RPCGENFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPCGENSERVICEFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPCGENSERVICEFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options passed to the RPC protocol compiler
|
|
when generating server side stubs.
|
|
These are in addition to any flags specified in the
|
|
<A
|
|
HREF="#cv-RPCGENFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-RPCGENXDRFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>RPCGENXDRFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options passed to the RPC protocol compiler
|
|
when generating XDR routines.
|
|
These are in addition to any flags specified in the
|
|
<A
|
|
HREF="#cv-RPCGENFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SCANNERS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SCANNERS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A list of the available implicit dependency scanners.
|
|
New file scanners may be added by
|
|
appending to this list,
|
|
although the more flexible approach
|
|
is to associate scanners
|
|
with a specific Builder.
|
|
See the sections "Builder Objects"
|
|
and "Scanner Objects,"
|
|
below, for more information.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SCCS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SCCS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The SCCS executable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SCCSCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SCCSCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to
|
|
fetch source files from SCCS.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SCCSCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SCCSCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when fetching
|
|
a source file from a CVS repository.
|
|
If this is not set, then <A
|
|
HREF="#cv-SCCSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SCCSCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SCCSFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SCCSFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options that are passed to SCCS.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SCCSGETFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SCCSGETFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed specifically to the SCCS "get" subcommand.
|
|
This can be set, for example, to
|
|
<CODE
|
|
CLASS="option"
|
|
>-e</CODE
|
|
>
|
|
to check out editable files from SCCS.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SCONS_HOME"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SCONS_HOME</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The (optional) path to the SCons library directory,
|
|
initialized from the external environment.
|
|
If set, this is used to construct a shorter and more
|
|
efficient search path in the
|
|
<A
|
|
HREF="#cv-MSVSSCONS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSCONS</CODE
|
|
></A
|
|
>
|
|
command line executed
|
|
from Microsoft Visual Studio project files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The C compiler used for generating shared-library objects.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCCCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCCCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a C source file
|
|
to a shared-library object file.
|
|
Any options specified in the <A
|
|
HREF="#cv-SHCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCFLAGS</CODE
|
|
></A
|
|
>,
|
|
<A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCCCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCCCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a C source file
|
|
is compiled to a shared object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHCCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(SHCCCOMSTR = "Compiling shared object $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the C and C++ compilers
|
|
to generate shared-library objects.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the C compiler (only; not C++)
|
|
to generate shared-library objects.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCXX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCXX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The C++ compiler used for generating shared-library objects.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCXXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCXXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a C++ source file
|
|
to a shared-library object file.
|
|
Any options specified in the <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCXXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCXXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a C++ source file
|
|
is compiled to a shared object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHCXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(SHCXXCOMSTR = "Compiling shared object $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHCXXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHCXXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the C++ compiler
|
|
to generate shared-library objects.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHELL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHELL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A string naming the shell program that will be passed to the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$SPAWN</CODE
|
|
>
|
|
function.
|
|
See the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$SPAWN</CODE
|
|
>
|
|
construction variable for more information.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF77"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF77</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Fortran 77 compiler used for generating shared-library objects.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRAN</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default Fortran compiler
|
|
for all Fortran versions.
|
|
You only need to set <A
|
|
HREF="#cv-SHF77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77</CODE
|
|
></A
|
|
> if you need to use a specific compiler
|
|
or compiler version for Fortran 77 files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF77COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF77COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 77 source file
|
|
to a shared-library object file.
|
|
You only need to set <A
|
|
HREF="#cv-SHF77COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77COM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
command line for Fortran 77 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF77COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF77COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 77 source file
|
|
is compiled to a shared-library object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHF77COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77COM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF77FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF77FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the Fortran 77 compiler
|
|
to generated shared-library objects.
|
|
You only need to set <A
|
|
HREF="#cv-SHF77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77FLAGS</CODE
|
|
></A
|
|
> if you need to define specific
|
|
user options for Fortran 77 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the user-specified options
|
|
passed to the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF77PPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF77PPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 77 source file to a
|
|
shared-library object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified in the <A
|
|
HREF="#cv-SHF77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77FLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
You only need to set <A
|
|
HREF="#cv-SHF77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77PPCOM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
C-preprocessor command line for Fortran 77 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default C-preprocessor command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF77PPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF77PPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 77 source file
|
|
is compiled to a shared-library object file
|
|
after first running the file through the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHF77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77PPCOM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF90"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF90</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Fortran 90 compiler used for generating shared-library objects.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRAN</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default Fortran compiler
|
|
for all Fortran versions.
|
|
You only need to set <A
|
|
HREF="#cv-SHF90"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90</CODE
|
|
></A
|
|
> if you need to use a specific compiler
|
|
or compiler version for Fortran 90 files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF90COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF90COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 90 source file
|
|
to a shared-library object file.
|
|
You only need to set <A
|
|
HREF="#cv-SHF90COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90COM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
command line for Fortran 90 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF90COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF90COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 90 source file
|
|
is compiled to a shared-library object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHF90COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90COM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF90FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF90FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the Fortran 90 compiler
|
|
to generated shared-library objects.
|
|
You only need to set <A
|
|
HREF="#cv-SHF90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90FLAGS</CODE
|
|
></A
|
|
> if you need to define specific
|
|
user options for Fortran 90 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the user-specified options
|
|
passed to the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF90PPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF90PPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 90 source file to a
|
|
shared-library object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified in the <A
|
|
HREF="#cv-SHF90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90FLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
You only need to set <A
|
|
HREF="#cv-SHF90PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90PPCOM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
C-preprocessor command line for Fortran 90 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default C-preprocessor command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF90PPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF90PPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 90 source file
|
|
is compiled to a shared-library object file
|
|
after first running the file through the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHF90PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90PPCOM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF95"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF95</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The Fortran 95 compiler used for generating shared-library objects.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRAN</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default Fortran compiler
|
|
for all Fortran versions.
|
|
You only need to set <A
|
|
HREF="#cv-SHF95"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95</CODE
|
|
></A
|
|
> if you need to use a specific compiler
|
|
or compiler version for Fortran 95 files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF95COM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF95COM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 95 source file
|
|
to a shared-library object file.
|
|
You only need to set <A
|
|
HREF="#cv-SHF95COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95COM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
command line for Fortran 95 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF95COMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF95COMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 95 source file
|
|
is compiled to a shared-library object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHF95COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95COM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF95FLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF95FLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the Fortran 95 compiler
|
|
to generated shared-library objects.
|
|
You only need to set <A
|
|
HREF="#cv-SHF95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95FLAGS</CODE
|
|
></A
|
|
> if you need to define specific
|
|
user options for Fortran 95 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the user-specified options
|
|
passed to the default Fortran compiler
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF95PPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF95PPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran 95 source file to a
|
|
shared-library object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified in the <A
|
|
HREF="#cv-SHF95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95FLAGS</CODE
|
|
></A
|
|
> and <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
You only need to set <A
|
|
HREF="#cv-SHF95PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95PPCOM</CODE
|
|
></A
|
|
> if you need to use a specific
|
|
C-preprocessor command line for Fortran 95 files.
|
|
You should normally set the <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
> variable,
|
|
which specifies the default C-preprocessor command line
|
|
for all Fortran versions.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHF95PPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHF95PPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran 95 source file
|
|
is compiled to a shared-library object file
|
|
after first running the file through the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHF95PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95PPCOM</CODE
|
|
></A
|
|
> or <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHFORTRAN"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHFORTRAN</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The default Fortran compiler used for generating shared-library objects.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHFORTRANCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHFORTRANCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran source file
|
|
to a shared-library object file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHFORTRANCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHFORTRANCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran source file
|
|
is compiled to a shared-library object file.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHFORTRANFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHFORTRANFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Options that are passed to the Fortran compiler
|
|
to generate shared-library objects.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHFORTRANPPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHFORTRANPPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to compile a Fortran source file to a
|
|
shared-library object file
|
|
after first running the file through the C preprocessor.
|
|
Any options specified
|
|
in the <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
> and
|
|
<A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
> construction variables
|
|
are included on this command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHFORTRANPPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHFORTRANPPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when a Fortran source file
|
|
is compiled to a shared-library object file
|
|
after first running the file throught the C preprocessor.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHLIBPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHLIBPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for shared library file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHLIBSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHLIBSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for shared library file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHLINK"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHLINK</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The linker for programs that use shared libraries.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHLINKCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHLINKCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to link programs using shared libaries.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHLINKCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHLINKCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when programs using shared libraries are linked.
|
|
If this is not set, then <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(SHLINKCOMSTR = "Linking shared $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHLINKFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHLINKFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General user options passed to the linker for programs using shared libraries.
|
|
Note that this variable should
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
contain
|
|
<CODE
|
|
CLASS="option"
|
|
>-l</CODE
|
|
>
|
|
(or similar) options for linking with the libraries listed in <A
|
|
HREF="#cv-LIBS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBS</CODE
|
|
></A
|
|
>,
|
|
nor
|
|
<CODE
|
|
CLASS="option"
|
|
>-L</CODE
|
|
>
|
|
(or similar) include search path options
|
|
that scons generates automatically from <A
|
|
HREF="#cv-LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPATH</CODE
|
|
></A
|
|
>.
|
|
See
|
|
<A
|
|
HREF="#cv-_LIBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_LIBFLAGS</CODE
|
|
></A
|
|
>
|
|
above,
|
|
for the variable that expands to library-link options,
|
|
and
|
|
<A
|
|
HREF="#cv-_LIBDIRFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_LIBDIRFLAGS</CODE
|
|
></A
|
|
>
|
|
above,
|
|
for the variable that expands to library search path options.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHOBJPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHOBJPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for shared object file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SHOBJSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SHOBJSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for shared object file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SOURCE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SOURCE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A reserved variable name
|
|
that may not be set or used in a construction environment.
|
|
(See "Variable Substitution," below.)
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SOURCE_URL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SOURCE_URL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The URL
|
|
(web address)
|
|
of the location from which the project was retrieved.
|
|
This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Source:</TT
|
|
>
|
|
field in the controlling information for Ipkg and RPM packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SOURCES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SOURCES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A reserved variable name
|
|
that may not be set or used in a construction environment.
|
|
(See "Variable Substitution," below.)
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SPAWN"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SPAWN</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A command interpreter function that will be called to execute command line
|
|
strings. The function must expect the following arguments:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> def spawn(shell, escape, cmd, args, env):
|
|
</PRE
|
|
><P
|
|
> <CODE
|
|
CLASS="varname"
|
|
>sh</CODE
|
|
>
|
|
is a string naming the shell program to use.
|
|
<CODE
|
|
CLASS="varname"
|
|
>escape</CODE
|
|
>
|
|
is a function that can be called to escape shell special characters in
|
|
the command line.
|
|
<CODE
|
|
CLASS="varname"
|
|
>cmd</CODE
|
|
>
|
|
is the path to the command to be executed.
|
|
<CODE
|
|
CLASS="varname"
|
|
>args</CODE
|
|
>
|
|
is the arguments to the command.
|
|
<CODE
|
|
CLASS="varname"
|
|
>env</CODE
|
|
>
|
|
is a dictionary of the environment variables
|
|
in which the command should be executed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SUMMARY"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SUMMARY</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A short summary of what the project is about.
|
|
This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Summary:</TT
|
|
>
|
|
field in the controlling information for Ipkg and RPM packages,
|
|
and as the
|
|
<TT
|
|
CLASS="literal"
|
|
>Description:</TT
|
|
>
|
|
field in MSI packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIG"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIG</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The scripting language wrapper and interface generator.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGCFILESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGCFILESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix that will be used for intermediate C
|
|
source files generated by
|
|
the scripting language wrapper and interface generator.
|
|
The default value is
|
|
<TT
|
|
CLASS="filename"
|
|
>_wrap</TT
|
|
><A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
>.
|
|
By default, this value is used whenever the
|
|
<CODE
|
|
CLASS="option"
|
|
>-c++</CODE
|
|
>
|
|
option is
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>not</I
|
|
></SPAN
|
|
>
|
|
specified as part of the
|
|
<A
|
|
HREF="#cv-SWIGFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call
|
|
the scripting language wrapper and interface generator.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when calling
|
|
the scripting language wrapper and interface generator.
|
|
If this is not set, then <A
|
|
HREF="#cv-SWIGCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGCXXFILESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGCXXFILESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix that will be used for intermediate C++
|
|
source files generated by
|
|
the scripting language wrapper and interface generator.
|
|
The default value is
|
|
<TT
|
|
CLASS="filename"
|
|
>_wrap</TT
|
|
><A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
>.
|
|
By default, this value is used whenever the
|
|
<TT
|
|
CLASS="filename"
|
|
>-c++</TT
|
|
>
|
|
option is specified as part of the
|
|
<A
|
|
HREF="#cv-SWIGFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGFLAGS</CODE
|
|
></A
|
|
>
|
|
construction variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to
|
|
the scripting language wrapper and interface generator.
|
|
This is where you should set
|
|
<CODE
|
|
CLASS="option"
|
|
>-python</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>-perl5</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="option"
|
|
>-tcl</CODE
|
|
>,
|
|
or whatever other options you want to specify to SWIG.
|
|
If you set the
|
|
<CODE
|
|
CLASS="option"
|
|
>-c++</CODE
|
|
>
|
|
option in this variable,
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
will, by default,
|
|
generate a C++ intermediate source file
|
|
with the extension that is specified as the
|
|
<A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
>
|
|
variable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-_SWIGINCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>_SWIGINCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> An automatically-generated construction variable
|
|
containing the SWIG command-line options
|
|
for specifying directories to be searched for included files.
|
|
The value of <CODE
|
|
CLASS="envar"
|
|
>$_SWIGINCFLAGS</CODE
|
|
> is created
|
|
by appending <CODE
|
|
CLASS="envar"
|
|
>$SWIGINCPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$SWIGINCSUFFIX</CODE
|
|
>
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$SWIGPATH</CODE
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGINCPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGINCPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used to specify an include directory on the SWIG command line.
|
|
This will be appended to the beginning of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$SWIGPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_SWIGINCFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGINCSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGINCSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used to specify an include directory on the SWIG command line.
|
|
This will be appended to the end of each directory
|
|
in the <CODE
|
|
CLASS="envar"
|
|
>$SWIGPATH</CODE
|
|
> construction variable
|
|
when the <CODE
|
|
CLASS="envar"
|
|
>$_SWIGINCFLAGS</CODE
|
|
> variable is automatically generated.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGOUTDIR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGOUTDIR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Specifies the output directory in which
|
|
the scripting language wrapper and interface generator
|
|
should place generated language-specific files.
|
|
This will be used by SCons to identify
|
|
the files that will be generated by the <SPAN
|
|
CLASS="application"
|
|
>swig</SPAN
|
|
> call,
|
|
and translated into the
|
|
<TT
|
|
CLASS="literal"
|
|
>swig -outdir</TT
|
|
> option on the command line.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-SWIGPATH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>SWIGPATH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The list of directories that the scripting language wrapper
|
|
and interface generate will search for included files.
|
|
The SWIG implicit dependency scanner will search these
|
|
directories for include files.
|
|
The default is to use the same path
|
|
specified as <CODE
|
|
CLASS="envar"
|
|
>$CPPPATH</CODE
|
|
>.</P
|
|
><P
|
|
>Don't explicitly put include directory
|
|
arguments in SWIGFLAGS;
|
|
the result will be non-portable
|
|
and the directories will not be searched by the dependency scanner.
|
|
Note: directory names in SWIGPATH will be looked-up relative to the SConscript
|
|
directory when they are used in a command.
|
|
To force
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
to look-up a directory relative to the root of the source tree use #:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(SWIGPATH='#/include')
|
|
</PRE
|
|
><P
|
|
> The directory look-up can also be forced using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Dir</CODE
|
|
>()
|
|
function:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> include = Dir('include')
|
|
env = Environment(SWIGPATH=include)
|
|
</PRE
|
|
><P
|
|
> The directory list will be added to command lines
|
|
through the automatically-generated
|
|
<CODE
|
|
CLASS="envar"
|
|
>$_SWIGINCFLAGS</CODE
|
|
>
|
|
construction variable,
|
|
which is constructed by
|
|
appending the values of the
|
|
<CODE
|
|
CLASS="envar"
|
|
>$SWIGINCPREFIX</CODE
|
|
> and <CODE
|
|
CLASS="envar"
|
|
>$SWIGINCSUFFIX</CODE
|
|
>
|
|
construction variables
|
|
to the beginning and end
|
|
of each directory in <CODE
|
|
CLASS="envar"
|
|
>$SWIGPATH</CODE
|
|
>.
|
|
Any command lines you define that need
|
|
the SWIGPATH directory list should
|
|
include <CODE
|
|
CLASS="envar"
|
|
>$_SWIGINCFLAGS</CODE
|
|
>:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(SWIGCOM="my_swig -o $TARGET $_SWIGINCFLAGS $SORUCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TAR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TAR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The tar archiver.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TARCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TARCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the tar archiver.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TARCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TARCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when archiving files
|
|
using the tar archiver.
|
|
If this is not set, then <A
|
|
HREF="#cv-TARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(TARCOMSTR = "Archiving $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TARFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TARFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the tar archiver.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TARGET"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TARGET</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A reserved variable name
|
|
that may not be set or used in a construction environment.
|
|
(See "Variable Substitution," below.)
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TARGETS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TARGETS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A reserved variable name
|
|
that may not be set or used in a construction environment.
|
|
(See "Variable Substitution," below.)
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TARSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TARSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for tar file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TEMPFILEPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TEMPFILEPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix for a temporary file used
|
|
to execute lines longer than $MAXLINELENGTH.
|
|
The default is '@'.
|
|
This may be set for toolchains that use other values,
|
|
such as '-@' for the diab compiler
|
|
or '-via' for ARM toolchain.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TEX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TEX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The TeX formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TEXCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TEXCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the TeX formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TEXCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TEXCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when calling
|
|
the TeX formatter and typesetter.
|
|
If this is not set, then <A
|
|
HREF="#cv-TEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TEXCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(TEXCOMSTR = "Building $TARGET from TeX input $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TEXFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TEXFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the TeX formatter and typesetter.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TEXINPUTS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TEXINPUTS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> List of directories that the LaTeX programm will search
|
|
for include directories.
|
|
The LaTeX implicit dependency scanner will search these
|
|
directories for \include and \import files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-TOOLS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>TOOLS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A list of the names of the Tool specifications
|
|
that are part of this construction environment.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-VENDOR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>VENDOR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The person or organization who supply the packaged software.
|
|
This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Vendor:</TT
|
|
>
|
|
field in the controlling information for RPM packages,
|
|
and the
|
|
<TT
|
|
CLASS="literal"
|
|
>Manufacturer:</TT
|
|
>
|
|
field in the controlling information for MSI packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-VERSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>VERSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The version of the project, specified as a string.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WIN32_INSERT_DEF"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WIN32_INSERT_DEF</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A deprecated synonym for <A
|
|
HREF="#cv-WINDOWS_INSERT_DEF"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWS_INSERT_DEF</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WIN32DEFPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WIN32DEFPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A deprecated synonym for <A
|
|
HREF="#cv-WINDOWSDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSDEFPREFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WIN32DEFSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WIN32DEFSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A deprecated synonym for <A
|
|
HREF="#cv-WINDOWSDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSDEFSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WIN32EXPPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WIN32EXPPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A deprecated synonym for <A
|
|
HREF="#cv-WINDOWSEXPSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSEXPSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WIN32EXPSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WIN32EXPSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A deprecated synonym for <A
|
|
HREF="#cv-WINDOWSEXPSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSEXPSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWS_INSERT_DEF"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWS_INSERT_DEF</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> When this is set to true,
|
|
a library build of a Windows shared library
|
|
(<TT
|
|
CLASS="filename"
|
|
>.dll</TT
|
|
>file)
|
|
will also build a corresponding <TT
|
|
CLASS="filename"
|
|
>.def</TT
|
|
> file
|
|
at the same time,
|
|
if a <TT
|
|
CLASS="filename"
|
|
>.def</TT
|
|
> file
|
|
is not already listed as a build target.
|
|
The default is 0 (do not build a <TT
|
|
CLASS="filename"
|
|
>.def</TT
|
|
> file).
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWS_INSERT_MANIFEST"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWS_INSERT_MANIFEST</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> When this is set to true,
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
will be aware of the
|
|
<TT
|
|
CLASS="filename"
|
|
>.manifest</TT
|
|
>
|
|
files generated by Microsoft Visua C/C++ 8.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSDEFPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSDEFPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for Windows <TT
|
|
CLASS="filename"
|
|
>.def</TT
|
|
>file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSDEFSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSDEFSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for Windows <TT
|
|
CLASS="filename"
|
|
>.def</TT
|
|
> file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSEXPPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSEXPPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for Windows <TT
|
|
CLASS="filename"
|
|
>.exp</TT
|
|
> file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSEXPSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSEXPSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for Windows <TT
|
|
CLASS="filename"
|
|
>.exp</TT
|
|
> file names.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSPROGMANIFESTPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSPROGMANIFESTPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for executable program <TT
|
|
CLASS="filename"
|
|
>.manifest</TT
|
|
> files
|
|
generated by Microsoft Visual C/C++.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSPROGMANIFESTSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSPROGMANIFESTSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for executable program <TT
|
|
CLASS="filename"
|
|
>.manifest</TT
|
|
> files
|
|
generated by Microsoft Visual C/C++.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSSHLIBMANIFESTPREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSSHLIBMANIFESTPREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The prefix used for shared library <TT
|
|
CLASS="filename"
|
|
>.manifest</TT
|
|
> files
|
|
generated by Microsoft Visual C/C++.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-WINDOWSSHLIBMANIFESTSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>WINDOWSSHLIBMANIFESTSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for shared library <TT
|
|
CLASS="filename"
|
|
>.manifest</TT
|
|
> files
|
|
generated by Microsoft Visual C/C++.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_IPK_DEPENDS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_IPK_DEPENDS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Depends:</TT
|
|
>
|
|
field in the controlling information for Ipkg packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_IPK_DESCRIPTION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_IPK_DESCRIPTION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Description:</TT
|
|
>
|
|
field in the controlling information for Ipkg packages.
|
|
The default value is
|
|
<TT
|
|
CLASS="literal"
|
|
>$SUMMARY\n$DESCRIPTION</TT
|
|
>
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_IPK_MAINTAINER"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_IPK_MAINTAINER</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Maintainer:</TT
|
|
>
|
|
field in the controlling information for Ipkg packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_IPK_PRIORITY"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_IPK_PRIORITY</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Priority:</TT
|
|
>
|
|
field in the controlling information for Ipkg packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_IPK_SECTION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_IPK_SECTION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Section:</TT
|
|
>
|
|
field in the controlling information for Ipkg packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_MSI_LANGUAGE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_MSI_LANGUAGE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Language:</TT
|
|
>
|
|
attribute in the controlling information for MSI packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_MSI_LICENSE_TEXT"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_MSI_LICENSE_TEXT</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The text of the software license in RTF format.
|
|
Carriage return characters will be
|
|
replaced with the RTF equivalent \\par.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_MSI_UPGRADE_CODE"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_MSI_UPGRADE_CODE</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> TODO
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_AUTOREQPROV"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_AUTOREQPROV</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>AutoReqProv:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_BUILD"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_BUILD</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> internal, but overridable
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_BUILDREQUIRES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_BUILDREQUIRES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>BuildRequires:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_BUILDROOT"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_BUILDROOT</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> internal, but overridable
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_CLEAN"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_CLEAN</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> internal, but overridable
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_CONFLICTS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_CONFLICTS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Conflicts:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_DEFATTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_DEFATTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This value is used as the default attributes
|
|
for the files in the RPM package.
|
|
The default value is
|
|
<TT
|
|
CLASS="literal"
|
|
>(-,root,root)</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_DISTRIBUTION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_DISTRIBUTION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Distribution:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_EPOCH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_EPOCH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Epoch:</TT
|
|
>
|
|
field in the controlling information for RPM packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_EXCLUDEARCH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_EXCLUDEARCH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>ExcludeArch:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_EXLUSIVEARCH"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_EXLUSIVEARCH</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>ExclusiveArch:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_GROUP"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_GROUP</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Group:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_GROUP_lang"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_GROUP_lang</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Group(lang):</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
Note that
|
|
<CODE
|
|
CLASS="varname"
|
|
>lang</CODE
|
|
>
|
|
is not literal
|
|
and should be replaced by
|
|
the appropriate language code.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_ICON"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_ICON</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Icon:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_INSTALL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_INSTALL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> internal, but overridable
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_PACKAGER"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_PACKAGER</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Packager:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_POSTINSTALL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_POSTINSTALL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>%post:</TT
|
|
>
|
|
section in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_POSTUNINSTALL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_POSTUNINSTALL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>%postun:</TT
|
|
>
|
|
section in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_PREFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_PREFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Prefix:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_PREINSTALL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_PREINSTALL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>%pre:</TT
|
|
>
|
|
section in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_PREP"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_PREP</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> internal, but overridable
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_PREUNINSTALL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_PREUNINSTALL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>%preun:</TT
|
|
>
|
|
section in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_PROVIDES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_PROVIDES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Provides:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_REQUIRES"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_REQUIRES</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Requires:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_SERIAL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_SERIAL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Serial:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-X_RPM_URL"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>X_RPM_URL</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> This is used to fill in the
|
|
<TT
|
|
CLASS="literal"
|
|
>Url:</TT
|
|
>
|
|
field in the RPM
|
|
<TT
|
|
CLASS="filename"
|
|
>.spec</TT
|
|
> file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-YACC"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>YACC</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The parser generator.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-YACCCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>YACCCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the parser generator
|
|
to generate a source file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-YACCCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>YACCCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when generating a source file
|
|
using the parser generator.
|
|
If this is not set, then <A
|
|
HREF="#cv-YACCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCCOM</CODE
|
|
></A
|
|
> (the command line) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(YACCCOMSTR = "Yacc'ing $TARGET from $SOURCES")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-YACCFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>YACCFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the parser generator.
|
|
If <A
|
|
HREF="#cv-YACCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCFLAGS</CODE
|
|
></A
|
|
> contains a <CODE
|
|
CLASS="option"
|
|
>-d</CODE
|
|
> option,
|
|
SCons assumes that the call will also create a .h file
|
|
(if the yacc source file ends in a .y suffix)
|
|
or a .hpp file
|
|
(if the yacc source file ends in a .yy suffix)
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-YACCHFILESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>YACCHFILESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix of the C
|
|
header file generated by the parser generator
|
|
when the
|
|
<CODE
|
|
CLASS="option"
|
|
>-d</CODE
|
|
>
|
|
option is used.
|
|
Note that setting this variable does not cause
|
|
the parser generator to generate a header
|
|
file with the specified suffix,
|
|
it exists to allow you to specify
|
|
what suffix the parser generator will use of its own accord.
|
|
The default value is
|
|
<TT
|
|
CLASS="filename"
|
|
>.h</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-YACCHXXFILESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>YACCHXXFILESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix of the C++
|
|
header file generated by the parser generator
|
|
when the
|
|
<CODE
|
|
CLASS="option"
|
|
>-d</CODE
|
|
>
|
|
option is used.
|
|
Note that setting this variable does not cause
|
|
the parser generator to generate a header
|
|
file with the specified suffix,
|
|
it exists to allow you to specify
|
|
what suffix the parser generator will use of its own accord.
|
|
The default value is
|
|
<TT
|
|
CLASS="filename"
|
|
>.hpp</TT
|
|
>,
|
|
except on Mac OS X,
|
|
where the default is
|
|
<TT
|
|
CLASS="filename"
|
|
>${TARGET.suffix}.h</TT
|
|
>.
|
|
because the default <SPAN
|
|
CLASS="application"
|
|
>bison</SPAN
|
|
> parser generator just
|
|
appends <TT
|
|
CLASS="filename"
|
|
>.h</TT
|
|
>
|
|
to the name of the generated C++ file.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-YACCVCGFILESUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>YACCVCGFILESUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix of the file
|
|
containing the VCG grammar automaton definition
|
|
when the
|
|
<CODE
|
|
CLASS="option"
|
|
>--graph=</CODE
|
|
>
|
|
option is used.
|
|
Note that setting this variable does not cause
|
|
the parser generator to generate a VCG
|
|
file with the specified suffix,
|
|
it exists to allow you to specify
|
|
what suffix the parser generator will use of its own accord.
|
|
The default value is
|
|
<TT
|
|
CLASS="filename"
|
|
>.vcg</TT
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ZIP"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ZIP</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The zip compression and file packaging utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ZIPCOM"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ZIPCOM</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The command line used to call the zip utility,
|
|
or the internal Python function used to create a
|
|
zip archive.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ZIPCOMPRESSION"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ZIPCOMPRESSION</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The
|
|
<CODE
|
|
CLASS="varname"
|
|
>compression</CODE
|
|
>
|
|
flag
|
|
from the Python
|
|
<TT
|
|
CLASS="filename"
|
|
>zipfile</TT
|
|
>
|
|
module used by the internal Python function
|
|
to control whether the zip archive
|
|
is compressed or not.
|
|
The default value is
|
|
<TT
|
|
CLASS="literal"
|
|
>zipfile.ZIP_DEFLATED</TT
|
|
>,
|
|
which creates a compressed zip archive.
|
|
This value has no effect when using Python 1.5.2
|
|
or if the
|
|
<TT
|
|
CLASS="literal"
|
|
>zipfile</TT
|
|
>
|
|
module is otherwise unavailable.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ZIPCOMSTR"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ZIPCOMSTR</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The string displayed when archiving files
|
|
using the zip utility.
|
|
If this is not set, then <A
|
|
HREF="#cv-ZIPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ZIPCOM</CODE
|
|
></A
|
|
>
|
|
(the command line or internal Python function) is displayed.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(ZIPCOMSTR = "Zipping $TARGET")
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ZIPFLAGS"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ZIPFLAGS</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> General options passed to the zip utility.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="cv-ZIPSUFFIX"
|
|
></A
|
|
><CODE
|
|
CLASS="envar"
|
|
>ZIPSUFFIX</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> The suffix used for zip file names.
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="appendix"
|
|
><HR><H1
|
|
><A
|
|
NAME="app-builders"
|
|
></A
|
|
>Appendix B. Builders</H1
|
|
><P
|
|
>
|
|
This appendix contains descriptions of all of the
|
|
Builders that are <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>potentially</I
|
|
></SPAN
|
|
>
|
|
available "out of the box" in this version of SCons.
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
><A
|
|
NAME="b-CFile"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>CFile()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.CFile()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a C source file given a lex (<TT
|
|
CLASS="filename"
|
|
>.l</TT
|
|
>)
|
|
or yacc (<TT
|
|
CLASS="filename"
|
|
>.y</TT
|
|
>) input file.
|
|
The suffix specified by the <A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
> construction variable
|
|
(<TT
|
|
CLASS="filename"
|
|
>.c</TT
|
|
> by default)
|
|
is automatically added to the target
|
|
if it is not already present.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # builds foo.c
|
|
env.CFile(target = 'foo.c', source = 'foo.l')
|
|
# builds bar.c
|
|
env.CFile(target = 'bar', source = 'bar.y')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-CXXFile"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>CXXFile()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.CXXFile()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a C++ source file given a lex (<TT
|
|
CLASS="filename"
|
|
>.ll</TT
|
|
>)
|
|
or yacc (<TT
|
|
CLASS="filename"
|
|
>.yy</TT
|
|
>)
|
|
input file.
|
|
The suffix specified by the <A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
> construction variable
|
|
(<TT
|
|
CLASS="filename"
|
|
>.cc</TT
|
|
> by default)
|
|
is automatically added to the target
|
|
if it is not already present.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # builds foo.cc
|
|
env.CXXFile(target = 'foo.cc', source = 'foo.ll')
|
|
# builds bar.cc
|
|
env.CXXFile(target = 'bar', source = 'bar.yy')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-DVI"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>DVI()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.DVI()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a <TT
|
|
CLASS="filename"
|
|
>.dvi</TT
|
|
> file
|
|
from a <TT
|
|
CLASS="filename"
|
|
>.tex</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>.ltx</TT
|
|
> or <TT
|
|
CLASS="filename"
|
|
>.latex</TT
|
|
> input file.
|
|
If the source file suffix is <TT
|
|
CLASS="filename"
|
|
>.tex</TT
|
|
>,
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
will examine the contents of the file;
|
|
if the string
|
|
<TT
|
|
CLASS="literal"
|
|
>\documentclass</TT
|
|
>
|
|
or
|
|
<TT
|
|
CLASS="literal"
|
|
>\documentstyle</TT
|
|
>
|
|
is found, the file is assumed to be a LaTeX file and
|
|
the target is built by invoking the <A
|
|
HREF="#cv-LATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOM</CODE
|
|
></A
|
|
> command line;
|
|
otherwise, the <A
|
|
HREF="#cv-TEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TEXCOM</CODE
|
|
></A
|
|
> command line is used.
|
|
If the file is a LaTeX file,
|
|
the
|
|
<CODE
|
|
CLASS="function"
|
|
>DVI</CODE
|
|
>
|
|
builder method will also examine the contents
|
|
of the
|
|
<TT
|
|
CLASS="filename"
|
|
>.aux</TT
|
|
>
|
|
file and invoke the <A
|
|
HREF="#cv-BIBTEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BIBTEX</CODE
|
|
></A
|
|
> command line
|
|
if the string
|
|
<TT
|
|
CLASS="literal"
|
|
>bibdata</TT
|
|
>
|
|
is found,
|
|
start <A
|
|
HREF="#cv-MAKEINDEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MAKEINDEX</CODE
|
|
></A
|
|
> to generate an index if a
|
|
<TT
|
|
CLASS="filename"
|
|
>.ind</TT
|
|
>
|
|
file is found
|
|
and will examine the contents
|
|
<TT
|
|
CLASS="filename"
|
|
>.log</TT
|
|
>
|
|
file and re-run the <A
|
|
HREF="#cv-LATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOM</CODE
|
|
></A
|
|
> command
|
|
if the log file says it is necessary.</P
|
|
><P
|
|
>The suffix <TT
|
|
CLASS="filename"
|
|
>.dvi</TT
|
|
>
|
|
(hard-coded within TeX itself)
|
|
is automatically added to the target
|
|
if it is not already present.
|
|
Examples:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # builds from aaa.tex
|
|
env.DVI(target = 'aaa.dvi', source = 'aaa.tex')
|
|
# builds bbb.dvi
|
|
env.DVI(target = 'bbb', source = 'bbb.ltx')
|
|
# builds from ccc.latex
|
|
env.DVI(target = 'ccc.dvi', source = 'ccc.latex')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Install"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Install()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Install()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Installs one or more source files or directories
|
|
in the specified target,
|
|
which must be a directory.
|
|
The names of the specified source files or directories
|
|
remain the same within the destination directory.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Install('/usr/local/bin', source = ['foo', 'bar'])
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-InstallAs"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>InstallAs()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.InstallAs()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Installs one or more source files or directories
|
|
to specific names,
|
|
allowing changing a file or directory name
|
|
as part of the installation.
|
|
It is an error if the
|
|
target
|
|
and
|
|
source
|
|
arguments list different numbers of files or directories.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.InstallAs(target = '/usr/local/bin/foo',
|
|
source = 'foo_debug')
|
|
env.InstallAs(target = ['../lib/libfoo.a', '../lib/libbar.a'],
|
|
source = ['libFOO.a', 'libBAR.a'])
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Jar"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Jar()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Jar()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a Java archive (<TT
|
|
CLASS="filename"
|
|
>.jar</TT
|
|
>) file
|
|
from the specified list of sources.
|
|
Any directories in the source list
|
|
will be searched for <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files).
|
|
Any <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files in the source list
|
|
will be compiled to <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files
|
|
by calling the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> Builder.</P
|
|
><P
|
|
>If the <A
|
|
HREF="#cv-JARCHDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JARCHDIR</CODE
|
|
></A
|
|
> value is set, the
|
|
<SPAN
|
|
CLASS="application"
|
|
>jar</SPAN
|
|
>
|
|
command will change to the specified directory using the
|
|
<CODE
|
|
CLASS="option"
|
|
>-C</CODE
|
|
>
|
|
option.
|
|
If <CODE
|
|
CLASS="envar"
|
|
>$JARCHDIR</CODE
|
|
> is not set explicitly,
|
|
<SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> will use the top of any subdirectory tree
|
|
in which Java <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
>
|
|
were built by the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> Builder.</P
|
|
><P
|
|
>If the contents any of the source files begin with the string
|
|
<TT
|
|
CLASS="literal"
|
|
>Manifest-Version</TT
|
|
>,
|
|
the file is assumed to be a manifest
|
|
and is passed to the
|
|
<SPAN
|
|
CLASS="application"
|
|
>jar</SPAN
|
|
>
|
|
command with the
|
|
<CODE
|
|
CLASS="option"
|
|
>m</CODE
|
|
>
|
|
option set.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Jar(target = 'foo.jar', source = 'classes')
|
|
|
|
env.Jar(target = 'bar.jar',
|
|
source = ['bar1.java', 'bar2.java'])
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Java"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Java()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Java()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds one or more Java class files.
|
|
The sources may be any combination of explicit
|
|
<TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files,
|
|
or directory trees which will be scanned
|
|
for <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files.</P
|
|
><P
|
|
>SCons will parse each source <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> file
|
|
to find the classes
|
|
(including inner classes)
|
|
defined within that file,
|
|
and from that figure out the
|
|
target <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files that will be created.
|
|
The class files will be placed underneath
|
|
the specified target directory.</P
|
|
><P
|
|
>SCons will also search each Java file
|
|
for the Java package name,
|
|
which it assumes can be found on a line
|
|
beginning with the string
|
|
<TT
|
|
CLASS="literal"
|
|
>package</TT
|
|
>
|
|
in the first column;
|
|
the resulting <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files
|
|
will be placed in a directory reflecting
|
|
the specified package name.
|
|
For example,
|
|
the file
|
|
<TT
|
|
CLASS="filename"
|
|
>Foo.java</TT
|
|
>
|
|
defining a single public
|
|
<CODE
|
|
CLASS="classname"
|
|
>Foo</CODE
|
|
>
|
|
class and
|
|
containing a package name of
|
|
<CODE
|
|
CLASS="classname"
|
|
>sub.dir</CODE
|
|
>
|
|
will generate a corresponding
|
|
<TT
|
|
CLASS="filename"
|
|
>sub/dir/Foo.class</TT
|
|
>
|
|
class file.</P
|
|
><P
|
|
>Examples:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Java(target = 'classes', source = 'src')
|
|
env.Java(target = 'classes', source = ['src1', 'src2'])
|
|
env.Java(target = 'classes', source = ['File1.java', 'File2.java'])
|
|
</PRE
|
|
><P
|
|
> Java source files can use the native encoding for the underlying OS.
|
|
Since SCons compiles in simple ASCII mode by default,
|
|
the compiler will generate warnings about unmappable characters,
|
|
which may lead to errors as the file is processed further.
|
|
In this case, the user must specify the <TT
|
|
CLASS="literal"
|
|
>LANG</TT
|
|
>
|
|
environment variable to tell the compiler what encoding is uesd.
|
|
For portibility, it's best if the encoding is hard-coded
|
|
so that the compile will work if it is done on a system
|
|
with a different encoding.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment()
|
|
env['ENV']['LANG'] = 'en_GB.UTF-8'
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-JavaH"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>JavaH()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.JavaH()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds C header and source files for
|
|
implementing Java native methods.
|
|
The target can be either a directory
|
|
in which the header files will be written,
|
|
or a header file name which
|
|
will contain all of the definitions.
|
|
The source can be the names of <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files,
|
|
the names of <TT
|
|
CLASS="filename"
|
|
>.java</TT
|
|
> files
|
|
to be compiled into <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files
|
|
by calling the <A
|
|
HREF="#b-Java"
|
|
><CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
></A
|
|
> builder method,
|
|
or the objects returned from the
|
|
<CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
>
|
|
builder method.</P
|
|
><P
|
|
>If the construction variable
|
|
<A
|
|
HREF="#cv-JAVACLASSDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSDIR</CODE
|
|
></A
|
|
>
|
|
is set, either in the environment
|
|
or in the call to the
|
|
<CODE
|
|
CLASS="function"
|
|
>JavaH</CODE
|
|
>
|
|
builder method itself,
|
|
then the value of the variable
|
|
will be stripped from the
|
|
beginning of any <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> file names.</P
|
|
><P
|
|
>Examples:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # builds java_native.h
|
|
classes = env.Java(target = 'classdir', source = 'src')
|
|
env.JavaH(target = 'java_native.h', source = classes)
|
|
|
|
# builds include/package_foo.h and include/package_bar.h
|
|
env.JavaH(target = 'include',
|
|
source = ['package/foo.class', 'package/bar.class'])
|
|
|
|
# builds export/foo.h and export/bar.h
|
|
env.JavaH(target = 'export',
|
|
source = ['classes/foo.class', 'classes/bar.class'],
|
|
JAVACLASSDIR = 'classes')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Library"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Library()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Library()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A synonym for the
|
|
<CODE
|
|
CLASS="function"
|
|
>StaticLibrary</CODE
|
|
>
|
|
builder method.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-LoadableModule"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>LoadableModule()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.LoadableModule()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> On most systems,
|
|
this is the same as
|
|
<CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
>.
|
|
On Mac OS X (Darwin) platforms,
|
|
this creates a loadable module bundle.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-M4"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>M4()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.M4()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds an output file from an M4 input file.
|
|
This uses a default <A
|
|
HREF="#cv-M4FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$M4FLAGS</CODE
|
|
></A
|
|
> value of
|
|
<CODE
|
|
CLASS="option"
|
|
>-E</CODE
|
|
>,
|
|
which considers all warnings to be fatal
|
|
and stops on the first warning
|
|
when using the GNU version of m4.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.M4(target = 'foo.c', source = 'foo.c.m4')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Moc"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Moc()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Moc()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds an output file from a moc input file. Moc input files are either
|
|
header files or cxx files. This builder is only available after using the
|
|
tool 'qt'. See the <A
|
|
HREF="#cv-QTDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QTDIR</CODE
|
|
></A
|
|
> variable for more information.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Moc('foo.h') # generates moc_foo.cc
|
|
env.Moc('foo.cpp') # generates foo.moc
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-MSVSProject"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>MSVSProject()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.MSVSProject()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a Microsoft Visual Studio project file,
|
|
and by default builds a solution file as well.</P
|
|
><P
|
|
>This builds a Visual Studio project file, based on the version of
|
|
Visual Studio that is configured (either the latest installed version,
|
|
or the version specified by
|
|
<A
|
|
HREF="#cv-MSVS_VERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVS_VERSION</CODE
|
|
></A
|
|
>
|
|
in the Environment constructor).
|
|
For Visual Studio 6, it will generate a
|
|
<TT
|
|
CLASS="filename"
|
|
>.dsp</TT
|
|
>
|
|
file.
|
|
For Visual Studio 7 (.NET) and later versions, it will generate a
|
|
<TT
|
|
CLASS="filename"
|
|
>.vcproj</TT
|
|
>
|
|
file.</P
|
|
><P
|
|
>By default,
|
|
this also generates a solution file
|
|
for the specified project,
|
|
a
|
|
<TT
|
|
CLASS="filename"
|
|
>.dsw</TT
|
|
>
|
|
file for Visual Studio 6
|
|
or a
|
|
<TT
|
|
CLASS="filename"
|
|
>.sln</TT
|
|
>
|
|
file for Visual Studio 7 (.NET).
|
|
This behavior may be disabled by specifying
|
|
<TT
|
|
CLASS="literal"
|
|
>auto_build_solution=0</TT
|
|
>
|
|
when you call
|
|
<CODE
|
|
CLASS="function"
|
|
>MSVSProject</CODE
|
|
>,
|
|
in which case you presumably want to
|
|
build the solution file(s)
|
|
by calling the
|
|
<CODE
|
|
CLASS="function"
|
|
>MSVSSolution</CODE
|
|
>
|
|
Builder (see below).</P
|
|
><P
|
|
>The <CODE
|
|
CLASS="function"
|
|
>MSVSProject</CODE
|
|
> builder
|
|
takes several lists of filenames
|
|
to be placed into the project file.
|
|
These are currently limited to
|
|
<TT
|
|
CLASS="literal"
|
|
>srcs</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>incs</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>localincs</TT
|
|
>,
|
|
<TT
|
|
CLASS="literal"
|
|
>resources</TT
|
|
>,
|
|
and
|
|
<TT
|
|
CLASS="literal"
|
|
>misc</TT
|
|
>.
|
|
These are pretty self-explanatory, but it should be noted that these
|
|
lists are added to the <A
|
|
HREF="#cv-SOURCES"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SOURCES</CODE
|
|
></A
|
|
> construction variable as strings,
|
|
NOT as SCons File Nodes. This is because they represent file
|
|
names to be added to the project file, not the source files used to
|
|
build the project file.</P
|
|
><P
|
|
>The above filename lists are all optional,
|
|
although at least one must be specified
|
|
for the resulting project file to be non-empty.</P
|
|
><P
|
|
>In addition to the above lists of values,
|
|
the following values may be specified:</P
|
|
><P
|
|
><TT
|
|
CLASS="literal"
|
|
>target</TT
|
|
>:
|
|
The name of the target
|
|
<TT
|
|
CLASS="filename"
|
|
>.dsp</TT
|
|
>
|
|
or
|
|
<TT
|
|
CLASS="filename"
|
|
>.vcproj</TT
|
|
>
|
|
file.
|
|
The correct
|
|
suffix for the version of Visual Studio must be used,
|
|
but the
|
|
<A
|
|
HREF="#cv-MSVSPROJECTSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSPROJECTSUFFIX</CODE
|
|
></A
|
|
>
|
|
construction variable
|
|
will be defined to the correct value (see example below).</P
|
|
><P
|
|
><TT
|
|
CLASS="literal"
|
|
>variant</TT
|
|
>:
|
|
The name of this particular variant.
|
|
For Visual Studio 7 projects,
|
|
this can also be a list of variant names.
|
|
These are typically things like "Debug" or "Release", but really
|
|
can be anything you want.
|
|
For Visual Studio 7 projects,
|
|
they may also specify a target platform
|
|
separated from the variant name by a
|
|
<TT
|
|
CLASS="literal"
|
|
>|</TT
|
|
>
|
|
(vertical pipe)
|
|
character:
|
|
<TT
|
|
CLASS="literal"
|
|
>Debug|Xbox</TT
|
|
>.
|
|
The default target platform is Win32.
|
|
Multiple calls to
|
|
<CODE
|
|
CLASS="function"
|
|
>MSVSProject</CODE
|
|
>
|
|
with different variants are allowed;
|
|
all variants will be added to the project file with their appropriate
|
|
build targets and sources.</P
|
|
><P
|
|
><TT
|
|
CLASS="literal"
|
|
>buildtarget</TT
|
|
>:
|
|
An optional string, node, or list of strings or nodes
|
|
(one per build variant), to tell the Visual Studio debugger
|
|
what output target to use in what build variant.
|
|
The number of
|
|
<TT
|
|
CLASS="literal"
|
|
>buildtarget</TT
|
|
>
|
|
entries must match the number of
|
|
<TT
|
|
CLASS="literal"
|
|
>variant</TT
|
|
>
|
|
entries.</P
|
|
><P
|
|
><TT
|
|
CLASS="literal"
|
|
>runfile</TT
|
|
>:
|
|
The name of the file that Visual Studio 7 and later
|
|
will run and debug.
|
|
This appears as the value of the
|
|
<TT
|
|
CLASS="literal"
|
|
>Output</TT
|
|
>
|
|
field in the resutling Visual Studio project file.
|
|
If this is not specified,
|
|
the default is the same as the specified
|
|
<TT
|
|
CLASS="literal"
|
|
>buildtarget</TT
|
|
>
|
|
value.</P
|
|
><P
|
|
>Note that because <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> always executes its build commands
|
|
from the directory in which the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file is located,
|
|
if you generate a project file in a different directory
|
|
than the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> directory,
|
|
users will not be able to double-click
|
|
on the file name in compilation error messages
|
|
displayed in the Visual Studio console output window.
|
|
This can be remedied by adding the
|
|
Visual C/C++
|
|
.B /FC
|
|
compiler option to the <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
> variable
|
|
so that the compiler will print
|
|
the full path name of any
|
|
files that cause compilation errors.</P
|
|
><P
|
|
>Example usage:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> barsrcs = ['bar.cpp'],
|
|
barincs = ['bar.h'],
|
|
barlocalincs = ['StdAfx.h']
|
|
barresources = ['bar.rc','resource.h']
|
|
barmisc = ['bar_readme.txt']
|
|
|
|
dll = env.SharedLibrary(target = 'bar.dll',
|
|
source = barsrcs)
|
|
|
|
env.MSVSProject(target = 'Bar' + env['MSVSPROJECTSUFFIX'],
|
|
srcs = barsrcs,
|
|
incs = barincs,
|
|
localincs = barlocalincs,
|
|
resources = barresources,
|
|
misc = barmisc,
|
|
buildtarget = dll,
|
|
variant = 'Release')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-MSVSSolution"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>MSVSSolution()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.MSVSSolution()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a Microsoft Visual Studio solution file.</P
|
|
><P
|
|
>This builds a Visual Studio solution file,
|
|
based on the version of Visual Studio that is configured
|
|
(either the latest installed version,
|
|
or the version specified by
|
|
<A
|
|
HREF="#cv-MSVS_VERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVS_VERSION</CODE
|
|
></A
|
|
>
|
|
in the construction environment).
|
|
For Visual Studio 6, it will generate a
|
|
<TT
|
|
CLASS="filename"
|
|
>.dsw</TT
|
|
>
|
|
file.
|
|
For Visual Studio 7 (.NET), it will
|
|
generate a
|
|
<TT
|
|
CLASS="filename"
|
|
>.sln</TT
|
|
>
|
|
file.</P
|
|
><P
|
|
>The following values must be specified:</P
|
|
><P
|
|
><TT
|
|
CLASS="literal"
|
|
>target</TT
|
|
>:
|
|
The name of the target .dsw or .sln file. The correct
|
|
suffix for the version of Visual Studio must be used, but the value
|
|
<A
|
|
HREF="#cv-MSVSSOLUTIONSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSOLUTIONSUFFIX</CODE
|
|
></A
|
|
>
|
|
will be defined to the correct value (see example below).</P
|
|
><P
|
|
><TT
|
|
CLASS="literal"
|
|
>variant</TT
|
|
>:
|
|
The name of this particular variant, or a list of variant
|
|
names (the latter is only supported for MSVS 7 solutions). These are
|
|
typically things like "Debug" or "Release", but really can be anything
|
|
you want. For MSVS 7 they may also specify target platform, like this
|
|
"Debug|Xbox". Default platform is Win32.</P
|
|
><P
|
|
><TT
|
|
CLASS="literal"
|
|
>projects</TT
|
|
>:
|
|
A list of project file names, or Project nodes returned by calls to the
|
|
<CODE
|
|
CLASS="function"
|
|
>MSVSProject</CODE
|
|
>
|
|
Builder,
|
|
to be placed into the solution file.
|
|
It should be noted that these file names are NOT added to the $SOURCES
|
|
environment variable in form of files, but rather as strings. This
|
|
is because they represent file names to be added to the solution file,
|
|
not the source files used to build the solution file.</P
|
|
><P
|
|
>(NOTE: Currently only one project is supported per solution.)</P
|
|
><P
|
|
>Example Usage:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.MSVSSolution(target = 'Bar' + env['MSVSSOLUTIONSUFFIX'],
|
|
projects = ['bar' + env['MSVSPROJECTSUFFIX']],
|
|
variant = 'Release')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Object"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Object()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Object()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A synonym for the
|
|
<CODE
|
|
CLASS="function"
|
|
>StaticObject</CODE
|
|
>
|
|
builder method.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Package"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Package()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Package()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds software distribution packages.
|
|
Packages consist of files to install and packaging information.
|
|
The former may be specified with the <CODE
|
|
CLASS="varname"
|
|
>source</CODE
|
|
> parameter and may be left out,
|
|
in which case the <CODE
|
|
CLASS="function"
|
|
>FindInstalledFiles</CODE
|
|
> function will collect
|
|
all files that have an <CODE
|
|
CLASS="function"
|
|
>Install</CODE
|
|
> or <CODE
|
|
CLASS="function"
|
|
>InstallAs</CODE
|
|
> Builder attached.
|
|
If the <CODE
|
|
CLASS="varname"
|
|
>target</CODE
|
|
> is not specified
|
|
it will be deduced from additional information given to this Builder.</P
|
|
><P
|
|
>The packaging information is specified
|
|
with the help of construction variables documented below.
|
|
This information is called a tag to stress that
|
|
some of them can also be attached to files with the <CODE
|
|
CLASS="function"
|
|
>Tag</CODE
|
|
> function.
|
|
The mandatory ones will complain if they were not specified.
|
|
They vary depending on chosen target packager.</P
|
|
><P
|
|
>The target packager may be selected with the "PACKAGETYPE" command line
|
|
option or with the <CODE
|
|
CLASS="envar"
|
|
>$PACKAGETYPE</CODE
|
|
> construction variable. Currently
|
|
the following packagers available:</P
|
|
><P
|
|
> * msi - Microsoft Installer
|
|
* rpm - Redhat Package Manger
|
|
* ipkg - Itsy Package Management System
|
|
* tarbz2 - compressed tar
|
|
* targz - compressed tar
|
|
* zip - zip file
|
|
* src_tarbz2 - compressed tar source
|
|
* src_targz - compressed tar source
|
|
* src_zip - zip file source</P
|
|
><P
|
|
>An updated list is always available under the "package_type" option when
|
|
running "scons --help" on a project that has packaging activated.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env = Environment(tools=['default', 'packaging'])
|
|
env.Install('/bin/', 'my_program')
|
|
env.Package( NAME = 'foo',
|
|
VERSION = '1.2.3',
|
|
PACKAGEVERSION = 0,
|
|
PACKAGETYPE = 'rpm',
|
|
LICENSE = 'gpl',
|
|
SUMMARY = 'balalalalal',
|
|
DESCRIPTION = 'this should be really really long',
|
|
X_RPM_GROUP = 'Application/fu',
|
|
SOURCE_URL = 'http://foo.org/foo-1.2.3.tar.gz'
|
|
)
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-PCH"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>PCH()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.PCH()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a Microsoft Visual C++ precompiled header.
|
|
Calling this builder method
|
|
returns a list of two targets: the PCH as the first element, and the object
|
|
file as the second element. Normally the object file is ignored.
|
|
This builder method is only
|
|
provided when Microsoft Visual C++ is being used as the compiler.
|
|
The PCH builder method is generally used in
|
|
conjuction with the PCH construction variable to force object files to use
|
|
the precompiled header:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env['PCH'] = env.PCH('StdAfx.cpp')[0]
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-PDF"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>PDF()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.PDF()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a <TT
|
|
CLASS="filename"
|
|
>.pdf</TT
|
|
> file
|
|
from a <TT
|
|
CLASS="filename"
|
|
>.dvi</TT
|
|
> input file
|
|
(or, by extension, a <TT
|
|
CLASS="filename"
|
|
>.tex</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>.ltx</TT
|
|
>,
|
|
or
|
|
<TT
|
|
CLASS="filename"
|
|
>.latex</TT
|
|
> input file).
|
|
The suffix specified by the <A
|
|
HREF="#cv-PDFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFSUFFIX</CODE
|
|
></A
|
|
> construction variable
|
|
(<TT
|
|
CLASS="filename"
|
|
>.pdf</TT
|
|
> by default)
|
|
is added automatically to the target
|
|
if it is not already present. Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # builds from aaa.tex
|
|
env.PDF(target = 'aaa.pdf', source = 'aaa.tex')
|
|
# builds bbb.pdf from bbb.dvi
|
|
env.PDF(target = 'bbb', source = 'bbb.dvi')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-PostScript"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>PostScript()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.PostScript()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a <TT
|
|
CLASS="filename"
|
|
>.ps</TT
|
|
> file
|
|
from a <TT
|
|
CLASS="filename"
|
|
>.dvi</TT
|
|
> input file
|
|
(or, by extension, a <TT
|
|
CLASS="filename"
|
|
>.tex</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>.ltx</TT
|
|
>,
|
|
or
|
|
<TT
|
|
CLASS="filename"
|
|
>.latex</TT
|
|
> input file).
|
|
The suffix specified by the <A
|
|
HREF="#cv-PSSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PSSUFFIX</CODE
|
|
></A
|
|
> construction variable
|
|
(<TT
|
|
CLASS="filename"
|
|
>.ps</TT
|
|
> by default)
|
|
is added automatically to the target
|
|
if it is not already present. Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # builds from aaa.tex
|
|
env.PostScript(target = 'aaa.ps', source = 'aaa.tex')
|
|
# builds bbb.ps from bbb.dvi
|
|
env.PostScript(target = 'bbb', source = 'bbb.dvi')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Program"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Program()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Program()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds an executable given one or more object files
|
|
or C, C++, D, or Fortran source files.
|
|
If any C, C++, D or Fortran source files are specified,
|
|
then they will be automatically
|
|
compiled to object files using the
|
|
<CODE
|
|
CLASS="function"
|
|
>Object</CODE
|
|
>
|
|
builder method;
|
|
see that builder method's description for
|
|
a list of legal source file suffixes
|
|
and how they are interpreted.
|
|
The target executable file prefix
|
|
(specified by the <A
|
|
HREF="#cv-PROGPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PROGPREFIX</CODE
|
|
></A
|
|
> construction variable; nothing by default)
|
|
and suffix
|
|
(specified by the <A
|
|
HREF="#cv-PROGSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PROGSUFFIX</CODE
|
|
></A
|
|
> construction variable;
|
|
by default, <TT
|
|
CLASS="filename"
|
|
>.exe</TT
|
|
> on Windows systems,
|
|
nothing on POSIX systems)
|
|
are automatically added to the target if not already present.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Program(target = 'foo', source = ['foo.o', 'bar.c', 'baz.f'])
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-RES"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>RES()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.RES()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a Microsoft Visual C++ resource file.
|
|
This builder method is only provided
|
|
when Microsoft Visual C++ or MinGW is being used as the compiler. The
|
|
<TT
|
|
CLASS="filename"
|
|
>.res</TT
|
|
>
|
|
(or
|
|
<TT
|
|
CLASS="filename"
|
|
>.o</TT
|
|
>
|
|
for MinGW) suffix is added to the target name if no other suffix is given.
|
|
The source
|
|
file is scanned for implicit dependencies as though it were a C file.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.RES('resource.rc')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-RMIC"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>RMIC()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.RMIC()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds stub and skeleton class files
|
|
for remote objects
|
|
from Java <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files.
|
|
The target is a directory
|
|
relative to which the stub
|
|
and skeleton class files will be written.
|
|
The source can be the names of <TT
|
|
CLASS="filename"
|
|
>.class</TT
|
|
> files,
|
|
or the objects return from the
|
|
<CODE
|
|
CLASS="function"
|
|
>Java</CODE
|
|
>
|
|
builder method.</P
|
|
><P
|
|
>If the construction variable
|
|
<A
|
|
HREF="#cv-JAVACLASSDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSDIR</CODE
|
|
></A
|
|
>
|
|
is set, either in the environment
|
|
or in the call to the
|
|
<CODE
|
|
CLASS="function"
|
|
>RMIC</CODE
|
|
>
|
|
builder method itself,
|
|
then the value of the variable
|
|
will be stripped from the
|
|
beginning of any <TT
|
|
CLASS="filename"
|
|
>.class </TT
|
|
>
|
|
file names.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> classes = env.Java(target = 'classdir', source = 'src')
|
|
env.RMIC(target = 'outdir1', source = classes)
|
|
|
|
env.RMIC(target = 'outdir2',
|
|
source = ['package/foo.class', 'package/bar.class'])
|
|
|
|
env.RMIC(target = 'outdir3',
|
|
source = ['classes/foo.class', 'classes/bar.class'],
|
|
JAVACLASSDIR = 'classes')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-RPCGenClient"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>RPCGenClient()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.RPCGenClient()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Generates an RPC client stub (<TT
|
|
CLASS="filename"
|
|
>_clnt.c</TT
|
|
>) file
|
|
from a specified RPC (<TT
|
|
CLASS="filename"
|
|
>.x</TT
|
|
>) source file.
|
|
Because rpcgen only builds output files
|
|
in the local directory,
|
|
the command will be executed
|
|
in the source file's directory by default.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Builds src/rpcif_clnt.c
|
|
env.RPCGenClient('src/rpcif.x')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-RPCGenHeader"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>RPCGenHeader()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.RPCGenHeader()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Generates an RPC header (<TT
|
|
CLASS="filename"
|
|
>.h</TT
|
|
>) file
|
|
from a specified RPC (<TT
|
|
CLASS="filename"
|
|
>.x</TT
|
|
>) source file.
|
|
Because rpcgen only builds output files
|
|
in the local directory,
|
|
the command will be executed
|
|
in the source file's directory by default.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Builds src/rpcif.h
|
|
env.RPCGenHeader('src/rpcif.x')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-RPCGenService"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>RPCGenService()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.RPCGenService()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Generates an RPC server-skeleton (<TT
|
|
CLASS="filename"
|
|
>_svc.c</TT
|
|
>) file
|
|
from a specified RPC (<TT
|
|
CLASS="filename"
|
|
>.x</TT
|
|
>) source file.
|
|
Because rpcgen only builds output files
|
|
in the local directory,
|
|
the command will be executed
|
|
in the source file's directory by default.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Builds src/rpcif_svc.c
|
|
env.RPCGenClient('src/rpcif.x')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-RPCGenXDR"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>RPCGenXDR()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.RPCGenXDR()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Generates an RPC XDR routine (<TT
|
|
CLASS="filename"
|
|
>_xdr.c</TT
|
|
>) file
|
|
from a specified RPC (<TT
|
|
CLASS="filename"
|
|
>.x</TT
|
|
>) source file.
|
|
Because rpcgen only builds output files
|
|
in the local directory,
|
|
the command will be executed
|
|
in the source file's directory by default.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> # Builds src/rpcif_xdr.c
|
|
env.RPCGenClient('src/rpcif.x')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-SharedLibrary"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>SharedLibrary()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.SharedLibrary()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a shared library
|
|
(<TT
|
|
CLASS="filename"
|
|
>.so</TT
|
|
> on a POSIX system,
|
|
<TT
|
|
CLASS="filename"
|
|
>.dll</TT
|
|
> on Windows)
|
|
given one or more object files
|
|
or C, C++, D or Fortran source files.
|
|
If any source files are given,
|
|
then they will be automatically
|
|
compiled to object files.
|
|
The static library prefix and suffix (if any)
|
|
are automatically added to the target.
|
|
The target library file prefix
|
|
(specified by the <A
|
|
HREF="#cv-SHLIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLIBPREFIX</CODE
|
|
></A
|
|
> construction variable;
|
|
by default, <TT
|
|
CLASS="filename"
|
|
>lib</TT
|
|
> on POSIX systems,
|
|
nothing on Windows systems)
|
|
and suffix
|
|
(specified by the <A
|
|
HREF="#cv-SHLIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLIBSUFFIX</CODE
|
|
></A
|
|
> construction variable;
|
|
by default, <TT
|
|
CLASS="filename"
|
|
>.dll</TT
|
|
> on Windows systems,
|
|
<TT
|
|
CLASS="filename"
|
|
>.so</TT
|
|
> on POSIX systems)
|
|
are automatically added to the target if not already present.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.SharedLibrary(target = 'bar', source = ['bar.c', 'foo.o'])
|
|
</PRE
|
|
><P
|
|
> On Windows systems, the
|
|
<CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
>
|
|
builder method will always build an import
|
|
(<TT
|
|
CLASS="filename"
|
|
>.lib</TT
|
|
>) library
|
|
in addition to the shared (<TT
|
|
CLASS="filename"
|
|
>.dll</TT
|
|
>) library,
|
|
adding a <TT
|
|
CLASS="filename"
|
|
>.lib</TT
|
|
> library with the same basename
|
|
if there is not already a <TT
|
|
CLASS="filename"
|
|
>.lib</TT
|
|
> file explicitly
|
|
listed in the targets.</P
|
|
><P
|
|
>Any object files listed in the
|
|
<TT
|
|
CLASS="literal"
|
|
>source</TT
|
|
>
|
|
must have been built for a shared library
|
|
(that is, using the
|
|
<CODE
|
|
CLASS="function"
|
|
>SharedObject</CODE
|
|
>
|
|
builder method).
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
will raise an error if there is any mismatch.</P
|
|
><P
|
|
>On Windows systems, specifying
|
|
<TT
|
|
CLASS="literal"
|
|
>register=1</TT
|
|
>
|
|
will cause the <TT
|
|
CLASS="filename"
|
|
>.dll</TT
|
|
> to be
|
|
registered after it is built using REGSVR32.
|
|
The command that is run
|
|
("regsvr32" by default) is determined by <A
|
|
HREF="#cv-REGSVR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVR</CODE
|
|
></A
|
|
> construction
|
|
variable, and the flags passed are determined by <A
|
|
HREF="#cv-REGSVRFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVRFLAGS</CODE
|
|
></A
|
|
>. By
|
|
default, <A
|
|
HREF="#cv-REGSVRFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVRFLAGS</CODE
|
|
></A
|
|
> includes the <CODE
|
|
CLASS="option"
|
|
>/s</CODE
|
|
> option,
|
|
to prevent dialogs from popping
|
|
up and requiring user attention when it is run. If you change
|
|
<A
|
|
HREF="#cv-REGSVRFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVRFLAGS</CODE
|
|
></A
|
|
>, be sure to include the <CODE
|
|
CLASS="option"
|
|
>/s</CODE
|
|
> option.
|
|
For example,
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.SharedLibrary(target = 'bar',
|
|
source = ['bar.cxx', 'foo.obj'],
|
|
register=1)
|
|
</PRE
|
|
><P
|
|
> will register <TT
|
|
CLASS="filename"
|
|
>bar.dll</TT
|
|
> as a COM object
|
|
when it is done linking it.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-SharedObject"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>SharedObject()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.SharedObject()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds an object file for
|
|
inclusion in a shared library.
|
|
Source files must have one of the same set of extensions
|
|
specified above for the
|
|
<CODE
|
|
CLASS="function"
|
|
>StaticObject</CODE
|
|
>
|
|
builder method.
|
|
On some platforms building a shared object requires additional
|
|
compiler option
|
|
(e.g. <CODE
|
|
CLASS="option"
|
|
>-fPIC</CODE
|
|
> for gcc)
|
|
in addition to those needed to build a
|
|
normal (static) object, but on some platforms there is no difference between a
|
|
shared object and a normal (static) one. When there is a difference, SCons
|
|
will only allow shared objects to be linked into a shared library, and will
|
|
use a different suffix for shared objects. On platforms where there is no
|
|
difference, SCons will allow both normal (static)
|
|
and shared objects to be linked into a
|
|
shared library, and will use the same suffix for shared and normal
|
|
(static) objects.
|
|
The target object file prefix
|
|
(specified by the <A
|
|
HREF="#cv-SHOBJPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJPREFIX</CODE
|
|
></A
|
|
> construction variable;
|
|
by default, the same as <A
|
|
HREF="#cv-OBJPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJPREFIX</CODE
|
|
></A
|
|
>)
|
|
and suffix
|
|
(specified by the <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
> construction variable)
|
|
are automatically added to the target if not already present.
|
|
Examples:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.SharedObject(target = 'ddd', source = 'ddd.c')
|
|
env.SharedObject(target = 'eee.o', source = 'eee.cpp')
|
|
env.SharedObject(target = 'fff.obj', source = 'fff.for')
|
|
</PRE
|
|
><P
|
|
> Note that the source files will be scanned
|
|
according to the suffix mappings in the
|
|
<TT
|
|
CLASS="literal"
|
|
>SourceFileScanner</TT
|
|
>
|
|
object.
|
|
See the section "Scanner Objects,"
|
|
below, for a more information.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-StaticLibrary"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>StaticLibrary()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.StaticLibrary()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a static library given one or more object files
|
|
or C, C++, D or Fortran source files.
|
|
If any source files are given,
|
|
then they will be automatically
|
|
compiled to object files.
|
|
The static library prefix and suffix (if any)
|
|
are automatically added to the target.
|
|
The target library file prefix
|
|
(specified by the <A
|
|
HREF="#cv-LIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIX</CODE
|
|
></A
|
|
> construction variable;
|
|
by default, <TT
|
|
CLASS="filename"
|
|
>lib</TT
|
|
> on POSIX systems,
|
|
nothing on Windows systems)
|
|
and suffix
|
|
(specified by the <A
|
|
HREF="#cv-LIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIX</CODE
|
|
></A
|
|
> construction variable;
|
|
by default, <TT
|
|
CLASS="filename"
|
|
>.lib</TT
|
|
> on Windows systems,
|
|
<TT
|
|
CLASS="filename"
|
|
>.a</TT
|
|
> on POSIX systems)
|
|
are automatically added to the target if not already present.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.StaticLibrary(target = 'bar', source = ['bar.c', 'foo.o'])
|
|
</PRE
|
|
><P
|
|
> Any object files listed in the
|
|
<TT
|
|
CLASS="literal"
|
|
>source</TT
|
|
>
|
|
must have been built for a static library
|
|
(that is, using the
|
|
<CODE
|
|
CLASS="function"
|
|
>StaticObject</CODE
|
|
>
|
|
builder method).
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
will raise an error if there is any mismatch.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-StaticObject"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>StaticObject()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.StaticObject()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a static object file
|
|
from one or more C, C++, D, or Fortran source files.
|
|
Source files must have one of the following extensions:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> .asm assembly language file
|
|
.ASM assembly language file
|
|
.c C file
|
|
.C Windows: C file
|
|
POSIX: C++ file
|
|
.cc C++ file
|
|
.cpp C++ file
|
|
.cxx C++ file
|
|
.cxx C++ file
|
|
.c++ C++ file
|
|
.C++ C++ file
|
|
.d D file
|
|
.f Fortran file
|
|
.F Windows: Fortran file
|
|
POSIX: Fortran file + C pre-processor
|
|
.for Fortran file
|
|
.FOR Fortran file
|
|
.fpp Fortran file + C pre-processor
|
|
.FPP Fortran file + C pre-processor
|
|
.m Object C file
|
|
.mm Object C++ file
|
|
.s assembly language file
|
|
.S Windows: assembly language file
|
|
POSIX: assembly language file + C pre-processor
|
|
.spp assembly language file + C pre-processor
|
|
.SPP assembly language file + C pre-processor
|
|
</PRE
|
|
><P
|
|
> The target object file prefix
|
|
(specified by the <A
|
|
HREF="#cv-OBJPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJPREFIX</CODE
|
|
></A
|
|
> construction variable; nothing by default)
|
|
and suffix
|
|
(specified by the <A
|
|
HREF="#cv-OBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJSUFFIX</CODE
|
|
></A
|
|
> construction variable;
|
|
<TT
|
|
CLASS="filename"
|
|
>.obj</TT
|
|
> on Windows systems,
|
|
<TT
|
|
CLASS="filename"
|
|
>.o</TT
|
|
> on POSIX systems)
|
|
are automatically added to the target if not already present.
|
|
Examples:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.StaticObject(target = 'aaa', source = 'aaa.c')
|
|
env.StaticObject(target = 'bbb.o', source = 'bbb.c++')
|
|
env.StaticObject(target = 'ccc.obj', source = 'ccc.f')
|
|
</PRE
|
|
><P
|
|
> Note that the source files will be scanned
|
|
according to the suffix mappings in
|
|
<TT
|
|
CLASS="literal"
|
|
>SourceFileScanner</TT
|
|
>
|
|
object.
|
|
See the section "Scanner Objects,"
|
|
below, for a more information.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Tar"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Tar()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Tar()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a tar archive of the specified files
|
|
and/or directories.
|
|
Unlike most builder methods,
|
|
the
|
|
<CODE
|
|
CLASS="function"
|
|
>Tar</CODE
|
|
>
|
|
builder method may be called multiple times
|
|
for a given target;
|
|
each additional call
|
|
adds to the list of entries
|
|
that will be built into the archive.
|
|
Any source directories will
|
|
be scanned for changes to
|
|
any on-disk files,
|
|
regardless of whether or not
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
knows about them from other Builder or function calls.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Tar('src.tar', 'src')
|
|
|
|
# Create the stuff.tar file.
|
|
env.Tar('stuff', ['subdir1', 'subdir2'])
|
|
# Also add "another" to the stuff.tar file.
|
|
env.Tar('stuff', 'another')
|
|
|
|
# Set TARFLAGS to create a gzip-filtered archive.
|
|
env = Environment(TARFLAGS = '-c -z')
|
|
env.Tar('foo.tar.gz', 'foo')
|
|
|
|
# Also set the suffix to .tgz.
|
|
env = Environment(TARFLAGS = '-c -z',
|
|
TARSUFFIX = '.tgz')
|
|
env.Tar('foo')
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-TypeLibrary"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>TypeLibrary()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.TypeLibrary()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a Windows type library (<TT
|
|
CLASS="filename"
|
|
>.tlb</TT
|
|
>)
|
|
file from an input IDL file (<TT
|
|
CLASS="filename"
|
|
>.idl</TT
|
|
>).
|
|
In addition, it will build the associated inteface stub and
|
|
proxy source files,
|
|
naming them according to the base name of the <TT
|
|
CLASS="filename"
|
|
>.idl</TT
|
|
> file.
|
|
For example,
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.TypeLibrary(source="foo.idl")
|
|
</PRE
|
|
><P
|
|
> Will create <TT
|
|
CLASS="filename"
|
|
>foo.tlb</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>foo.h</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>foo_i.c</TT
|
|
>,
|
|
<TT
|
|
CLASS="filename"
|
|
>foo_p.c</TT
|
|
>
|
|
and
|
|
<TT
|
|
CLASS="filename"
|
|
>foo_data.c</TT
|
|
>
|
|
files.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Uic"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Uic()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Uic()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a header file, an implementation file and a moc file from an ui file.
|
|
and returns the corresponding nodes in the above order.
|
|
This builder is only available after using the tool 'qt'. Note: you can
|
|
specify <TT
|
|
CLASS="filename"
|
|
>.ui</TT
|
|
> files directly as source
|
|
files to the <CODE
|
|
CLASS="function"
|
|
>Program</CODE
|
|
>,
|
|
<CODE
|
|
CLASS="function"
|
|
>Library</CODE
|
|
> and <CODE
|
|
CLASS="function"
|
|
>SharedLibrary</CODE
|
|
> builders
|
|
without using this builder. Using this builder lets you override the standard
|
|
naming conventions (be careful: prefixes are always prepended to names of
|
|
built files; if you don't want prefixes, you may set them to ``).
|
|
See the <A
|
|
HREF="#cv-QTDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QTDIR</CODE
|
|
></A
|
|
> variable for more information.
|
|
Example:
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Uic('foo.ui') # -> ['foo.h', 'uic_foo.cc', 'moc_foo.cc']
|
|
env.Uic(target = Split('include/foo.h gen/uicfoo.cc gen/mocfoo.cc'),
|
|
source = 'foo.ui') # -> ['include/foo.h', 'gen/uicfoo.cc', 'gen/mocfoo.cc']
|
|
</PRE
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="b-Zip"
|
|
></A
|
|
><CODE
|
|
CLASS="function"
|
|
>Zip()</CODE
|
|
>, <CODE
|
|
CLASS="function"
|
|
>env.Zip()</CODE
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Builds a zip archive of the specified files
|
|
and/or directories.
|
|
Unlike most builder methods,
|
|
the
|
|
<CODE
|
|
CLASS="function"
|
|
>Zip</CODE
|
|
>
|
|
builder method may be called multiple times
|
|
for a given target;
|
|
each additional call
|
|
adds to the list of entries
|
|
that will be built into the archive.
|
|
Any source directories will
|
|
be scanned for changes to
|
|
any on-disk files,
|
|
regardless of whether or not
|
|
<SPAN
|
|
CLASS="application"
|
|
>scons</SPAN
|
|
>
|
|
knows about them from other Builder or function calls.
|
|
</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> env.Zip('src.zip', 'src')
|
|
|
|
# Create the stuff.zip file.
|
|
env.Zip('stuff', ['subdir1', 'subdir2'])
|
|
# Also add "another" to the stuff.tar file.
|
|
env.Zip('stuff', 'another')
|
|
</PRE
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="appendix"
|
|
><HR><H1
|
|
><A
|
|
NAME="app-tools"
|
|
></A
|
|
>Appendix C. Tools</H1
|
|
><P
|
|
>
|
|
This appendix contains descriptions of all of the
|
|
Tools modules that are
|
|
available "out of the box" in this version of SCons.
|
|
|
|
</P
|
|
><P
|
|
></P
|
|
><DIV
|
|
CLASS="variablelist"
|
|
><DL
|
|
><DT
|
|
><A
|
|
NAME="t-386asm"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>386asm</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the 386ASM assembler
|
|
for the Phar Lap ETS embedded operating system.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-aixcXX"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>aixc++</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the IMB xlc / Visual Age C++ compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXVERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXVERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-aixcc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>aixcc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the IBM xlc / Visual Age C compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCVERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCVERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCC</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-aixf77"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>aixf77</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the IBM Visual Age f77 Fortran compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-F77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-aixlink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>aixlink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the IBM Visual Age linker.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLIBSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-applelink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>applelink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Apple linker
|
|
(similar to the GNU linker).
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-FRAMEWORKPATHPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKPATHPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULECOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULECOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULEFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULEFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULEPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULEPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_FRAMEWORKPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FRAMEWORKPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_FRAMEWORKS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FRAMEWORKS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-FRAMEWORKSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKSFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-ar"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>ar</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>ar</SPAN
|
|
> library archiver.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RANLIB"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RANLIB</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RANLIBCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RANLIBCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RANLIBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RANLIBFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-as"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>as</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>as</SPAN
|
|
> assembler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-bcc32"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>bcc32</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the bcc32 compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-BitKeeper"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>BitKeeper</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the BitKeeper
|
|
source code control system.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-BITKEEPER"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BITKEEPER</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-BITKEEPERCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BITKEEPERCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-BITKEEPERGET"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BITKEEPERGET</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-BITKEEPERGETFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BITKEEPERGETFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-BITKEEPERCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BITKEEPERCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-cc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>cc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for generic POSIX C copmilers.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FRAMEWORKPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FRAMEWORKS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FRAMEWORKS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-PLATFORM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PLATFORM</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-cvf"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>cvf</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Compaq Visual Fortran compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANMODDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANMODDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIRPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANMODDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANMODDIRSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-OBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_FORTRANMODFLAG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANMODFLAG</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-CVS"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>CVS</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the CVS source code
|
|
management system.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CVS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CVS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CVSCOFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CVSCOFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CVSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CVSCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CVSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CVSFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CVSCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CVSCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-cXX"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>cXX</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for generic POSIX C++ compilers.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CPPDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-OBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CXXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-default"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>default</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets variables by calling a default list of Tool modules
|
|
for the platform on which SCons is running.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-dmd"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>dmd</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for D language compilers
|
|
(the Digital Mars D compiler, or GDC).
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-dvi"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>dvi</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Attaches the <CODE
|
|
CLASS="function"
|
|
>DVI</CODE
|
|
> builder to the
|
|
construction environment.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-dvipdf"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>dvipdf</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the dvipdf utility.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-DVIPDF"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPDF</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-DVIPDFCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPDFCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-DVIPDFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPDFFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-DVIPDFCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPDFCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-dvips"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>dvips</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the dvips utility.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-DVIPS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-DVIPSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$DVIPSFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PSCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PSPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PSPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PSSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PSSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-PSCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PSCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-f77"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>f77</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for generic POSIX Fortran 77 compilers.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-F77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F77COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F77FILESUFFIXES"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77FILESUFFIXES</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F77PPFILESUFFIXES"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PPFILESUFFIXES</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77PPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_F77INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F77INCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-F77COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77COMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F77PPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77PPCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANPPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77COMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77PPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77PPCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANPPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-f90"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>f90</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for generic POSIX Fortran 90 compilers.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-F90"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F90COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F90PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90PPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_F90INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F90INCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-F90COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90COMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F90PPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90PPCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90COMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90PPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90PPCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-f95"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>f95</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for generic POSIX Fortran 95 compilers.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-F95"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F95COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F95PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95PPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95PPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_F95INCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_F95INCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-F95COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95COMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F95PPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95PPCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95COMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95PPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95PPCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-fortran"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>fortran</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for generic POSIX Fortran compilers.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-FORTRANCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANPPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANPPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-gXX"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>g++</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for the <SPAN
|
|
CLASS="application"
|
|
>gXX</SPAN
|
|
> C++ compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXVERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXVERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-g77"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>g77</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for the <SPAN
|
|
CLASS="application"
|
|
>g77</SPAN
|
|
> Fortran compiler.
|
|
Calls the <TT
|
|
CLASS="literal"
|
|
>f77</TT
|
|
> Tool module
|
|
to set variables.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-gas"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>gas</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>gas</SPAN
|
|
> assembler.
|
|
Calls the <TT
|
|
CLASS="literal"
|
|
>as</TT
|
|
> module.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-gcc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>gcc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for the <SPAN
|
|
CLASS="application"
|
|
>gcc</SPAN
|
|
> C compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCVERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCVERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-gnulink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>gnulink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for GNU linker/loader.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-RPATHPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPATHPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPATHSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPATHSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-gs"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>gs</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for Ghostscript.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-GS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$GS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-GSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$GSCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-GSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$GSFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-GSCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$GSCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-hpcXX"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>hpc++</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for the compilers aCC on HP/UX systems.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-hpcc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>hpcc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Set construction variables for the
|
|
<SPAN
|
|
CLASS="application"
|
|
>aCC</SPAN
|
|
> on HP/UX systems.
|
|
Calls the <TT
|
|
CLASS="literal"
|
|
>cXX</TT
|
|
> tool for additional variables.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXVERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXVERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-hplink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>hplink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the linker on HP/UX systems.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLIBSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-icc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>icc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the
|
|
<SPAN
|
|
CLASS="application"
|
|
>icc</SPAN
|
|
> compiler on OS/2 systems.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-icl"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>icl</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Intel C/C++ compiler.
|
|
Calls the <TT
|
|
CLASS="literal"
|
|
>intelc</TT
|
|
> Tool module to set its variables.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-ifl"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>ifl</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Intel Fortran compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANPPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANPPCOM</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRANFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_FORTRANINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_FORTRANINCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-ifort"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>ifort</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for newer versions
|
|
of the Intel Fortran compiler for Linux.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-F77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F77</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F90"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F90</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-F95"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$F95</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-FORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$FORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF77FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF77FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF90FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF90FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHF95FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHF95FLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHFORTRANFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHFORTRANFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-ilink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>ilink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the
|
|
<SPAN
|
|
CLASS="application"
|
|
>ilink</SPAN
|
|
> linker on OS/2 systems.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LIBDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-ilink32"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>ilink32</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Borland
|
|
<SPAN
|
|
CLASS="application"
|
|
>ilink32</SPAN
|
|
> linker.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LIBDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-install"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>install</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for file
|
|
and directory installation.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-INSTALL"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INSTALL</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INSTALLSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INSTALLSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-intelc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>intelc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Intel C/C++ compiler
|
|
(Linux and Windows, version 7 and later).
|
|
Calls the <TT
|
|
CLASS="literal"
|
|
>gcc</TT
|
|
> or <TT
|
|
CLASS="literal"
|
|
>msvc</TT
|
|
>
|
|
(on Linux and Windows, respectively)
|
|
to set underlying variables.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INTEL_C_COMPILER_VERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INTEL_C_COMPILER_VERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-jar"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>jar</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>jar</SPAN
|
|
> utility.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-JAR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JARCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JARFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JARFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JARSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JARSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-JARCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JARCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-javac"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>javac</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>javac</SPAN
|
|
> compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-JAVABOOTCLASSPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVABOOTCLASSPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVAC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVAC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVACCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVACFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVACLASSPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVACLASSSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVASOURCEPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVASOURCEPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVASUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVASUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-JAVACCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-javah"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>javah</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>javah</SPAN
|
|
> tool.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-JAVACLASSSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVAH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVAH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVAHCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVAHCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVAHFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVAHFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-JAVACLASSPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-JAVAHCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVAHCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-latex"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>latex</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>latex</SPAN
|
|
> utility.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LATEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LATEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-LATEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-lex"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>lex</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>lex</SPAN
|
|
> lexical analyser.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LEXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-LEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LEXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-link"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>link</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for generic POSIX linkers.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LDMODULE"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULE</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULECOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULECOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULEFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULEFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULEPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULEPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLIBSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-LDMODULECOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULECOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-linkloc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>linkloc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the
|
|
<SPAN
|
|
CLASS="application"
|
|
>LinkLoc</SPAN
|
|
>
|
|
linker for the Phar Lap ETS embedded operating system.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LIBDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-LINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-m4"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>m4</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>m4</SPAN
|
|
> macro processor.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-M4"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$M4</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-M4COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$M4COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-M4FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$M4FLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-M4COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$M4COMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-masm"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>masm</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Microsoft assembler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-ASCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPDEFFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPDEFFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_CPPINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_CPPINCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-midl"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>midl</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Microsoft IDL compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-MIDL"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MIDL</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MIDLCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MIDLCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MIDLFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MIDLFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-MIDLCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MIDLCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-mingw"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>mingw</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for MinGW (Minimal Gnu on Windows).
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULECOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULECOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-OBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCINCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCINCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCINCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCINCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCINCSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSDEFSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-RCCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-mslib"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>mslib</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Microsoft
|
|
<SPAN
|
|
CLASS="application"
|
|
>mslib</SPAN
|
|
>
|
|
library archiver.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-ARCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-mslink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>mslink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Microsoft linker.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LDMODULE"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULE</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULECOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULECOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULEFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULEFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULEPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULEPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LDMODULESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-REGSVR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-REGSVRCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVRCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-REGSVRFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVRFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WIN32DEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WIN32DEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WIN32DEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WIN32DEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WIN32EXPPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WIN32EXPPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WIN32EXPSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WIN32EXPSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSDEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSEXPPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSEXPPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSEXPSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSEXPSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSPROGMANIFESTPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSPROGMANIFESTPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSPROGMANIFESTSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSPROGMANIFESTSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSSHLIBMANIFESTPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSSHLIBMANIFESTPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWSSHLIBMANIFESTSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWSSHLIBMANIFESTSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-WINDOWS_INSERT_DEF"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$WINDOWS_INSERT_DEF</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-LDMODULECOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LDMODULECOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVS_IGNORE_IDE_PATHS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVS_IGNORE_IDE_PATHS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-REGSVRCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$REGSVRCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-msvc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>msvc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Microsoft Visual C/C++ compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-BUILDERS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BUILDERS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCPCHFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCPCHFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCPDBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCPDBFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-OBJPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-OBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$OBJSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PCHCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PCHCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PCHPDBFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PCHPDBFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CCCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-msvs"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>msvs</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for Microsoft Visual Studio.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-MSVSBUILDCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSBUILDCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSCLEANCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSCLEANCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSENCODING"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSENCODING</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSPROJECTCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSPROJECTCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSREBUILDCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSREBUILDCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSSCONS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSCONS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSSCONSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSCONSCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSSCONSCRIPT"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSCONSCRIPT</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSSCONSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSCONSFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MSVSSOLUTIONCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MSVSSOLUTIONCOM</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-mwcc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>mwcc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Metrowerks CodeWarrior compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CPPDEFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CPPDEFSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-INCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$INCSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MWCW_VERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MWCW_VERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MWCW_VERSIONS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MWCW_VERSIONS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-CCCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CCCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-mwld"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>mwld</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Metrowerks CodeWarrior linker.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBDIRSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBDIRSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBLINKSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBLINKSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-nasm"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>nasm</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the
|
|
<SPAN
|
|
CLASS="application"
|
|
>nasm</SPAN
|
|
> Netwide Assembler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-ASCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ASPPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ASPPCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-packaging"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>packaging</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> A framework for building binary and source packages.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-Packaging"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>Packaging</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <CODE
|
|
CLASS="function"
|
|
>Package</CODE
|
|
> Builder.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-pdf"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>pdf</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Portable Document Format builder.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-PDFPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-pdflatex"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>pdflatex</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>pdflatex</SPAN
|
|
> utility.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LATEXRETRIES"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXRETRIES</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFLATEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFLATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFLATEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-PDFLATEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-pdftex"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>pdftex</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>pdftex</SPAN
|
|
> utility.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LATEXRETRIES"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXRETRIES</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFLATEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFLATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFLATEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFTEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFTEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFTEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFTEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFTEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFTEXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-PDFLATEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFLATEXCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-PDFTEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$PDFTEXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-Perforce"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>Perforce</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for interacting with the
|
|
Perforce source code management system.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-P4"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$P4</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-P4COM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$P4COM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-P4FLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$P4FLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-P4COMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$P4COMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-qt"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>qt</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for building Qt applications.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-QTDIR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QTDIR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_AUTOSCAN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_AUTOSCAN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_BINPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_BINPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_CPPPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_CPPPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_LIB"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_LIB</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_LIBPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_LIBPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCCXXPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCCXXPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCCXXSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCCXXSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCFROMCXXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCFROMCXXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCFROMCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCFROMCXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCFROMHCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCFROMHCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCFROMHFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCFROMHFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCHPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCHPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_MOCHSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_MOCHSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UIC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UIC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UICCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UICDECLFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICDECLFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UICDECLPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICDECLPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UICDECLSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICDECLSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UICIMPLFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICIMPLFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UICIMPLPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICIMPLPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UICIMPLSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UICIMPLSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-QT_UISUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$QT_UISUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-RCS"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>RCS</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the interaction
|
|
with the Revision Control System.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-RCS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCS_CO"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS_CO</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCS_COCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS_COCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RCS_COFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS_COFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-RCS_COCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RCS_COCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-rmic"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>rmic</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>rmic</SPAN
|
|
> utility.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-JAVACLASSSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$JAVACLASSSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RMIC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RMIC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RMICCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RMICCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RMICFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RMICFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-RMICCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RMICCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-rpcgen"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>rpcgen</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for building with RPCGEN.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-RPCGEN"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGEN</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPCGENCLIENTFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENCLIENTFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPCGENFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPCGENHEADERFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENHEADERFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPCGENSERVICEFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENSERVICEFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPCGENXDRFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPCGENXDRFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-SCCS"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>SCCS</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for interacting with the
|
|
Source Code Control System.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-SCCS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SCCS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SCCSCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SCCSCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SCCSFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SCCSFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SCCSGETFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SCCSGETFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-SCCSCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SCCSCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-sgiar"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>sgiar</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the SGI library archiver.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-ARCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-sgicXX"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>sgic++</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the SGI C++ compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-sgicc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>sgicc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the SGI C compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-sgilink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>sgilink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the SGI linker.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-LINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPATHPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPATHPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPATHSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPATHSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-sunar"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>sunar</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Sun library archiver.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINK"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINK</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-ARCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-suncXX"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>sunc++</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Sun C++ compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-CXXVERSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXXVERSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCXXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCXXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-suncc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>suncc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Sun C compiler.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-CXX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$CXX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHCCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHCCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHOBJSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHOBJSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-sunlink"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>sunlink</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Sun linker.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-RPATHPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPATHPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-RPATHSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$RPATHSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SHLINKFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SHLINKFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-swig"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>swig</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the SWIG interface generator.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-SWIG"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIG</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SWIGCFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGCFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SWIGCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SWIGCXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGCXXFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SWIGFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SWIGINCPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGINCPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SWIGINCSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGINCSUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-SWIGPATH"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGPATH</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-_SWIGINCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$_SWIGINCFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-SWIGCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$SWIGCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-tar"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>tar</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>tar</SPAN
|
|
> archiver.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-TAR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TAR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-TARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-TARFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-TARSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-TARCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TARCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-tex"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>tex</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the TeX formatter and typesetter.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-BIBTEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BIBTEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-BIBTEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BIBTEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-BIBTEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BIBTEXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LATEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LATEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LATEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MAKEINDEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MAKEINDEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MAKEINDEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MAKEINDEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MAKEINDEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MAKEINDEXFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-TEX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TEX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-TEXCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TEXCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-TEXFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TEXFLAGS</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-BIBTEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$BIBTEXCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LATEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LATEXCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-MAKEINDEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$MAKEINDEXCOMSTR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-TEXCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$TEXCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-tlib"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>tlib</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the Borlan
|
|
<SPAN
|
|
CLASS="application"
|
|
>tib</SPAN
|
|
> library archiver.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-AR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$AR</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ARFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBPREFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBPREFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-LIBSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$LIBSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-ARCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ARCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-yacc"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>yacc</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>yacc</SPAN
|
|
> parse generator.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-YACC"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACC</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-YACCCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-YACCFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-YACCHFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCHFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-YACCHXXFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCHXXFILESUFFIX</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-YACCVCGFILESUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCVCGFILESUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-YACCCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$YACCCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
><DT
|
|
><A
|
|
NAME="t-zip"
|
|
></A
|
|
><TT
|
|
CLASS="literal"
|
|
>zip</TT
|
|
></DT
|
|
><DD
|
|
><P
|
|
> Sets construction variables for the <SPAN
|
|
CLASS="application"
|
|
>zip</SPAN
|
|
> archiver.
|
|
</P
|
|
><P
|
|
> Sets: <A
|
|
HREF="#cv-ZIP"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ZIP</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ZIPCOM"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ZIPCOM</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ZIPCOMPRESSION"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ZIPCOMPRESSION</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ZIPFLAGS"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ZIPFLAGS</CODE
|
|
></A
|
|
>, <A
|
|
HREF="#cv-ZIPSUFFIX"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ZIPSUFFIX</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
><P
|
|
> Uses: <A
|
|
HREF="#cv-ZIPCOMSTR"
|
|
><CODE
|
|
CLASS="envar"
|
|
>$ZIPCOMSTR</CODE
|
|
></A
|
|
>.
|
|
</P
|
|
></DD
|
|
></DL
|
|
></DIV
|
|
></DIV
|
|
><DIV
|
|
CLASS="appendix"
|
|
><HR><H1
|
|
><A
|
|
NAME="app-tasks"
|
|
></A
|
|
>Appendix D. Handling Common Tasks</H1
|
|
><P
|
|
> There is a common set of simple tasks that many build configurations rely
|
|
on as they become more complex. Most build tools have special
|
|
purpose constructs for performing these tasks, but since <TT
|
|
CLASS="filename"
|
|
>SConscript</TT
|
|
>
|
|
files are <SPAN
|
|
CLASS="application"
|
|
>Python</SPAN
|
|
> scripts, you can use more flexible built-in <SPAN
|
|
CLASS="application"
|
|
>Python</SPAN
|
|
>
|
|
services to perform these tasks. This appendix lists a number of these
|
|
tasks and how to implement them in <SPAN
|
|
CLASS="application"
|
|
>Python</SPAN
|
|
>.
|
|
</P
|
|
><DIV
|
|
CLASS="example"
|
|
><A
|
|
NAME="AEN10745"
|
|
></A
|
|
><P
|
|
><B
|
|
>Example D-1. Wildcard globbing to create a list of filenames</B
|
|
></P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import glob
|
|
files = glob.glob(wildcard)
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="example"
|
|
><A
|
|
NAME="AEN10748"
|
|
></A
|
|
><P
|
|
><B
|
|
>Example D-2. Filename extension substitution</B
|
|
></P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os.path
|
|
filename = os.path.splitext(filename)[0]+extension
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="example"
|
|
><A
|
|
NAME="AEN10751"
|
|
></A
|
|
><P
|
|
><B
|
|
>Example D-3. Appending a path prefix to a list of filenames</B
|
|
></P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os.path
|
|
filenames = [os.path.join(prefix, x) for x in filenames]
|
|
</PRE
|
|
><P
|
|
>or in Python 1.5.2:</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os.path
|
|
new_filenames = []
|
|
for x in filenames:
|
|
new_filenames.append(os.path.join(prefix, x))
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="example"
|
|
><A
|
|
NAME="AEN10756"
|
|
></A
|
|
><P
|
|
><B
|
|
>Example D-4. Substituting a path prefix with another one</B
|
|
></P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> if filename.find(old_prefix) == 0:
|
|
filename = filename.replace(old_prefix, new_prefix)
|
|
</PRE
|
|
><P
|
|
>or in Python 1.5.2:</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import string
|
|
if string.find(filename, old_prefix) == 0:
|
|
filename = string.replace(filename, old_prefix, new_prefix)
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="example"
|
|
><A
|
|
NAME="AEN10761"
|
|
></A
|
|
><P
|
|
><B
|
|
>Example D-5. Filtering a filename list to exclude/retain only a specific set
|
|
of extensions</B
|
|
></P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os.path
|
|
filenames = [x for x in filenames if os.path.splitext(x)[1] in extensions]
|
|
</PRE
|
|
><P
|
|
>or in Python 1.5.2:</P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
> import os.path
|
|
new_filenames = []
|
|
for x in filenames:
|
|
if os.path.splitext(x)[1] in extensions:
|
|
new_filenames.append(x)
|
|
</PRE
|
|
></DIV
|
|
><DIV
|
|
CLASS="example"
|
|
><A
|
|
NAME="AEN10766"
|
|
></A
|
|
><P
|
|
><B
|
|
>Example D-6. The "backtick function": run a shell command and capture the
|
|
output</B
|
|
></P
|
|
><PRE
|
|
CLASS="programlisting"
|
|
>import os
|
|
output = os.popen(command).read()
|
|
</PRE
|
|
></DIV
|
|
></DIV
|
|
></DIV
|
|
><H3
|
|
CLASS="FOOTNOTES"
|
|
>Notes</H3
|
|
><TABLE
|
|
BORDER="0"
|
|
CLASS="FOOTNOTES"
|
|
WIDTH="100%"
|
|
><TR
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="5%"
|
|
><A
|
|
NAME="FTN.AEN380"
|
|
HREF="#AEN380"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[1]</SPAN
|
|
></A
|
|
></TD
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="95%"
|
|
><P
|
|
>In programming parlance,
|
|
the <TT
|
|
CLASS="filename"
|
|
>SConstruct</TT
|
|
> file is
|
|
<SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>declarative</I
|
|
></SPAN
|
|
>,
|
|
meaning you tell <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> what you want done
|
|
and let it figure out the order in which to do it,
|
|
rather than strictly <SPAN
|
|
CLASS="emphasis"
|
|
><I
|
|
CLASS="emphasis"
|
|
>imperative</I
|
|
></SPAN
|
|
>,
|
|
where you specify explicitly the order in
|
|
which to do things.
|
|
</P
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="5%"
|
|
><A
|
|
NAME="FTN.AEN1019"
|
|
HREF="#AEN1019"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[2]</SPAN
|
|
></A
|
|
></TD
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="95%"
|
|
><P
|
|
> This easily-overlooked distinction between
|
|
how <SPAN
|
|
CLASS="application"
|
|
>SCons</SPAN
|
|
> decides if the target itself must be rebuilt
|
|
and how the target is then used to decide if a different
|
|
target must be rebuilt is one of the confusing
|
|
things that has led to the <CODE
|
|
CLASS="function"
|
|
>TargetSignatures</CODE
|
|
>
|
|
and <CODE
|
|
CLASS="function"
|
|
>SourceSignatures</CODE
|
|
> functions being
|
|
replaced by the simpler <CODE
|
|
CLASS="function"
|
|
>Decider</CODE
|
|
> function.
|
|
</P
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="5%"
|
|
><A
|
|
NAME="FTN.AEN2335"
|
|
HREF="#AEN2335"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[3]</SPAN
|
|
></A
|
|
></TD
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="95%"
|
|
><P
|
|
> The <CODE
|
|
CLASS="function"
|
|
>AddOption</CODE
|
|
> function is,
|
|
in fact, implemented using a subclass
|
|
of the <CODE
|
|
CLASS="classname"
|
|
>optparse.OptionParser</CODE
|
|
>.
|
|
</P
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="5%"
|
|
><A
|
|
NAME="FTN.AEN2910"
|
|
HREF="#AEN2910"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[4]</SPAN
|
|
></A
|
|
></TD
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="95%"
|
|
><P
|
|
> Unfortunately, in the early days of SCons design,
|
|
we used the name <CODE
|
|
CLASS="function"
|
|
>Copy</CODE
|
|
> for the function that
|
|
returns a copy of the environment,
|
|
otherwise that would be the logical choice for
|
|
a Builder that copies a file or directory tree
|
|
to a target location.
|
|
</P
|
|
></TD
|
|
></TR
|
|
><TR
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="5%"
|
|
><A
|
|
NAME="FTN.AEN4110"
|
|
HREF="#AEN4110"
|
|
><SPAN
|
|
CLASS="footnote"
|
|
>[5]</SPAN
|
|
></A
|
|
></TD
|
|
><TD
|
|
ALIGN="LEFT"
|
|
VALIGN="TOP"
|
|
WIDTH="95%"
|
|
><P
|
|
> Actually, the MD5 signature is used as the name of the file
|
|
in the shared cache directory in which the contents are stored.
|
|
</P
|
|
></TD
|
|
></TR
|
|
></TABLE
|
|
></BODY
|
|
></HTML
|
|
> |