In the previous example,
each of the subsidiary SConscript
files
created its own construction environment
by calling Environment
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
SConscript
file.
SCons supports the ability to export variables
from a parent SConscript
file
to its subsidiary SConscript
files,
which allows you to share common initialized
values throughout your build hierarchy.
There are two ways to export a variable,
such as a construction environment,
from an SConscript
file,
so that it may be used by other SConscript
files.
First, you can call the Export
function with a list of variables,
or a string of white-space separated variable names.
Each call to Export
adds one
or more variables to a global list
of variables that are available for import
by other SConscript
files.
env = Environment() Export('env')
You may export more than one variable name at a time:
env = Environment() debug = ARGUMENTS['debug'] Export('env', 'debug')
Because white space is not legal in Python variable names,
the Export
function will even automatically split
a string into separate names for you:
Export('env debug')
Second, you can specify a list of
variables to export as a second argument
to the SConscript
function call:
SConscript('src/SConscript', 'env')
Or as the exports
keyword argument:
SConscript('src/SConscript', exports='env')
These calls export the specified variables
to only the listed SConscript
files.
You may, however, specify more than one
SConscript
file in a list:
SConscript(['src1/SConscript', 'src2/SConscript'], exports='env')
This is functionally equivalent to
calling the SConscript
function
multiple times with the same exports
argument,
one per SConscript
file.
Once a variable has been exported from a calling
SConscript
file,
it may be used in other SConscript
files
by calling the Import
function:
Import('env') env.Program('prog', ['prog.c'])
The Import
call makes the env
construction
environment available to the SConscript
file,
after which the variable can be used to build
programs, libraries, etc.
Like the Export
function,
the Import
function can be used
with multiple variable names:
Import('env', 'debug') env = env.Clone(DEBUG = debug) env.Program('prog', ['prog.c'])
And the Import
function will similarly
split a string along white-space
into separate variable names:
Import('env debug') env = env.Clone(DEBUG = debug) env.Program('prog', ['prog.c'])
Lastly, as a special case,
you may import all of the variables that
have been exported by supplying an asterisk
to the Import
function:
Import('*') env = env.Clone(DEBUG = debug) env.Program('prog', ['prog.c'])
If you're dealing with a lot of SConscript
files,
this can be a lot simpler than keeping
arbitrary lists of imported variables in each file.
Sometimes, you would like to be able to
use information from a subsidiary
SConscript
file in some way.
For example,
suppose that you want to create one
library from source files
scattered throughout a number
of subsidiary SConscript
files.
You can do this by using the Return
function to return values
from the subsidiary SConscript
files
to the calling file.
If, for example, we have two subdirectories
foo
and bar
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 SConscript
calls
like this:
env = Environment() Export('env') objs = [] for subdir in ['foo', 'bar']: o = SConscript('%s/SConscript' % subdir) objs.append(o) env.Library('prog', objs)
We can do this by using the Return
function in the
foo/SConscript
file like this:
Import('env') obj = env.Object('foo.c') Return('obj')
(The corresponding
bar/SConscript
file should be pretty obvious.)
Then when we run SCons,
the object files from the subsidiary subdirectories
are all correctly archived in the desired library:
% scons -Q
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