OLD | NEW |
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 """Tool for automatically creating .nmf files from .nexe/.pexe/.bc executables. | 6 """Tool for automatically creating .nmf files from .nexe/.pexe/.bc executables. |
7 | 7 |
8 As well as creating the nmf file this tool can also find and stage | 8 As well as creating the nmf file this tool can also find and stage |
9 any shared libraries dependencies that the executables might have. | 9 any shared libraries dependencies that the executables might have. |
10 """ | 10 """ |
(...skipping 448 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
459 else: | 459 else: |
460 canonicalized.append([unquoted[0], unquoted[2], unquoted[4]]) | 460 canonicalized.append([unquoted[0], unquoted[2], unquoted[4]]) |
461 else: | 461 else: |
462 err.write('Bad key:arch:url tuple for --extra-files: ' + kv + '\n') | 462 err.write('Bad key:arch:url tuple for --extra-files: ' + kv + '\n') |
463 if seen_error: | 463 if seen_error: |
464 return None | 464 return None |
465 return canonicalized | 465 return canonicalized |
466 | 466 |
467 | 467 |
468 def GetSDKRoot(): | 468 def GetSDKRoot(): |
469 """Determine current NACL_SDK_ROOT, either via the environment variable | 469 """Returns the root directory of the NaCl SDK. |
470 itself, or by attempting to derive it from the location of this script. | |
471 """ | 470 """ |
472 sdk_root = os.environ.get('NACL_SDK_ROOT') | 471 # This script should be installed in NACL_SDK_ROOT/tools. Assert that |
473 if not sdk_root: | 472 # the 'toolchain' folder exists within this directory in case, for |
474 sdk_root = os.path.dirname(SCRIPT_DIR) | 473 # example, this script is moved to a different location. |
475 if not os.path.exists(os.path.join(sdk_root, 'toolchain')): | 474 # During the Chrome build this script is sometimes run outside of |
476 return None | 475 # of an SDK but in these cases it should always be run with --objdump= |
477 | 476 # and --no-default-libpath which avoids the need to call this function. |
| 477 sdk_root = os.path.dirname(SCRIPT_DIR) |
| 478 assert(os.path.exists(os.path.join(sdk_root, 'toolchain'))) |
478 return sdk_root | 479 return sdk_root |
479 | 480 |
480 | 481 |
481 def FindObjdumpExecutable(): | 482 def FindObjdumpExecutable(): |
482 """Derive path to objdump executable to use for determining shared | 483 """Derive path to objdump executable to use for determining shared |
483 object dependencies. | 484 object dependencies. |
484 """ | 485 """ |
485 sdk_root = GetSDKRoot() | |
486 if not sdk_root: | |
487 return None | |
488 | |
489 osname = getos.GetPlatform() | 486 osname = getos.GetPlatform() |
490 toolchain = os.path.join(sdk_root, 'toolchain', '%s_x86_glibc' % osname) | 487 toolchain = os.path.join(GetSDKRoot(), 'toolchain', '%s_x86_glibc' % osname) |
491 objdump = os.path.join(toolchain, 'bin', 'x86_64-nacl-objdump') | 488 objdump = os.path.join(toolchain, 'bin', 'x86_64-nacl-objdump') |
492 if osname == 'win': | 489 if osname == 'win': |
493 objdump += '.exe' | 490 objdump += '.exe' |
494 | 491 |
495 if not os.path.exists(objdump): | 492 if not os.path.exists(objdump): |
496 sys.stderr.write('WARNING: failed to find objdump in default ' | 493 sys.stderr.write('WARNING: failed to find objdump in default ' |
497 'location: %s' % objdump) | 494 'location: %s' % objdump) |
498 return None | 495 return None |
499 | 496 |
500 return objdump | 497 return objdump |
501 | 498 |
502 | 499 |
503 def GetDefaultLibPath(config): | 500 def GetDefaultLibPath(config): |
504 """Derive default library path to use when searching for shared | 501 """Derive default library path to use when searching for shared |
505 objects. This currently include the toolchain library folders | 502 objects. This currently include the toolchain library folders |
506 as well as the top level SDK lib folder and the naclports lib | 503 as well as the top level SDK lib folder and the naclports lib |
507 folder. We include both 32-bit and 64-bit library paths. | 504 folder. We include both 32-bit and 64-bit library paths. |
508 """ | 505 """ |
509 assert(config in ('Debug', 'Release')) | 506 assert(config in ('Debug', 'Release')) |
510 sdk_root = GetSDKRoot() | 507 sdk_root = GetSDKRoot() |
511 if not sdk_root: | |
512 # TOOD(sbc): output a warning here? We would also need to suppress | |
513 # the warning when run from the chromium build. | |
514 return [] | |
515 | 508 |
516 osname = getos.GetPlatform() | 509 osname = getos.GetPlatform() |
517 libpath = [ | 510 libpath = [ |
518 # Core toolchain libraries | 511 # Core toolchain libraries |
519 'toolchain/%s_x86_glibc/x86_64-nacl/lib' % osname, | 512 'toolchain/%s_x86_glibc/x86_64-nacl/lib' % osname, |
520 'toolchain/%s_x86_glibc/x86_64-nacl/lib32' % osname, | 513 'toolchain/%s_x86_glibc/x86_64-nacl/lib32' % osname, |
521 # naclports installed libraries | 514 # naclports installed libraries |
522 'toolchain/%s_x86_glibc/x86_64-nacl/usr/lib' % osname, | 515 'toolchain/%s_x86_glibc/x86_64-nacl/usr/lib' % osname, |
523 'toolchain/%s_x86_glibc/i686-nacl/usr/lib' % osname, | 516 'toolchain/%s_x86_glibc/i686-nacl/usr/lib' % osname, |
524 # SDK bundle libraries | 517 # SDK bundle libraries |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
573 metavar='DIRECTORY') | 566 metavar='DIRECTORY') |
574 parser.add_argument('--no-arch-prefix', action='store_true', | 567 parser.add_argument('--no-arch-prefix', action='store_true', |
575 help='Don\'t put shared libraries in the lib32/lib64 ' | 568 help='Don\'t put shared libraries in the lib32/lib64 ' |
576 'directories. Instead, they will be put in the same ' | 569 'directories. Instead, they will be put in the same ' |
577 'directory as the .nexe that matches its architecture.') | 570 'directory as the .nexe that matches its architecture.') |
578 parser.add_argument('-t', '--toolchain', help='Legacy option, do not use') | 571 parser.add_argument('-t', '--toolchain', help='Legacy option, do not use') |
579 parser.add_argument('-n', '--name', dest='name', | 572 parser.add_argument('-n', '--name', dest='name', |
580 help='Rename FOO as BAR', | 573 help='Rename FOO as BAR', |
581 action='append', default=[], metavar='FOO,BAR') | 574 action='append', default=[], metavar='FOO,BAR') |
582 parser.add_argument('-x', '--extra-files', | 575 parser.add_argument('-x', '--extra-files', |
583 help=('Add extra key:file tuple to the "files"' + | 576 help='Add extra key:file tuple to the "files"' |
584 ' section of the .nmf'), | 577 ' section of the .nmf', |
585 action='append', default=[], metavar='FILE') | 578 action='append', default=[], metavar='FILE') |
586 parser.add_argument('-O', '--pnacl-optlevel', | 579 parser.add_argument('-O', '--pnacl-optlevel', |
587 help='Set the optimization level to N in PNaCl manifests', | 580 help='Set the optimization level to N in PNaCl manifests', |
588 metavar='N') | 581 metavar='N') |
589 parser.add_argument('--pnacl-debug-optlevel', | 582 parser.add_argument('--pnacl-debug-optlevel', |
590 help='Set the optimization level to N for debugging ' | 583 help='Set the optimization level to N for debugging ' |
591 'sections in PNaCl manifests', | 584 'sections in PNaCl manifests', |
592 metavar='N') | 585 metavar='N') |
593 parser.add_argument('-v', '--verbose', | 586 parser.add_argument('-v', '--verbose', |
594 help='Verbose output', action='store_true') | 587 help='Verbose output', action='store_true') |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
662 lib_path=options.lib_path, | 655 lib_path=options.lib_path, |
663 extra_files=canonicalized, | 656 extra_files=canonicalized, |
664 lib_prefix=options.lib_prefix, | 657 lib_prefix=options.lib_prefix, |
665 nexe_prefix=options.nexe_prefix, | 658 nexe_prefix=options.nexe_prefix, |
666 no_arch_prefix=options.no_arch_prefix, | 659 no_arch_prefix=options.no_arch_prefix, |
667 remap=remap, | 660 remap=remap, |
668 pnacl_optlevel=pnacl_optlevel, | 661 pnacl_optlevel=pnacl_optlevel, |
669 pnacl_debug_optlevel=pnacl_debug_optlevel, | 662 pnacl_debug_optlevel=pnacl_debug_optlevel, |
670 nmf_root=nmf_root) | 663 nmf_root=nmf_root) |
671 | 664 |
672 if not options.output: | 665 if options.output is None: |
673 sys.stdout.write(nmf.GetJson()) | 666 sys.stdout.write(nmf.GetJson()) |
674 else: | 667 else: |
675 with open(options.output, 'w') as output: | 668 with open(options.output, 'w') as output: |
676 output.write(nmf.GetJson()) | 669 output.write(nmf.GetJson()) |
677 | 670 |
678 if options.stage_dependencies and not nmf.pnacl: | 671 if options.stage_dependencies and not nmf.pnacl: |
679 Trace('Staging dependencies...') | 672 Trace('Staging dependencies...') |
680 nmf.StageDependencies(options.stage_dependencies) | 673 nmf.StageDependencies(options.stage_dependencies) |
681 | 674 |
682 return 0 | 675 return 0 |
683 | 676 |
684 | 677 |
685 if __name__ == '__main__': | 678 if __name__ == '__main__': |
686 try: | 679 try: |
687 rtn = main(sys.argv[1:]) | 680 rtn = main(sys.argv[1:]) |
688 except Error, e: | 681 except Error, e: |
689 sys.stderr.write('%s: %s\n' % (os.path.basename(__file__), e)) | 682 sys.stderr.write('%s: %s\n' % (os.path.basename(__file__), e)) |
690 rtn = 1 | 683 rtn = 1 |
691 except KeyboardInterrupt: | 684 except KeyboardInterrupt: |
692 sys.stderr.write('%s: interrupted\n' % os.path.basename(__file__)) | 685 sys.stderr.write('%s: interrupted\n' % os.path.basename(__file__)) |
693 rtn = 1 | 686 rtn = 1 |
694 sys.exit(rtn) | 687 sys.exit(rtn) |
OLD | NEW |