Install toolchain into tools_bin rather than /usr/local
[nativeclient.git] / SConstruct
blobcb59c1764c7d91592ceb148a747ea39e4ceab9bd
1 # Copyright 2008, Google Inc.
2 # All rights reserved.
3 #
4 # Redistribution and use in source and binary forms, with or without
5 # modification, are permitted provided that the following conditions are
6 # met:
7 #
8 # * Redistributions of source code must retain the above copyright
9 # notice, this list of conditions and the following disclaimer.
10 # * Redistributions in binary form must reproduce the above
11 # copyright notice, this list of conditions and the following disclaimer
12 # in the documentation and/or other materials provided with the
13 # distribution.
14 # * Neither the name of Google Inc. nor the names of its
15 # contributors may be used to endorse or promote products derived from
16 # this software without specific prior written permission.
18 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19 # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20 # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21 # A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22 # OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23 # SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24 # LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 # DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 # THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 import glob
32 import os
33 import stat
34 import sys
35 sys.path.append("./common")
36 import nacl_util
39 # Underlay gtest
40 Dir('gtest').addRepository(Dir('../third_party/gtest'))
43 environment_list = []
45 # ----------------------------------------------------------
46 # Base environment for both nacl and non-nacl variants.
47 pre_base_env = Environment(
48 tools = ['component_setup'],
49 # Makes SOURCE_ROOT independent of site_init.
50 SOURCE_ROOT = Dir('#/../..').abspath,
51 # Publish dlls as final products (to staging).
52 COMPONENT_LIBRARY_PUBLISH = True,
54 pre_base_env.Append(BUILD_GROUPS=['most'])
55 # ----------------------------------------------------------
56 # Small tests are usually unit tests
57 NODE_SMALL_TEST = pre_base_env.Alias(target='small_tests')
59 def AddNodeToSmallTestsSuite(env, node):
60 NODE_SMALL_TEST[0].add_dependency(node)
62 pre_base_env.AddMethod(AddNodeToSmallTestsSuite)
64 # ----------------------------------------------------------
65 # Medium tests are usually larger than unit tests, but don't take as much time
66 # as large tests
67 NODE_MEDIUM_TEST = pre_base_env.Alias(target='medium_tests')
69 def AddNodeToMediumTestsSuite(env, node):
70 NODE_MEDIUM_TEST[0].add_dependency(node)
72 pre_base_env.AddMethod(AddNodeToMediumTestsSuite)
74 # ----------------------------------------------------------
75 # Large tests are usually long tests
76 NODE_LARGE_TESTS = pre_base_env.Alias(target='large_tests')
78 def AddNodeToLargeTestsSuite(env, node):
79 NODE_LARGE_TESTS[0].add_dependency(node)
81 pre_base_env.AddMethod(AddNodeToLargeTestsSuite)
83 # ----------------------------------------------------------
84 NODE_SMOKE_TEST = pre_base_env.Alias(target='smoke_test')
86 def AddNodeToSmokeTestSuite(env, node):
87 NODE_SMOKE_TEST[0].add_dependency(node)
89 pre_base_env.AddMethod(AddNodeToSmokeTestSuite)
91 def _SmokeTestIntro(**args):
92 Banner("Running Smoke Test")
94 node = pre_base_env.Command(target='dummy',
95 source=[],
96 action=_SmokeTestIntro)
98 AlwaysBuild(node)
99 pre_base_env.AddNodeToSmokeTestSuite(node)
101 # ----------------------------------------------------------
102 def Banner(text):
103 print '=' * 70
104 print text
105 print '=' * 70
107 pre_base_env.AddMethod(Banner)
110 def FindLikelySelLdr(directory):
111 candidates = []
112 if (nacl_util.GetSelLdr('opt')):
113 candidates.append(nacl_util.GetSelLdr('opt'))
114 if (nacl_util.GetSelLdr('dbg')):
115 candidates.append(nacl_util.GetSelLdr('dbg'))
116 latest = (None, 0)
117 for c in candidates:
118 mtime = os.stat(c)[stat.ST_MTIME]
119 if mtime > latest[1]:
120 latest = (c, mtime)
121 return latest[0]
124 def CommandSelLdrTestNacl(env, name, exe, guess_sel_ldr=False, flags='" "',
125 stdin='None', stdout='None', filter='" "'):
126 script = '${SCONSTRUCT_DIR}/tools/sel_ldr_tester.py'
127 if guess_sel_ldr:
128 sel_ldr = FindLikelySelLdr(env.subst('$DESTINATION_ROOT'))
129 # Bail out if sel_ldr can't be found.
130 if not sel_ldr: return []
131 else:
132 sel_ldr = '$STAGING_DIR/${PROGPREFIX}sel_ldr${PROGSUFFIX}'
133 deps = [script, sel_ldr, exe]
134 if stdin != 'None': deps.append(stdin)
135 if stdout != 'None': deps.append(stdout)
136 # TODO: consider redirecting output into tests/results
137 return env.Command(name, deps,
138 '$PYTHON ${SOURCES[0].abspath} '
139 '${SOURCES[1].abspath} '
140 '${SOURCES[2].abspath} '
141 '%s %s %s %s > $TARGET' % (
142 flags, stdin, stdout, filter))
144 pre_base_env.AddMethod(CommandSelLdrTestNacl)
146 # ----------------------------------------------------------
147 if ARGUMENTS.get('pp', 0):
148 def CommandPrettyPrinter(cmd, targets, source, env):
149 prefix = env.subst('$SOURCE_ROOT') + '/googleclient/'
150 target = targets[0]
151 cmd_tokens = cmd.split()
152 if "python" in cmd_tokens[0]:
153 cmd_name = cmd_tokens[1]
154 else:
155 cmd_name = cmd_tokens[0].split('(')[0]
156 if cmd_name.startswith(prefix):
157 cmd_name = cmd_name[len(prefix):]
158 env_name = env.subst('${BUILD_TYPE}${BUILD_SUBTYPE}')
159 print '[%s] [%s] %s' % (cmd_name, env_name, target.get_path())
160 pre_base_env.Append(PRINT_CMD_LINE_FUNC = CommandPrettyPrinter)
162 # ----------------------------------------------------------
163 base_env = pre_base_env.Clone()
164 base_env.Append(
165 BUILD_SUBTYPE = '',
166 BUILD_SCONSCRIPTS = [
167 # NOTE: this dir also has a SConscript.nacl
168 'tests/npapi_bridge/SConscript',
169 'ncv',
170 'service_runtime',
171 'service_runtime/nrd_xfer_lib',
172 'tools/libsrpc/SConscript.nonnacl',
173 'tools/npapi_runtime',
174 'intermodule_comm',
175 'npapi_plugin',
176 'npapi_plugin/install.scons',
177 'gtest',
178 'nonnacl_util',
179 # 'nacl_ie_plugin',
181 CPPDEFINES = [
182 ['NACL_BLOCK_SHIFT', '5'],
183 ['NACL_BLOCK_SIZE', '32'],
185 GEN2_FLAGS = '-c -f "Video|Audio|Multimedia"',
187 base_env.Replace(
188 SDL_HERMETIC_LINUX_DIR='$MAIN_DIR/../third_party/sdl/linux/v1_2_13',
189 SDL_HERMETIC_MAC_DIR='$MAIN_DIR/../third_party/sdl/osx/v1_2_13',
190 SDL_HERMETIC_WINDOWS_DIR='$MAIN_DIR/../third_party/sdl/win/v1_2_13',
195 # Optionally ignore the build process.
196 DeclareBit('prebuilt', 'Disable all build steps, only support install steps')
197 base_env.SetBitFromOption('prebuilt', False)
198 if base_env.Bit('prebuilt'):
199 base_env.Replace(BUILD_SCONSCRIPTS = ['npapi_plugin/install.scons'])
201 # Add the sdk root path (without setting up the tools).
202 base_env['NACL_SDK_ROOT_ONLY'] = True
203 base_env.Tool('naclsdk')
206 base_env.Help("""\
207 ======================================================================
208 Help for NaCl
209 ======================================================================
211 Common tasks:
212 -------------
214 * cleaning: scons -c
215 * build mandel: scons MODE=all mandel.nexe
216 * some unittests: scons run_unit_tests
217 * a smoke test: scons -k pp=1 smoke_test
218 * 2nd smoke test: scons -k pp=1 MODE=nacl smoke_test
219 * documentation: scons MODE=doc
220 * firefox plugin: scons MODE=opt-linux npGoogleNaClPlugin
221 * sel_ldr: scons MODE=opt-linux sel_ldr
222 * firefox install: scons firefox_install
224 Options:
225 --------
226 pp=1 use command line pretty printing (more concise output)
227 sdl=<mode> where <mode>:
228 'none': don't use SDL (default)
229 'local': use locally installed SDL
230 'hermetic': use the hermetic SDL copy
231 naclsdk_mode=<mode> where <mode>:
232 'local': use locally installed sdk kit
233 'download': use the download copy (default)
234 'custom:<path>': use kit at <path>
236 Automagically generated help:
237 -----------------------------
238 """)
240 # ----------------------------------------------------------
241 windows_env = base_env.Clone(
242 tools = ['target_platform_windows'],
243 ASCOM = '$ASPPCOM /E | as -o $TARGET',
244 PDB = '${TARGET.base}.pdb',
246 windows_env.Append(
247 CPPDEFINES = [
248 ['NACL_WINDOWS', '1'],
249 ['NACL_OSX', '0'],
250 ['NACL_LINUX', '0'],
251 ['_WIN32_WINNT', '0x0501']
253 NACL_PLATFORM = 'win',
254 LIBS = ['wsock32', 'advapi32'],
255 CCFLAGS = ['/EHsc'],
258 windows_debug_env = windows_env.Clone(
259 tools = ['target_debug'],
260 BUILD_TYPE = 'dbg-win',
261 BUILD_TYPE_DESCRIPTION = 'Windows debug build',
264 windows_debug_env.Append(BUILD_GROUPS = ['default'])
265 environment_list.append(windows_debug_env)
267 windows_optimized_env = windows_env.Clone(
268 tools = ['target_optimized'],
269 BUILD_TYPE = 'opt-win',
270 BUILD_TYPE_DESCRIPTION = 'Windows optimized build',
272 environment_list.append(windows_optimized_env)
274 if ARGUMENTS.get('sdl', 'hermetic') != 'none':
275 # These will only apply to sdl!=none builds!
276 windows_debug_env.Append(
277 CPPDEFINES = [
278 '_DLL',
279 '_MT'])
280 windows_optimized_env.Append(
281 CPPDEFINES = [
282 '_DLL',
283 '_MT'])
284 # SDL likes DLLs
285 if '/MT' in windows_optimized_env['CCFLAGS']:
286 windows_optimized_env.FilterOut(CCFLAGS=['/MT']);
287 windows_optimized_env.Append(CCFLAGS=['/MD']);
288 if '/MTd' in windows_debug_env['CCFLAGS']:
289 windows_debug_env.FilterOut(CCFLAGS=['/MTd']);
290 windows_debug_env.Append(CCFLAGS=['/MDd']);
291 # this doesn't feel right, but fixes dbg-win
292 windows_debug_env.Append(LINKFLAGS = ['/NODEFAULTLIB:msvcrt'])
293 # make source level debugging a little easier
294 if '/Z7' not in windows_debug_env['CCFLAGS']:
295 if '/Zi' not in windows_debug_env['CCFLAGS']:
296 windows_debug_env.Append(CCFLAGS=['/Z7'])
298 # ----------------------------------------------------------
300 unix_like_env = base_env.Clone()
301 unix_like_env.Append(
302 CCFLAGS = [
303 # '-malign-double',
304 '-Werror',
305 '-Wall',
306 # '-Wswitch-enum',
307 '-fvisibility=hidden',
308 '-Wno-unused-variable',
309 # '-Wsign-compare',
311 CFLAGS = ['-std=gnu99'],
312 LIBS = ['pthread', 'ssl', 'crypto'],
315 # ----------------------------------------------------------
317 mac_env = unix_like_env.Clone(
318 tools = ['target_platform_mac'],
319 # TODO: this should really be able to live in unix_like_env
320 # but can't due to what the target_platform_x module is
321 # doing.
322 LINK = '$CXX',
323 PLUGIN_SUFFIX = '.bundle',
325 mac_env.Append(
326 CPPDEFINES = [
327 ['NACL_WINDOWS', '0'],
328 ['NACL_OSX', '1'],
329 ['NACL_LINUX', '0'],
330 ['MAC_OS_X_VERSION_MIN_REQUIRED', 'MAC_OS_X_VERSION_10_4'],
332 NACL_PLATFORM = 'osx',
333 CCFLAGS = ['-mmacosx-version-min=10.4']
336 mac_debug_env = mac_env.Clone(
337 tools = ['target_debug'],
338 BUILD_TYPE = 'dbg-mac',
339 BUILD_TYPE_DESCRIPTION = 'MacOS debug build',
341 mac_debug_env.Append(BUILD_GROUPS = ['default'])
342 environment_list.append(mac_debug_env)
344 mac_optimized_env = mac_env.Clone(
345 tools = ['target_optimized'],
346 BUILD_TYPE = 'opt-mac',
347 BUILD_TYPE_DESCRIPTION = 'MacOS optimized build',
349 environment_list.append(mac_optimized_env)
351 # ----------------------------------------------------------
353 linux_env = unix_like_env.Clone(
354 tools = ['target_platform_linux'],
355 # TODO: this should really be able to live in unix_like_env
356 # but can't due to what the target_platform_x module is
357 # doing.
358 LINK = '$CXX',
361 # -m32 and -L/usr/lib32 are needed to do 32-bit builds on 64-bit
362 # user-space machines; requires ia32-libs-dev to be installed; or,
363 # failing that, ia32-libs and symbolic links *manually* created for
364 # /usr/lib32/libssl.so and /usr/lib32/libcrypto.so to the current
365 # /usr/lib32/lib*.so.version (tested with ia32-libs 2.2ubuntu11; no
366 # ia32-libs-dev was available for testing).
368 linux_env.SetDefault(
369 # NOTE: look into http://www.scons.org/wiki/DoxygenBuilder
370 DOXYGEN = ARGUMENTS.get('DOXYGEN', '/usr/bin/doxygen'),
373 linux_env.Append(
374 ASFLAGS = [ '-m32', ],
375 CFLAGS = [ '-m32', ],
376 CCFLAGS = [ '-m32', ],
377 CPPDEFINES = [
378 ['NACL_WINDOWS', '0'],
379 ['NACL_OSX', '0'],
380 ['NACL_LINUX', '1'],
382 LIBS = ['rt'],
383 LINKFLAGS = [ '-m32', '-L/usr/lib32', ],
384 NACL_PLATFORM = 'linux',
388 linux_debug_env = linux_env.Clone(
389 tools = ['target_debug'],
390 BUILD_TYPE = 'dbg-linux',
391 BUILD_TYPE_DESCRIPTION = 'Linux debug build',
393 linux_debug_env.Append(BUILD_GROUPS = ['default'])
394 environment_list.append(linux_debug_env)
396 linux_optimized_env = linux_env.Clone(
397 tools = ['target_optimized'],
398 BUILD_TYPE = 'opt-linux',
399 BUILD_TYPE_DESCRIPTION = 'Linux optimized build',
401 environment_list.append(linux_optimized_env)
404 # ----------------------------------------------------------
405 # The nacl_env is used to build native_client modules
406 # using a special tool chain which produces platform
407 # independent binaries
408 # ----------------------------------------------------------
409 nacl_env = pre_base_env.Clone(
410 tools = ['naclsdk'],
411 BUILD_TYPE = 'nacl',
412 BUILD_TYPE_DESCRIPTION = 'NaCl module build',
413 # TODO: explain this
414 LINK = '$CXX',
415 # hook for app to specify extra libraries
416 LIBS = "$EXTRA_LIBS",
417 # optimize binaries
418 CCFLAGS = ['-O2', '-mfpmath=sse', '-msse', '-fomit-frame-pointer'],
419 # TODO: explain this
420 CPPPATH = ['$SOURCE_ROOT/googleclient'],
423 Banner('Building nexe binaries using sdk at [%s]' %
424 nacl_env.subst('$NACL_SDK_ROOT'))
427 nacl_env.Append(
428 BUILD_SCONSCRIPTS = [
429 #### ALPHABETICALLY SORTED ####
430 'intermodule_comm/SConscript.nacl',
433 'tests/app_lib/SConscript.nacl',
434 'tests/cloudfs/SConscript.nacl',
435 'tests/earth/SConscript.nacl',
436 'tests/fib/SConscript.nacl',
437 'tests/file/SConscript.nacl',
438 'tests/hello_world/SConscript.nacl',
439 'tests/imc_shm_mmap/SConscript.nacl',
440 'tests/life/SConscript.nacl',
441 'tests/mandel/SConscript.nacl',
442 'tests/mandel_nav/SConscript.nacl',
443 'tests/mmap/SConscript.nacl',
444 'tests/noop/SConscript.nacl',
445 'tests/npapi_bridge/SConscript.nacl',
446 'tests/npapi_hw/SConscript.nacl',
447 'tests/npapi_pi/SConscript.nacl',
448 'tests/nrd_xfer/SConscript.nacl',
449 'tests/null/SConscript.nacl',
450 'tests/srpc/SConscript.nacl',
451 'tests/srpc_hw/SConscript.nacl',
452 'tests/syscalls/SConscript.nacl',
453 'tests/threads/SConscript.nacl',
454 'tests/tone/SConscript.nacl',
455 'tests/voronoi/SConscript.nacl',
457 'tools/libsrpc/SConscript.nacl',
458 'tools/npapi_runtime/SConscript.nacl',
459 #### ALPHABETICALLY SORTED ####
463 # Uncomment this if you want the nacl stuff to be build by default.
464 #nacl_env.Append(BUILD_GROUPS = ['default'])
465 environment_list.append(nacl_env)
467 # ----------------------------------------------------------
468 # CODE COVERAGE
469 # ----------------------------------------------------------
470 # ----------------------------------------------------------
471 # VARIOUS HELPERS
472 # ----------------------------------------------------------
474 doc_env = pre_base_env.Clone(
475 BUILD_TYPE = 'doc',
476 BUILD_TYPE_DESCRIPTION = 'Documentation build',
477 HOST_PLATFORMS = '*',
479 doc_env.FilterOut(BUILD_GROUPS=['most'])
480 environment_list.append(doc_env)
481 doc_env.Append(
482 BUILD_SCONSCRIPTS = [
483 'documentation',
488 # ----------------------------------------------------------
490 # Blank out defaults.
491 Default(None)
493 BuildComponents(environment_list)
495 # Change default to build everything, but not run tests.
496 Default(['all_programs', 'all_bundles', 'all_test_programs', 'all_libraries'])
498 # ----------------------------------------------------------
501 # Generate a solution, defer to the end.
502 solution_env = base_env.Clone(tools = ['visual_studio_solution'])
503 solution = solution_env.Solution(
504 'nacl', environment_list,
505 exclude_pattern = '.*third_party.*',
506 extra_build_targets = {
507 'Firefox': 'c:/Program Files/Mozilla FireFox/firefox.exe',
510 solution_env.Alias('solution', solution)