用户在执行 SCons
的外部环境变量设置是,可以使用 python
的 os.ennviron
模块,可以将 import os
放在任意 SConstruct
中,并在该文件中使用用户外部环境变量。
import os
env = os.environ
print("current OS is", env["OS"])
执行 socns
结果就是 ‘Windows_NT’,对此,认为可以使用用户环境变量或者是系统环境变量。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q
('current OS is', 'Windows_NT')
scons: `.' is up to date.
特此说明,SCons
可以使用大部分 python
中的语法、环境、库等信息,模块调用也可以共享。
在一个构建环境中,可以对环境内容进行设置,例如设置不同编译器,优化等级,库文件,头文件搜索路径或者其他参数,此时需要使用 Environment
相关函数。
env = Environment(CC='gcc', CCFLAGS='-O2')
env.Program('hello.c')
执行 scons
之后的结果就是下面结果,可以看出和之前不同的是,编译语句增加了 -O2
的优化等级,和设置的一致。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q
gcc -o hello.o -c -O2 hello.c
gcc -o hello.exe hello.o
除了可以设置环境变量之外,也可以通过 get
函数获取变量的值,并打印输出。
env = Environment()
print("CC is: %s" % env['CC'])
print("LATEX is: %s" % env.get('LATEX', None))
执行 scons
之后的结果就是下面结果,默认编译器就是 gcc
, LATEX
变量没有值,使用了设置的默认值 None
。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q
CC is: gcc
LATEX is: None
scons: `.' is up to date.
查看默认 SCons
的默认变量,可以使用下面语句:
env = Environment()
for item in sorted(env.Dictionary().items()):
print("construction variable = '%s', value = '%s'" % item)
# 或者
env = Environment()
print(env.Dump())
在一个命令不知道怎么使用时,使用 --help
来获取当前命令的选项帮助是最好的方法。SCons 也是提供了 help
选项的编写,可以帮助用户简单的创建 --help
的语句。
Help("""
Type: 'scons program' to build the production program,
'scons debug' to build the debug version.
""")
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -h
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.
使用 -H
可以看有关 SCons
的帮助文档。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -H
usage: scons [OPTION] [TARGET] ...
SCons Options:
-b, -d, -e, -m, -S, -t, -w, --environment-overrides, --no-keep-going,
--no-print-directory, --print-directory, --stop, --touch
Ignored for compatibility.
-c, --clean, --remove Remove specified targets and dependencies.
-C DIR, --directory=DIR Change to DIR before doing anything.
--cache-debug=FILE Print CacheDir debug info to FILE.
--cache-disable, --no-cache
Do not retrieve built targets from CacheDir.
--cache-force, --cache-populate
Copy already-built targets into the CacheDir.
--cache-readonly Do not update CacheDir with built targets.
--cache-show Print build actions for files from CacheDir.
--config=MODE Controls Configure subsystem: auto, force,
cache.
-D Search up directory tree for SConstruct,
build all Default() targets.
--debug=TYPE Print various types of debugging information:
count, duplicate, explain, findlibs, includes,
memoizer, memory, objects, pdb, prepare,
presub, stacktrace, time, action-timestamps.
--diskcheck=TYPE Enable specific on-disk checks.
--duplicate=DUPLICATE Set the preferred duplication methods. Must be
one of hard-soft-copy, soft-hard-copy,
hard-copy, soft-copy, copy
--enable-virtualenv Import certain virtualenv variables to SCons
-f FILE, --file=FILE, --makefile=FILE, --sconstruct=FILE
Read FILE as the top-level SConstruct file.
-h, --help Print defined help message, or this one.
-H, --help-options Print this message and exit.
-i, --ignore-errors Ignore errors from build actions.
-I DIR, --include-dir=DIR Search DIR for imported Python modules.
--ignore-virtualenv Do not import virtualenv variables to SCons
--implicit-cache Cache implicit dependencies
--implicit-deps-changed Ignore cached implicit dependencies.
--implicit-deps-unchanged Ignore changes in implicit dependencies.
--interact, --interactive Run in interactive mode.
-j N, --jobs=N Allow N jobs at once.
-k, --keep-going Keep going when a target can't be made.
--max-drift=N Set maximum system clock drift to N seconds.
--md5-chunksize=N Set chunk-size for MD5 signature computation to
N kilobytes.
-n, --no-exec, --just-print, --dry-run, --recon
Don't build; just print commands.
--no-site-dir Don't search or use the usual site_scons dir.
--profile=FILE Profile SCons and put results in FILE.
-q, --question Don't build; exit status says if up to date.
-Q Suppress "Reading/Building" progress messages.
--random Build dependencies in random order.
-s, --silent, --quiet Don't print commands.
--site-dir=DIR Use DIR instead of the usual site_scons dir.
--stack-size=N Set the stack size of the threads used to run
jobs to N kilobytes.
--taskmastertrace=FILE Trace Node evaluation to FILE.
--tree=OPTIONS Print a dependency tree in various formats: all,
derived, prune, status.
-u, --up, --search-up Search up directory tree for SConstruct,
build targets at or below current directory.
-U Search up directory tree for SConstruct,
build Default() targets from local SConscript.
-v, --version Print the SCons version number and exit.
--warn=WARNING-SPEC, --warning=WARNING-SPEC
Enable or disable warnings.
-Y REPOSITORY, --repository=REPOSITORY, --srcdir=REPOSITORY
Search REPOSITORY for source and target files.
可以使用 ARGUMENTS.get
来获取命令行参数,在一些情况下,可以增加选项以增加多个项目的构建。
env = Environment()
if ARGUMENTS.get('VERBOSE') != '1':
print("VERBOSE")
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q
VERBOSE
scons: '.' is up to date.
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q VERBOSE=1
scons: '.' is up to date.
或者使用 set PARAM=VALUE
方式显式设置参数的值。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ set SCONSFLAGS=-Q
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons
VERBOSE
scons: `.' is up to date.
SCsonstruct
内容如下,在命令行使用 -h, --help
时,可以使用 GetOption
来获取 help
参数,如果有 help
选项,则输出 help text
文本,没有 help
选项时,输出 not help
。if not GetOption('help'):
SConscript('SConscript', export='env')
print("not hellp")
else :
Help("help text")
print("hellp")
可以看出预期结果进行输出。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -h
hellp
help text
Use scons -H for help about command-line options.
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons
not hellp
scons: `.' is up to date.
使用 SetOption
可以设置命令行选项,例如设置 GetOption('help')
就可以看作是执行了 scons -h
。
import os
SetOption('help', "1")
print("help : %s" % GetOption('help'))
Program('hello.c')
下面可以看到 SCson
的可选项有 -h, -d, -e, -m, -S, -t, -w
等,可以使用 SetOption
进行配置。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons
scons: Reading SConscript files ...
help : 1
scons: done reading SConscript files.
usage: scons [OPTION] [TARGET] ...
SCons Options:
-b, -d, -e, -m, -S, -t, -w, --environment-overrides, --no-keep-going,
--no-print-directory, --print-directory, --stop, --touch
可以使用 GetOption
或者 SetOption
的选项如下:
String for GetOption and SetOption | Command-Line Option(s) |
---|---|
cache_debug | –cache-debug |
cache_disable | –cache-disable |
cache_force | –cache-force |
cache_show | –cache-show |
clean | -c, --clean, --remove |
config | –config |
directory | -C, --directory |
diskcheck | –diskcheck |
duplicate | –duplicate |
file | -f, --file, --makefile , --sconstruct |
help | -h, --help |
ignore_errors | –ignore-errors |
implicit_cache | –implicit-cache |
implicit_deps_changed | –implicit-deps-changed |
implicit_deps_unchanged | –implicit-deps-unchanged |
interactive | –interact, --interactive |
keep_going | -k, --keep-going |
max_drift | –max-drift |
no_exec | -n, --no-exec, --just-print, --dry-run, --recon |
no_site_dir | –no-site-dir |
num_jobs | -j, --jobs |
profile_file | –profile |
question | -q, --question |
random | –random |
repository | -Y, --repository, --srcdir |
silent | -s, --silent, --quiet |
site_dir | –site-dir |
stack_size | –stack-size |
taskmastertrace_file | –taskmastertrace |
warn | –warn --warning |
暂时不做解释
随时可以在构建命令中,使用 ARGUMENTS
或者 增加选项来通过 GetOption
来获取命令行中的选项变量,但是每次执行,都需要开发者对执行命令特别熟悉,以防止漏掉选项造成编译失败或者编译与实际情况不符等现象。为了解决上述问题,可以使用 python
读取一个文件,文件内存储使用的选项变量。SCons
提供了 Variables
类来处理构建变量,来影响整个构建过程。
vars = Variables(None, ARGUMENTS)
vars.Add('HELLO_BUILD', default=0)
env = Environment(variables=vars, CPPDEFINES={'HELLO': '${HELLO_BUILD}'})
env.Program(['hello.c'])
执行 scons -Q -HELLO_BUILD=1
可以得到以下输出。
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q HELLO_BUILD=1
gcc -o hello.o -c -DHELLO=1 hello.c
gcc -o hello.exe hello.o
创建外部文件,作为选项的存放文件,所有的选项都放在这个文件内,使用时通过 python
来读取每个选项,并增加到当前环境中。
vars = Variables('var.py', ARGUMENTS)
vars.Add('HELLO_BUILD')
env = Environment(variables=vars, CPPDEFINES={'HELLO': '${HELLO_BUILD}'})
env.Program(['hello.c'])
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q
gcc -o hello.o -c -DHELLO=2 hello.c
gcc -o hello.exe hello.o
同时可以使用 BoolVariable
类来创建一个变量,使用 Add
来添加到当前环境中。三个参数依次是: 参数名称, 帮助信息, 默认值。bool变量可以是 True 和 False 两个值。 yes,y,t,True 都认为是 True, no,n,f,False 都认为是 False。
vars = Variables('var1.py', ARGUMENTS)
vars.Add(BoolVariable('HELLO_BUILD', help='Set to build for release', default=0))
env = Environment(variables=vars, CPPDEFINES={'HELLO': '${HELLO_BUILD}'})
env.Program(['hello.c'])
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q HELLO_BUILD=t
gcc -o hello.o -c -DHELLO=True hello.c
admin@DESKTOP-NQU1HUV C:\Users\admin\Desktop\scons\day6
$ scons -Q HELLO_BUILD=yes
gcc -o hello.o -c -DHELLO=True hello.c
gcc -o hello.exe hello.o
初此之外,还有其他类来实现变量的创建,下面简单介绍:
# enmu
vars.Add(
EnumVariable(
'COLOR',
help='Set background color',
default='red',
allowed_values=('red', 'green', 'blue'),
map={'navy': 'blue'},
)
)
# 增加一个 map 参数,是一个设置别名的方法,例如 `navy` 可以当作是 `blue` 的别名,是同样的意思。
# 枚举变量的值默认是严格大小写区分的,需要注意。如果要忽略大小写,可以增加 `ignorecase=1,` 的参数
#
# 可以使用 --help 来查看当前 enum 的取值范围
scons -Q -h
COLOR: Set background color (red|green|blue)
default: red
actual: red
ignorecase
的使用方法:
当值为1的时候,忽略命令行参数值的大小写,且将命令行参数直接添加到构建环境内。
ignorecase = 1
==> scons -Q COLOR=Red foo.o cc -o foo.o -c -DCOLOR="Red" foo.c
当值为2的时候,忽略命令行参数值的大小写,且将命令行参数转为全小写添加到构建环境内。
ignorecase = 2
==> scons -Q COLOR=Red foo.o cc -o foo.o -c -DCOLOR="red" foo.c
可以使用 ListVariable
一次增加多个选项。具体应用如下:
vars = Variables('custom.py')
vars.Add(
ListVariable(
'COLORS', help='List of colors', default=0, names=['red', 'green', 'blue']
)
)
env = Environment(variables=vars, CPPDEFINES={'COLORS': '"${COLORS}"'})
env.Program('foo.c')
执行结果:
% scons -Q COLORS=red,blue foo.o
cc -o foo.o -c -DCOLORS="red -Dblue" foo.c
% scons -Q COLORS=blue,green,red foo.o
cc -o foo.o -c -DCOLORS="blue -Dgreen -Dred" foo.c
PathVariable
来方便的创建构建变量的文件。例如如果选哟创建一个配置文件,来包含需要的选项,则按照一下操作:创建 config.cfg
文件,内容为选项值:
COLOR=red
vars = Variables('custom.py')
vars.Add(
PathVariable(
'CONFIG',
help='Path to configuration file',
default='config.cfg',
validator=PathVariable.PathIsFile,
)
)
env = Environment(variables=vars, CPPDEFINES={'CONFIG_FILE': '"$CONFIG"'})
env.Program('foo.c')
执行过程:
% scons -Q foo.o
cc -o foo.o -c -DCONFIG_FILE="config.cfg" foo.c
% scons -Q CONFIG=./config.cfg foo.o
scons: 'foo.o' is up to date.
其中 validator
可以设置验证函数,验证功能函数有以下几个:
如果想确保任何指定路径实际上都需要是文件而不是目录,请使用 PathVariable.PathIsFile
作为验证函数。
如果是目录,则需要使用 PathVariable.PathIsDir
,并修改下面传入参数 env = Environment(variables=vars, CPPDEFINES={'DBDIR': '"$DBDIR"'})
。
如果目录不存在,且需要创建,则需要使用 PathVariable.PathIsDirCreate
,并修改下面传入函数 env = Environment(variables=vars, CPPDEFINES={'DBDIR': '"$DBDIR"'})
。
如果不关心输入的是文件还是目录是否存在,则需要使用 PathVariable.PathAccept
PackageVariable
后面详细介绍
UnknownVariables
SCons
提供了一个 COMMAND_LINE_TARGETS
变量来保存命令行中的目标参数,如果需要的话,可以对目标进行检查,做出对应的处理。
下面举例说明: 对 hello
目标的显示构建,在构建过程中显示,提示开发者。
if 'hello' in COMMAND_LINE_TARGETS:
print("hello is being built!!! ")
Default(Program('hello.c'))
Program('hello.c')
但是实际执行,一直在出错,暂时不做测试,后期进行补充。
SCons
在默认状态下,会对构建脚本中所有目标进行构建,如果需要默认构建一个目标,则需要使用 Default
来指定构建目标。
没有测试出来,后面进行补充