1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180
|
#!/usr/bin/python
# Copyright (c) 2012 The Native Client Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
from optparse import OptionParser, OptionValueError
import os
import shutil
import sys
"""Prep NaCl Toolchain
Does final assembly of the NaCl toolchain prior to building untrusted modules.
"""
SCRIPT_DIR = os.path.dirname(os.path.abspath(__file__))
NACL_DIR = os.path.dirname(SCRIPT_DIR)
# Mapping from TC/include relative path to original source
HEADER_MAP = {
'x86_newlib': {
'x86_64-nacl/include/pthread.h': 'src/untrusted/pthread/pthread.h',
'x86_64-nacl/include/semaphore.h': 'src/untrusted/pthread/semaphore.h',
'x86_64-nacl/include/nacl/dynamic_annotations.h':
'src/untrusted/valgrind/dynamic_annotations.h',
'x86_64-nacl/include/nacl/nacl_dyncode.h':
'src/untrusted/nacl/nacl_dyncode.h',
'x86_64-nacl/include/nacl/nacl_random.h':
'src/untrusted/nacl/nacl_random.h',
'x86_64-nacl/include/nacl/nacl_startup.h':
'src/untrusted/nacl/nacl_startup.h',
'x86_64-nacl/include/nacl/nacl_thread.h':
'src/untrusted/nacl/nacl_thread.h',
'x86_64-nacl/include/irt.h': 'src/untrusted/irt/irt.h',
'x86_64-nacl/lib32/crt1.o': 'src/untrusted/stubs/crt1.x',
'x86_64-nacl/lib/crt1.o': 'src/untrusted/stubs/crt1.x',
},
'x86_glibc': {
'x86_64-nacl/include/nacl/dynamic_annotations.h':
'src/untrusted/valgrind/dynamic_annotations.h',
'x86_64-nacl/include/nacl/nacl_dyncode.h':
'src/untrusted/nacl/nacl_dyncode.h',
'x86_64-nacl/include/nacl/nacl_random.h':
'src/untrusted/nacl/nacl_random.h',
'x86_64-nacl/include/nacl/nacl_startup.h':
'src/untrusted/nacl/nacl_startup.h',
'x86_64-nacl/include/nacl/nacl_thread.h':
'src/untrusted/nacl/nacl_thread.h',
'x86_64-nacl/include/irt.h': 'src/untrusted/irt/irt.h',
},
'arm_newlib': {
'arm-nacl/include/pthread.h': 'src/untrusted/pthread/pthread.h',
'arm-nacl/include/semaphore.h': 'src/untrusted/pthread/semaphore.h',
'arm-nacl/include/nacl/dynamic_annotations.h':
'src/untrusted/valgrind/dynamic_annotations.h',
'arm-nacl/include/nacl/nacl_dyncode.h':
'src/untrusted/nacl/nacl_dyncode.h',
'arm-nacl/include/nacl/nacl_random.h':
'src/untrusted/nacl/nacl_random.h',
'arm-nacl/include/nacl/nacl_startup.h':
'src/untrusted/nacl/nacl_startup.h',
'arm-nacl/include/nacl/nacl_thread.h':
'src/untrusted/nacl/nacl_thread.h',
'arm-nacl/include/irt.h': 'src/untrusted/irt/irt.h',
'arm-nacl/lib/crt1.o': 'src/untrusted/stubs/crt1.x',
},
'pnacl': {
'le32-nacl/include/pthread.h': 'src/untrusted/pthread/pthread.h',
'le32-nacl/include/semaphore.h': 'src/untrusted/pthread/semaphore.h',
'le32-nacl/include/nacl/dynamic_annotations.h':
'src/untrusted/valgrind/dynamic_annotations.h',
'le32-nacl/include/nacl/nacl_dyncode.h':
'src/untrusted/nacl/nacl_dyncode.h',
'le32-nacl/include/nacl/nacl_random.h':
'src/untrusted/nacl/nacl_random.h',
'le32-nacl/include/nacl/nacl_startup.h':
'src/untrusted/nacl/nacl_startup.h',
'le32-nacl/include/nacl/nacl_thread.h':
'src/untrusted/nacl/nacl_thread.h',
'le32-nacl/include/irt.h': 'src/untrusted/irt/irt.h',
}
}
def PosixPath(filepath):
if sys.platform == 'win32':
return filepath.replace('\\', '/')
return filepath
def RealToRelative(filepath, basepath):
"""Returns a relative path from an absolute basepath and filepath."""
path_parts = filepath.split('/')
base_parts = basepath.split('/')
while path_parts and base_parts and path_parts[0] == base_parts[0]:
path_parts = path_parts[1:]
base_parts = base_parts[1:]
rel_parts = ['..'] * len(base_parts) + path_parts
return '/'.join(rel_parts)
def MakeDir(outdir):
if outdir and not os.path.exists(outdir):
os.makedirs(outdir)
def GetInputs(tc_map, basepath):
out_set = set()
for filename in tc_map:
src = PosixPath(os.path.join(NACL_DIR, tc_map[filename]))
out_set.add(RealToRelative(src, basepath))
return '\n'.join(sorted(out_set)) + '\n'
def CopyFiles(tc_map, tc_dst):
for filename in tc_map:
src = PosixPath(os.path.join(NACL_DIR, tc_map[filename]))
dst = os.path.join(tc_dst, filename)
MakeDir(os.path.dirname(dst))
if not os.path.exists(src):
raise RuntimeError('File not found: ' + src)
shutil.copy(src, dst)
def DoMain(argv):
parser = OptionParser()
parser.add_option('-p', '--path', dest='path', default='',
help='Set include path.')
parser.add_option('-t', '--tool', dest='tool', default='',
help='Select toolset.')
parser.add_option('-i', '--inputs', dest='inputs', action='store_true',
help='Return dependency list.', default=False)
parser.add_option('-v', '--verbose', dest='verbose', action='store_true',
help='Enable versbose output.')
options, files = parser.parse_args(argv)
basepath = PosixPath(os.path.abspath(os.getcwd()))
if len(files):
raise OptionValueError('Not expecting arguments: ' + ' '.join(files))
if options.tool not in HEADER_MAP:
raise OptionValueError('Unknown tool name: ' + options.tool)
tc_map = HEADER_MAP[options.tool]
tc_dest = os.path.abspath(options.path)
if options.inputs:
return GetInputs(tc_map, basepath)
if not options.path or not os.path.exists(options.path):
raise RuntimeError('Must set path to a valid directory.')
if not options.tool in HEADER_MAP:
raise RuntimeError('Must specify the toolchain.')
if not options.inputs:
CopyFiles(tc_map, tc_dest)
fh = open(os.path.join(tc_dest, 'stamp.prep'), 'w')
fh.write('NACL SDK stamp for %s\n' % options.tool)
fh.close()
if options.verbose:
print 'Created stamp file.'
return 0
def main(argv):
result = DoMain(argv[1:])
if type(result) == int:
return result
sys.stdout.write(result)
return 0
if __name__ == '__main__':
sys.exit(main(sys.argv))
|