Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(99)

Side by Side Diff: native_client_sdk/src/build_tools/generate_make.py

Issue 13488007: [NaCl SDK] Make the SDK examples buildable as a packaged app. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: fix license headers Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 #!/usr/bin/env python 1 #!/usr/bin/env python
2 # Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 # Copyright (c) 2012 The Chromium Authors. All rights reserved.
3 # Use of this source code is governed by a BSD-style license that can be 3 # Use of this source code is governed by a BSD-style license that can be
4 # found in the LICENSE file. 4 # found in the LICENSE file.
5 5
6 import cStringIO 6 import cStringIO
7 import optparse 7 import optparse
8 import os 8 import os
9 import sys 9 import sys
10 10
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
80 80
81 81
82 def GetProjectObjects(source_dict): 82 def GetProjectObjects(source_dict):
83 object_list = [] 83 object_list = []
84 for key in ['.c', '.cc']: 84 for key in ['.c', '.cc']:
85 for src in source_dict[key]: 85 for src in source_dict[key]:
86 object_list.append(os.path.splitext(src)[0]) 86 object_list.append(os.path.splitext(src)[0])
87 return object_list 87 return object_list
88 88
89 89
90 def GetPlatforms(plat_list, plat_filter): 90 def GetPlatforms(plat_list, plat_filter, first_toolchain):
91 platforms = [] 91 platforms = []
92 for plat in plat_list: 92 for plat in plat_list:
93 if plat in plat_filter: 93 if plat in plat_filter:
94 platforms.append(plat) 94 platforms.append(plat)
95
96 if first_toolchain:
97 return [platforms[0]]
95 return platforms 98 return platforms
96 99
97 100
98 # 'KEY' : ( <TYPE>, [Accepted Values], <Required?>) 101 # 'KEY' : ( <TYPE>, [Accepted Values], <Required?>)
99 DSC_FORMAT = { 102 DSC_FORMAT = {
100 'TOOLS' : (list, ['newlib:arm', 'newlib:x64', 'newlib:x86', 'newlib', 103 'TOOLS' : (list, ['newlib:arm', 'newlib:x64', 'newlib:x86', 'newlib',
101 'glibc', 'pnacl', 'win', 'linux'], True), 104 'glibc', 'pnacl', 'win', 'linux'], True),
102 'CONFIGS' : (list, ['Debug', 'Release'], False), 105 'CONFIGS' : (list, ['Debug', 'Release'], False),
103 'PREREQ' : (list, '', False), 106 'PREREQ' : (list, '', False),
104 'TARGETS' : (list, { 107 'TARGETS' : (list, {
105 'NAME': (str, '', True), 108 'NAME': (str, '', True),
106 'TYPE': (str, ['main', 'lib', 'so'], True), 109 # main = nexe target
110 # lib = library target
111 # so = shared object target, automatically added to NMF
112 # so-standalone = shared object target, not put into NMF
113 'TYPE': (str, ['main', 'lib', 'so', 'so-standalone'], True),
107 'SOURCES': (list, '', True), 114 'SOURCES': (list, '', True),
108 'CCFLAGS': (list, '', False), 115 'CCFLAGS': (list, '', False),
109 'CXXFLAGS': (list, '', False), 116 'CXXFLAGS': (list, '', False),
110 'DEFINES': (list, '', False), 117 'DEFINES': (list, '', False),
111 'LDFLAGS': (list, '', False), 118 'LDFLAGS': (list, '', False),
112 'INCLUDES': (list, '', False), 119 'INCLUDES': (list, '', False),
113 'LIBS' : (list, '', False), 120 'LIBS' : (list, '', False),
114 'DEPS' : (list, '', False) 121 'DEPS' : (list, '', False)
115 }, True), 122 }, True),
116 'HEADERS': (list, { 123 'HEADERS': (list, {
117 'FILES': (list, '', True), 124 'FILES': (list, '', True),
118 'DEST': (str, '', True), 125 'DEST': (str, '', True),
119 }, False), 126 }, False),
120 'SEARCH': (list, '', False), 127 'SEARCH': (list, '', False),
121 'POST': (str, '', False), 128 'POST': (str, '', False),
122 'PRE': (str, '', False), 129 'PRE': (str, '', False),
123 'DEST': (str, ['examples', 'src', 'testlibs', 'tests'], True), 130 'DEST': (str, ['examples', 'src', 'testlibs', 'tests'], True),
124 'NAME': (str, '', False), 131 'NAME': (str, '', False),
125 'DATA': (list, '', False), 132 'DATA': (list, '', False),
126 'TITLE': (str, '', False), 133 'TITLE': (str, '', False),
127 'DESC': (str, '', False),
128 'FOCUS': (str, '', False),
129 'GROUP': (str, '', False), 134 'GROUP': (str, '', False),
130 'EXPERIMENTAL': (bool, [True, False], False) 135 'EXPERIMENTAL': (bool, [True, False], False)
131 } 136 }
132 137
133 138
134 def ErrorMsgFunc(text): 139 def ErrorMsgFunc(text):
135 sys.stderr.write(text + '\n') 140 sys.stderr.write(text + '\n')
136 141
137 142
138 def ValidateFormat(src, dsc_format, ErrorMsg=ErrorMsgFunc): 143 def ValidateFormat(src, dsc_format, ErrorMsg=ErrorMsgFunc):
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after
246 return None 251 return None
247 252
248 253
249 def IsNexe(desc): 254 def IsNexe(desc):
250 for target in desc['TARGETS']: 255 for target in desc['TARGETS']:
251 if target['TYPE'] == 'main': 256 if target['TYPE'] == 'main':
252 return True 257 return True
253 return False 258 return False
254 259
255 260
256 def ProcessHTML(srcroot, dstroot, desc, toolchains): 261 def ProcessHTML(srcroot, dstroot, desc, toolchains, configs, first_toolchain):
257 name = desc['NAME'] 262 name = desc['NAME']
258 outdir = os.path.join(dstroot, desc['DEST'], name) 263 outdir = os.path.join(dstroot, desc['DEST'], name)
259 srcfile = os.path.join(srcroot, 'index.html') 264 srcfile = os.path.join(srcroot, 'index.html')
260 dstfile = os.path.join(outdir, 'index.html') 265 dstfile = os.path.join(outdir, 'index.html')
261 tools = GetPlatforms(toolchains, desc['TOOLS']) 266 tools = GetPlatforms(toolchains, desc['TOOLS'], first_toolchain)
262 267
263 if use_gyp and getos.GetPlatform() != 'win': 268 if use_gyp and getos.GetPlatform() != 'win':
264 configs = ['debug', 'release'] 269 # Make the config names lowercase when using gyp...
265 else: 270 configs = [c.lower() for c in configs]
266 configs = ['Debug', 'Release']
267 271
268 if use_gyp: 272 if use_gyp:
269 path = "build/{tc}-{config}" 273 path = "build/{tc}-{config}"
270 else: 274 else:
271 path = "{tc}/{config}" 275 path = "{tc}/{config}"
272 276
273 replace = { 277 replace = {
274 'title': desc['TITLE'], 278 'title': desc['TITLE'],
275 'attrs': 279 'attrs':
276 'data-name="%s" data-tools="%s" data-configs="%s" data-path="%s"' % ( 280 'data-name="%s" data-tools="%s" data-configs="%s" data-path="%s"' % (
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
316 ErrorExit('Failed to find: ' + src_name) 320 ErrorExit('Failed to find: ' + src_name)
317 dst_file = os.path.join(dst_dir, src_name) 321 dst_file = os.path.join(dst_dir, src_name)
318 if os.path.exists(dst_file): 322 if os.path.exists(dst_file):
319 if os.stat(src_file).st_mtime <= os.stat(dst_file).st_mtime: 323 if os.stat(src_file).st_mtime <= os.stat(dst_file).st_mtime:
320 Trace('Skipping "%s", destination "%s" is newer.' % ( 324 Trace('Skipping "%s", destination "%s" is newer.' % (
321 src_file, dst_file)) 325 src_file, dst_file))
322 continue 326 continue
323 buildbot_common.CopyFile(src_file, dst_file) 327 buildbot_common.CopyFile(src_file, dst_file)
324 328
325 329
326 def ProcessProject(srcroot, dstroot, desc, toolchains): 330 def ProcessProject(srcroot, dstroot, desc, toolchains, first_toolchain):
327 name = desc['NAME'] 331 name = desc['NAME']
328 out_dir = os.path.join(dstroot, desc['DEST'], name) 332 out_dir = os.path.join(dstroot, desc['DEST'], name)
329 buildbot_common.MakeDir(out_dir) 333 buildbot_common.MakeDir(out_dir)
330 srcdirs = desc.get('SEARCH', ['.', '..']) 334 srcdirs = desc.get('SEARCH', ['.', '..'])
331 335
332 # Copy sources to example directory 336 # Copy sources to example directory
333 sources = GenerateSourceCopyList(desc) 337 sources = GenerateSourceCopyList(desc)
334 FindAndCopyFiles(sources, srcroot, srcdirs, out_dir) 338 FindAndCopyFiles(sources, srcroot, srcdirs, out_dir)
335 339
336 # Copy public headers to the include directory. 340 # Copy public headers to the include directory.
(...skipping 22 matching lines...) Expand all
359 gyp += '.bat' 363 gyp += '.bat'
360 buildbot_common.Run([gyp, '-Gstandalone', '--format', generator, 364 buildbot_common.Run([gyp, '-Gstandalone', '--format', generator,
361 '--toplevel-dir=.', gypfile], cwd=out_dir) 365 '--toplevel-dir=.', gypfile], cwd=out_dir)
362 366
363 if sys.platform == 'win32' or not use_gyp: 367 if sys.platform == 'win32' or not use_gyp:
364 if IsNexe(desc): 368 if IsNexe(desc):
365 template = os.path.join(SCRIPT_DIR, 'template.mk') 369 template = os.path.join(SCRIPT_DIR, 'template.mk')
366 else: 370 else:
367 template = os.path.join(SCRIPT_DIR, 'library.mk') 371 template = os.path.join(SCRIPT_DIR, 'library.mk')
368 372
369 tools = {} 373 # Ensure the order of |tools| is the same as toolchains; that way if
370 tool_list = [] 374 # first_toolchain is set, it will choose based on the order of |toolchains|.
371 for tool in desc['TOOLS']: 375 tools = [tool for tool in toolchains if tool in desc['TOOLS']]
372 if ':' in tool: 376 if first_toolchain:
373 tool, arch = tool.split(':') 377 tools = [tools[0]]
374 else:
375 arch = None
376 # Ignore tools that are not enabled in this SDK build
377 if tool not in toolchains:
378 continue
379 tools.setdefault(tool, [])
380 if tool not in tool_list:
381 tool_list.append(tool)
382 if arch:
383 tools[tool].append(arch)
384
385 template_dict = { 378 template_dict = {
386 'pre': desc.get('PRE', ''), 379 'pre': desc.get('PRE', ''),
387 'tools': tool_list, 380 'tools': tools,
388 'targets': desc['TARGETS'], 381 'targets': desc['TARGETS'],
389 } 382 }
390 RunTemplateFile(template, make_path, template_dict) 383 RunTemplateFile(template, make_path, template_dict)
391 384
392 outdir = os.path.dirname(os.path.abspath(make_path)) 385 outdir = os.path.dirname(os.path.abspath(make_path))
393 pepperdir = os.path.dirname(os.path.dirname(outdir)) 386 pepperdir = os.path.dirname(os.path.dirname(outdir))
394 AddMakeBat(pepperdir, outdir) 387 AddMakeBat(pepperdir, outdir)
395 return (name, desc['DEST']) 388 return (name, desc['DEST'])
396 389
397 390
(...skipping 16 matching lines...) Expand all
414 parser.add_option('--master', help='Create master Makefile.', 407 parser.add_option('--master', help='Create master Makefile.',
415 action='store_true') 408 action='store_true')
416 parser.add_option('--newlib', help='Create newlib examples.', 409 parser.add_option('--newlib', help='Create newlib examples.',
417 action='store_true') 410 action='store_true')
418 parser.add_option('--glibc', help='Create glibc examples.', 411 parser.add_option('--glibc', help='Create glibc examples.',
419 action='store_true') 412 action='store_true')
420 parser.add_option('--pnacl', help='Create pnacl examples.', 413 parser.add_option('--pnacl', help='Create pnacl examples.',
421 action='store_true') 414 action='store_true')
422 parser.add_option('--host', help='Create host examples.', 415 parser.add_option('--host', help='Create host examples.',
423 action='store_true') 416 action='store_true')
417 parser.add_option('--config', help='Add configuration (debug/release).',
418 action='append')
424 parser.add_option('--experimental', help='Create experimental examples.', 419 parser.add_option('--experimental', help='Create experimental examples.',
425 action='store_true') 420 action='store_true')
421 parser.add_option('--first-valid-toolchain',
422 help='Only build one toolchain, the first one that is valid.',
423 action='store_true')
426 parser.add_option('-v', '--verbose', help='Verbose output', 424 parser.add_option('-v', '--verbose', help='Verbose output',
427 action='store_true') 425 action='store_true')
428 426
429 toolchains = [] 427 toolchains = []
430 platform = getos.GetPlatform() 428 platform = getos.GetPlatform()
431 429
432 options, args = parser.parse_args(argv) 430 options, args = parser.parse_args(argv)
433 if options.verbose: 431 if options.verbose:
434 Trace.verbose = True 432 Trace.verbose = True
435 if options.newlib: 433 if options.newlib:
436 toolchains.append('newlib') 434 toolchains.append('newlib')
437 if options.glibc: 435 if options.glibc:
438 toolchains.append('glibc') 436 toolchains.append('glibc')
439 if options.pnacl: 437 if options.pnacl:
440 toolchains.append('pnacl') 438 toolchains.append('pnacl')
441 if options.host: 439 if options.host:
442 toolchains.append(platform) 440 toolchains.append(platform)
443 441
444 if not args: 442 if not args:
445 ErrorExit('Please specify one or more projects to generate Makefiles for.') 443 ErrorExit('Please specify one or more projects to generate Makefiles for.')
446 444
447 # By default support newlib and glibc 445 # By default support newlib and glibc
448 if not toolchains: 446 if not toolchains:
449 toolchains = ['newlib', 'glibc', 'pnacl'] 447 toolchains = ['newlib', 'glibc', 'pnacl']
450 448
449 valid_configs = ['Debug', 'Release']
450 if options.config:
451 configs = []
452 for config in options.config:
453 if config in valid_configs:
454 configs.append(config)
455 else:
456 ErrorExit('Invalid config: %s' % config)
457 else:
458 configs = valid_configs
459
451 master_projects = {} 460 master_projects = {}
452 461
453 landing_page = LandingPage()
454 for i, filename in enumerate(args): 462 for i, filename in enumerate(args):
455 if i: 463 if i:
456 # Print two newlines between each dsc file we process 464 # Print two newlines between each dsc file we process
457 Trace('\n') 465 Trace('\n')
458 desc = LoadProject(filename, toolchains) 466 desc = LoadProject(filename, toolchains)
459 if not desc: 467 if not desc:
460 Trace('Skipping %s, not in [%s].' % (filename, ', '.join(toolchains))) 468 Trace('Skipping %s, not in [%s].' % (filename, ', '.join(toolchains)))
461 continue 469 continue
462 470
463 if desc.get('EXPERIMENTAL', False) and not options.experimental: 471 if desc.get('EXPERIMENTAL', False) and not options.experimental:
464 Trace('Skipping %s, experimental only.' % (filename,)) 472 Trace('Skipping %s, experimental only.' % (filename,))
465 continue 473 continue
466 474
467 srcroot = os.path.dirname(os.path.abspath(filename)) 475 srcroot = os.path.dirname(os.path.abspath(filename))
468 if not ProcessProject(srcroot, options.dstroot, desc, toolchains): 476 if not ProcessProject(srcroot, options.dstroot, desc, toolchains,
477 options.first_valid_toolchain):
469 ErrorExit('\n*** Failed to process project: %s ***' % filename) 478 ErrorExit('\n*** Failed to process project: %s ***' % filename)
470 479
471 # if this is an example update it's html file. 480 # if this is an example update it's html file.
472 if ShouldProcessHTML(desc): 481 if ShouldProcessHTML(desc):
473 ProcessHTML(srcroot, options.dstroot, desc, toolchains) 482 ProcessHTML(srcroot, options.dstroot, desc, toolchains, configs,
474 483 options.first_valid_toolchain)
475 # if this is an example, update landing page html file.
476 if desc['DEST'] == 'examples':
477 Trace('Adding desc: %s' % filename)
478 landing_page.AddDesc(desc)
479 484
480 # Create a list of projects for each DEST. This will be used to generate a 485 # Create a list of projects for each DEST. This will be used to generate a
481 # master makefile. 486 # master makefile.
482 master_projects.setdefault(desc['DEST'], []).append(desc) 487 master_projects.setdefault(desc['DEST'], []).append(desc)
483 488
484 # Generate the landing page text file. 489
485 index_html = os.path.join(options.dstroot, 'examples', 'index.html') 490 if master_projects.get('examples'):
486 with open(index_html, 'w') as fh: 491 landing_page = LandingPage()
487 fh.write(landing_page.GeneratePage()) 492 for desc in master_projects.get('examples'):
493 landing_page.AddDesc(desc)
494
495 # Generate the landing page text file.
496 index_html = os.path.join(options.dstroot, 'examples', 'index.html')
497 example_resources_dir = os.path.join(SDK_EXAMPLE_DIR, 'resources')
498 index_template = os.path.join(example_resources_dir, 'index.html.template')
499 with open(index_html, 'w') as fh:
500 fh.write(landing_page.GeneratePage(index_template))
501
502 # Copy additional files needed for the landing page.
503 extra_files = ['index.css', 'index.js', 'button_close.png',
504 'button_close_hover.png']
505 for filename in extra_files:
506 src_file = os.path.join(example_resources_dir, filename)
507 dst_file = os.path.join(options.dstroot, 'examples', filename)
508 buildbot_common.CopyFile(src_file, dst_file)
488 509
489 if options.master: 510 if options.master:
490 if use_gyp: 511 if use_gyp:
491 master_in = os.path.join(SDK_EXAMPLE_DIR, 'Makefile_gyp') 512 master_in = os.path.join(SDK_EXAMPLE_DIR, 'Makefile_gyp')
492 else: 513 else:
493 master_in = os.path.join(SDK_EXAMPLE_DIR, 'Makefile') 514 master_in = os.path.join(SDK_EXAMPLE_DIR, 'Makefile')
494 for dest, projects in master_projects.iteritems(): 515 for dest, projects in master_projects.iteritems():
495 master_out = os.path.join(options.dstroot, dest, 'Makefile') 516 master_out = os.path.join(options.dstroot, dest, 'Makefile')
496 GenerateMasterMakefile(master_in, master_out, projects) 517 GenerateMasterMakefile(master_in, master_out, projects)
497 518
498 return 0 519 return 0
499 520
500 521
501 if __name__ == '__main__': 522 if __name__ == '__main__':
502 sys.exit(main(sys.argv[1:])) 523 sys.exit(main(sys.argv[1:]))
503 524
OLDNEW
« no previous file with comments | « native_client_sdk/src/build_tools/generate_index.py ('k') | native_client_sdk/src/build_tools/template.mk » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698