Upstream version 9.38.198.0
[platform/framework/web/crosswalk.git] / src / native_client / pnacl / driver / pnacl-ld.py
1 #!/usr/bin/python
2 # Copyright (c) 2012 The Native Client Authors. All rights reserved.
3 # Use of this source code is governed by a BSD-style license that can be
4 # found in the LICENSE file.
5
6 from driver_tools import ArchMerge, DriverChain, GetArch, \
7     ParseArgs, ParseTriple, RunDriver, RunWithEnv, SetArch, \
8     SetExecutableMode, TempNameGen, UnrecognizedOption
9 from driver_env import env
10 from driver_log import Log
11 import filetype
12 import ldtools
13 import pathtools
14
15 EXTRA_ENV = {
16   'ALLOW_NATIVE': '0', # Allow LD args which will change the behavior
17                        # of native linking. This must be accompanied by
18                        # -arch to produce a .nexe.
19   'USE_IRT': '1',  # Use stable IRT interfaces.
20
21   'INPUTS'   : '',
22   'OUTPUT'   : '',
23
24   'STATIC'   : '0',
25   'PIC'      : '0',
26   'USE_STDLIB': '1',
27   'RELOCATABLE': '0',
28   'SONAME'   : '',
29
30   'STRIP_MODE' : 'none',
31
32   'STRIP_FLAGS'      : '${STRIP_FLAGS_%STRIP_MODE%}',
33   'STRIP_FLAGS_all'  : '-s',
34   'STRIP_FLAGS_debug': '-S',
35
36   'OPT_INLINE_THRESHOLD': '100',
37   'OPT_LEVEL': '',  # Default opt is 0, but we need to know if it's explicitly
38                     # requested or not, since we don't want to propagate
39                     # the value to TRANSLATE_FLAGS if it wasn't explicitly set.
40   'OPT_LTO_FLAGS': '-std-link-opts -disable-internalize',
41   'OPT_FLAGS': '${#OPT_LEVEL && !OPT_LEVEL == 0 ? ${OPT_LTO_FLAGS}} ${OPT_STRIP_%STRIP_MODE%} ' +
42                '-inline-threshold=${OPT_INLINE_THRESHOLD} ',
43   'OPT_STRIP_none': '',
44   'OPT_STRIP_all': '-disable-opt --strip',
45   'OPT_STRIP_debug': '-disable-opt --strip-debug',
46
47   'TRANSLATE_FLAGS': '${PIC ? -fPIC} ${!USE_STDLIB ? -nostdlib} ' +
48                      '${#SONAME ? -Wl,--soname=${SONAME}} ' +
49                      '${#OPT_LEVEL ? -O${OPT_LEVEL}} ' +
50                      '--allow-llvm-bitcode-input ' +
51                      '${CXX_EH_MODE==zerocost ? --pnacl-allow-zerocost-eh} ' +
52                      '${TRANSLATE_FLAGS_USER}',
53
54   # Extra pnacl-translate flags specified by the user using -Wt
55   'TRANSLATE_FLAGS_USER': '',
56
57   'GOLD_PLUGIN_ARGS': '-plugin=${GOLD_PLUGIN_SO} ' +
58                       '-plugin-opt=emit-llvm',
59
60   'LD_FLAGS'       : '-nostdlib ${@AddPrefix:-L:SEARCH_DIRS} ' +
61                      '${STATIC ? -static} ' +
62                      '${RELOCATABLE ? -relocatable} ' +
63                      '${#SONAME ? --soname=${SONAME}}',
64
65   # Flags for native linking.
66   # Only allowed if ALLOW_NATIVE is true.
67   'LD_FLAGS_NATIVE': '',
68
69   'SEARCH_DIRS'        : '${SEARCH_DIRS_USER} ${SEARCH_DIRS_BUILTIN}',
70   'SEARCH_DIRS_USER'   : '',
71
72   # Standard Library Directories
73   'SEARCH_DIRS_BUILTIN': '${USE_STDLIB ? ' +
74                          '  ${BASE_USR}/local/lib/ ' +
75                          '  ${BASE_USR}/lib/ ' +
76                          '  ${BASE_SDK}/lib/ ' +
77                          '  ${BASE_LIB}/ ' +
78                          '}',
79
80   'BCLD_OFORMAT'        : '${BCLD_OFORMAT_%ARCH%}',
81   'BCLD_OFORMAT_ARM'    : 'elf32-littlearm',
82   'BCLD_OFORMAT_X8632'  : 'elf32-i386-nacl',
83   'BCLD_OFORMAT_X8664'  : 'elf64-x86-64-nacl',
84   'BCLD_OFORMAT_MIPS32' : 'elf32-tradlittlemips',
85
86   'BCLD_ALLOW_UNRESOLVED'  :
87     # The following functions are implemented in the native support library.
88     # Before a .pexe is produced, they get rewritten to intrinsic calls.
89     # However, this rewriting happens after bitcode linking - so gold has
90     # to be told that these are allowed to remain unresolved.
91     '--allow-unresolved=memcpy '
92     '--allow-unresolved=memset '
93     '--allow-unresolved=memmove '
94     '--allow-unresolved=setjmp '
95     '--allow-unresolved=longjmp '
96     # These TLS layout functions are either defined by the ExpandTls
97     # pass or (for non-ABI-stable code only) by PNaCl's native support
98     # code.
99     '--allow-unresolved=__nacl_tp_tls_offset '
100     '--allow-unresolved=__nacl_tp_tdb_offset '
101     # __nacl_get_arch() is for non-ABI-stable code only.
102     '--allow-unresolved=__nacl_get_arch '
103     '${CXX_EH_MODE==sjlj ? '
104       # These symbols are defined by libsupc++ and the PNaClSjLjEH
105       # pass generates references to them.
106       '--undefined=__pnacl_eh_stack '
107       '--undefined=__pnacl_eh_resume '
108       # These symbols are defined by the PNaClSjLjEH pass and
109       # libsupc++ refers to them.
110       '--allow-unresolved=__pnacl_eh_type_table '
111       '--allow-unresolved=__pnacl_eh_action_table '
112       '--allow-unresolved=__pnacl_eh_filter_table} '
113     # For exception-handling enabled tests.
114     '${CXX_EH_MODE==zerocost ? '
115       '--allow-unresolved=_Unwind_Backtrace '
116       '--allow-unresolved=_Unwind_DeleteException '
117       '--allow-unresolved=_Unwind_GetCFA '
118       '--allow-unresolved=_Unwind_GetDataRelBase '
119       '--allow-unresolved=_Unwind_GetGR '
120       '--allow-unresolved=_Unwind_GetIP '
121       '--allow-unresolved=_Unwind_GetIPInfo '
122       '--allow-unresolved=_Unwind_GetLanguageSpecificData '
123       '--allow-unresolved=_Unwind_GetRegionStart '
124       '--allow-unresolved=_Unwind_GetTextRelBase '
125       '--allow-unresolved=_Unwind_PNaClSetResult0 '
126       '--allow-unresolved=_Unwind_PNaClSetResult1 '
127       '--allow-unresolved=_Unwind_RaiseException '
128       '--allow-unresolved=_Unwind_Resume '
129       '--allow-unresolved=_Unwind_Resume_or_Rethrow '
130       '--allow-unresolved=_Unwind_SetGR '
131       '--allow-unresolved=_Unwind_SetIP}',
132
133   'BCLD_FLAGS':
134     '--oformat ${BCLD_OFORMAT} ' +
135     '${!RELOCATABLE ? --undef-sym-check ${BCLD_ALLOW_UNRESOLVED}} ' +
136     '${GOLD_PLUGIN_ARGS} ${LD_FLAGS}',
137   'RUN_BCLD': ('${LD} ${BCLD_FLAGS} ${inputs} -o ${output}'),
138
139   'CXX_EH_MODE': 'none',
140   'ALLOW_NEXE_BUILD_ID': '0',
141   'DISABLE_ABI_CHECK': '0',
142   'LLVM_PASSES_TO_DISABLE': '',
143 }
144
145 def AddToBCLinkFlags(*args):
146   env.append('LD_FLAGS', *args)
147
148 def AddToNativeFlags(*args):
149   env.append('LD_FLAGS_NATIVE', *args)
150
151 def AddToBothFlags(*args):
152   env.append('LD_FLAGS', *args)
153   env.append('LD_FLAGS_NATIVE', *args)
154
155 def SetLibTarget(*args):
156   arch = ParseTriple(args[0])
157   if arch != 'le32':
158     env.set('BCLIB_ARCH', arch)
159
160 def IsPortable():
161   return env.getone('BCLIB_ARCH') == ''
162
163 LDPatterns = [
164   ( '--pnacl-allow-native', "env.set('ALLOW_NATIVE', '1')"),
165   ( '--noirt',              "env.set('USE_IRT', '0')"),
166   ( '--pnacl-exceptions=(none|sjlj|zerocost)', "env.set('CXX_EH_MODE', $0)"),
167   # TODO(mseaborn): Remove "--pnacl-allow-exceptions", which is
168   # superseded by "--pnacl-exceptions".
169   ( '--pnacl-allow-exceptions', "env.set('CXX_EH_MODE', 'zerocost')"),
170   ( '(--pnacl-allow-nexe-build-id)', "env.set('ALLOW_NEXE_BUILD_ID', '1')"),
171   ( '--pnacl-disable-abi-check', "env.set('DISABLE_ABI_CHECK', '1')"),
172   # "--pnacl-disable-pass" allows an ABI simplification pass to be
173   # disabled if it is causing problems.  These passes are generally
174   # required for ABI-stable pexes but can be omitted when the PNaCl
175   # toolchain is used for producing native nexes.
176   ( '--pnacl-disable-pass=(.+)', "env.append('LLVM_PASSES_TO_DISABLE', $0)"),
177   ( ('-target', '(.+)'), SetLibTarget),
178   ( ('--target=(.+)'), SetLibTarget),
179
180   ( '-o(.+)',          "env.set('OUTPUT', pathtools.normalize($0))"),
181   ( ('-o', '(.+)'),    "env.set('OUTPUT', pathtools.normalize($0))"),
182   ( ('--output', '(.+)'), "env.set('OUTPUT', pathtools.normalize($0))"),
183
184   ( '-static',         "env.set('STATIC', '1')"),
185   ( '-nostdlib',       "env.set('USE_STDLIB', '0')"),
186
187   ( '-r',              "env.set('RELOCATABLE', '1')"),
188   ( '-relocatable',    "env.set('RELOCATABLE', '1')"),
189   ( '-i',              "env.set('RELOCATABLE', '1')"),
190
191   ( ('-L', '(.+)'),
192     "env.append('SEARCH_DIRS_USER', pathtools.normalize($0))\n"),
193   ( '-L(.+)',
194     "env.append('SEARCH_DIRS_USER', pathtools.normalize($0))\n"),
195   ( ('--library-path', '(.+)'),
196     "env.append('SEARCH_DIRS_USER', pathtools.normalize($0))\n"),
197
198   # -rpath and -rpath-link are only relevant to dynamic linking.
199   # Ignore them for compatibility with build scripts that expect to be
200   # able to pass them.
201   ( ('(-rpath)','(.*)'), ""),
202   ( ('(-rpath)=(.*)'), ""),
203   ( ('(-rpath-link)','(.*)'), ""),
204   ( ('(-rpath-link)=(.*)'), ""),
205
206   # This overrides the builtin linker script.
207   ( ('(-T)', '(.*)'),    AddToNativeFlags),
208
209   # TODO(pdox): Allow setting an alternative _start symbol in bitcode
210   ( ('(-e)','(.*)'),     AddToBothFlags),
211
212   # TODO(pdox): Support GNU versioning.
213   ( '(--version-script=.*)', ""),
214
215   # Flags to pass to the native linker.
216   ( '-Wn,(.*)', "env.append('LD_FLAGS_NATIVE', *($0.split(',')))"),
217   ( ('(-Ttext-segment=.*)'), AddToNativeFlags),
218   ( ('(-Trodata-segment=.*)'), AddToNativeFlags),
219   ( ('(--section-start)', '(.+)'), AddToNativeFlags),
220   ( ('(--build-id)'), AddToNativeFlags),
221
222   # Flags to pass to translate
223   ( '-Wt,(.*)', "env.append('TRANSLATE_FLAGS_USER', *($0.split(',')))"),
224
225   # NOTE: -export-dynamic doesn't actually do anything to the bitcode link
226   # right now.  This is just in case we do want to record that in metadata
227   # eventually, and have that influence the native linker flags.
228   ( '(-export-dynamic)', AddToBCLinkFlags),
229
230   ( '-?-soname=(.*)',             "env.set('SONAME', $0)"),
231   ( ('-?-soname', '(.*)'),        "env.set('SONAME', $0)"),
232
233   ( '(-M)',                       AddToBCLinkFlags),
234   ( '(--print-map)',              AddToBCLinkFlags),
235   ( '(-t)',                       AddToBCLinkFlags),
236   ( '(--trace)',                  AddToBCLinkFlags),
237   ( ('(-y)','(.*)'),              AddToBCLinkFlags),
238   ( ('(-defsym)','(.*)'),         AddToBCLinkFlags),
239
240   ( '-melf_nacl',            "env.set('ARCH', 'X8632')"),
241   ( ('-m','elf_nacl'),       "env.set('ARCH', 'X8632')"),
242   ( '-melf64_nacl',          "env.set('ARCH', 'X8664')"),
243   ( ('-m','elf64_nacl'),     "env.set('ARCH', 'X8664')"),
244   ( '-marmelf_nacl',         "env.set('ARCH', 'ARM')"),
245   ( ('-m','armelf_nacl'),    "env.set('ARCH', 'ARM')"),
246   ( '-mmipselelf_nacl',      "env.set('ARCH', 'MIPS32')"),
247   ( ('-m','mipselelf_nacl'), "env.set('ARCH', 'MIPS32')"),
248
249   ( ('(-?-wrap)', '(.+)'), AddToBCLinkFlags),
250   ( ('(-?-wrap=.+)'),      AddToBCLinkFlags),
251
252   # NOTE: For scons tests, the code generation fPIC flag is used with pnacl-ld.
253   ( '-fPIC',               "env.set('PIC', '1')"),
254
255   # This controls LTO optimization.
256   # opt does not support -Os but internally it is identical to -O2
257   # opt also does not support -O4 but -O4 is how you ask clang for LTO, so we
258   # can support it as well
259   ( '-Os',                 "env.set('OPT_LEVEL', '2')"),
260   ( '-O([0-3])',           "env.set('OPT_LEVEL', $0)"),
261   ( '-O([0-9]+)',          "env.set('OPT_LEVEL', '3')"),
262
263   ( '(-translate-fast)',   "env.append('TRANSLATE_FLAGS', $0)"),
264
265   ( '-s',                  "env.set('STRIP_MODE', 'all')"),
266   ( '--strip-all',         "env.set('STRIP_MODE', 'all')"),
267   ( '-S',                  "env.set('STRIP_MODE', 'debug')"),
268   ( '--strip-debug',       "env.set('STRIP_MODE', 'debug')"),
269
270   ( '-g', ""),
271
272   # Inputs and options that need to be kept in order
273   ( '(-l.*)',              "env.append('INPUTS', $0)"),
274   ( ('(-l)','(.*)'),       "env.append('INPUTS', $0+$1)"),
275   ( ('--library', '(.*)'), "env.append('INPUTS', '-l'+$0)"),
276
277   ( '(--no-as-needed)',    "env.append('INPUTS', $0)"),
278   ( '(--as-needed)',       "env.append('INPUTS', $0)"),
279   ( '(--start-group)',     "env.append('INPUTS', $0)"),
280   ( '(--end-group)',       "env.append('INPUTS', $0)"),
281   ( '(-Bstatic)',          "env.append('INPUTS', $0)"),
282   ( '(-Bdynamic)',          "env.append('INPUTS', $0)"),
283   ( '(--(no-)?whole-archive)', "env.append('INPUTS', $0)"),
284   ( '(--undefined=.*)',    "env.append('INPUTS', $0)"),
285   ( ('(-u)','(.*)'),       "env.append('INPUTS', $0+$1)"),
286   ( '(-u.*)',              "env.append('INPUTS', $0)"),
287   ( '(-.*)',               UnrecognizedOption),
288   ( '(.*)',                "env.append('INPUTS', pathtools.normalize($0))"),
289 ]
290
291 def main(argv):
292   env.update(EXTRA_ENV)
293   ParseArgs(argv, LDPatterns)
294   # If the user passed -arch, then they want native output.
295   arch_flag_given = GetArch() is not None
296
297   # Both LD_FLAGS_NATIVE and TRANSLATE_FLAGS_USER affect
298   # the translation process. If they are non-empty,
299   # then --pnacl-allow-native must be given.
300   allow_native = env.getbool('ALLOW_NATIVE')
301   native_flags = env.get('LD_FLAGS_NATIVE') + env.get('TRANSLATE_FLAGS_USER')
302   if len(native_flags) > 0:
303     if not allow_native:
304       flagstr = ' '.join(native_flags)
305       Log.Fatal('"%s" affects translation. '
306                 'To allow, specify --pnacl-allow-native' % flagstr)
307
308   if env.getbool('ALLOW_NATIVE') and not arch_flag_given:
309       Log.Fatal("--pnacl-allow-native given, but translation "
310                 "is not happening (missing -arch?)")
311
312   # Overriding the lib target uses native-flavored bitcode libs rather than the
313   # portable bitcode libs. It is currently only tested/supported for
314   # building the IRT.
315   if not IsPortable():
316     env.set('BASE_USR', "${BASE_USR_ARCH}")
317     env.set('BASE_LIB', "${BASE_LIB_ARCH}")
318
319   if env.getbool('RELOCATABLE'):
320     env.set('STATIC', '0')
321
322   inputs = env.get('INPUTS')
323   output = env.getone('OUTPUT')
324
325   if output == '':
326     output = pathtools.normalize('a.out')
327
328   if not arch_flag_given:
329     # If -arch is not given, assume X86-32.
330     # This is because gold requires an arch (even for bitcode linking).
331     SetArch('X8632')
332   assert(GetArch() is not None)
333
334   inputs = FixPrivateLibs(inputs)
335
336   # Expand all parameters
337   # This resolves -lfoo into actual filenames,
338   # and expands linker scripts into command-line arguments.
339   inputs = ldtools.ExpandInputs(inputs,
340                                 env.get('SEARCH_DIRS'),
341                                 env.getbool('STATIC'),
342                                 # Once all glibc bitcode link is purely
343                                 # bitcode (e.g., even libc_nonshared.a)
344                                 # we may be able to restrict this more.
345                                 # This is also currently used by
346                                 # pnacl_generate_pexe=0 with glibc,
347                                 # for user libraries.
348                                 ldtools.LibraryTypes.ANY)
349
350   # Make sure the inputs have matching arch.
351   CheckInputsArch(inputs)
352
353   regular_inputs, native_objects = SplitLinkLine(inputs)
354
355   if env.getbool('RELOCATABLE'):
356     bitcode_type = 'po'
357     native_type = 'o'
358   else:
359     bitcode_type = 'pexe'
360     native_type = 'nexe'
361
362   if native_objects and not allow_native:
363     argstr = ' '.join(native_objects)
364     Log.Fatal("Native objects '%s' detected in the link. "
365               "To allow, specify --pnacl-allow-native" % argstr)
366
367   tng = TempNameGen([], output)
368
369   # Do the bitcode link.
370   if HasBitcodeInputs(inputs):
371     chain = DriverChain(inputs, output, tng)
372     chain.add(LinkBC, 'pre_opt.' + bitcode_type)
373
374     # Some ABI simplification passes assume the whole program is
375     # available (e.g. -expand-varargs, -nacl-expand-ctors and
376     # -nacl-expand-tls).  While we could try running a subset of
377     # simplification passes when linking native objects, we don't
378     # do this because it complicates testing.  For example,
379     # it requires '-expand-constant-expr' to be able to handle
380     # 'landingpad' instructions.
381     # However, if we aren't using biased bitcode, then at least -expand-byval
382     # must be run to work with the PPAPI shim calling convention.
383     # This assumes that PPAPI does not use var-args, so passes like
384     # -expand-varargs and other calling-convention-changing passes are
385     # not needed.
386     abi_simplify = (env.getbool('STATIC') and
387                     len(native_objects) == 0 and
388                     env.getone('CXX_EH_MODE') != 'zerocost' and
389                     not env.getbool('ALLOW_NEXE_BUILD_ID') and
390                     IsPortable())
391     still_need_expand_byval = IsPortable()
392
393     abi_simplify_opts = []
394     if env.getone('CXX_EH_MODE') == 'sjlj':
395       abi_simplify_opts += ['-enable-pnacl-sjlj-eh']
396
397     preopt_passes = []
398     if abi_simplify:
399       preopt_passes += ['-pnacl-abi-simplify-preopt'] + abi_simplify_opts
400     elif env.getone('CXX_EH_MODE') != 'zerocost':
401       # '-lowerinvoke' prevents use of C++ exception handling, which
402       # is not yet supported in the PNaCl ABI.  '-simplifycfg' removes
403       # landingpad blocks made unreachable by '-lowerinvoke'.
404       #
405       # We run this in order to remove 'resume' instructions,
406       # otherwise these are translated to calls to _Unwind_Resume(),
407       # which will not be available at native link time.
408       preopt_passes += ['-lowerinvoke', '-simplifycfg']
409     if len(preopt_passes) != 0:
410       chain.add(DoLLVMPasses(preopt_passes), 'simplify_preopt.' + bitcode_type)
411
412     if env.getone('OPT_LEVEL') != '' and env.getone('OPT_LEVEL') != '0':
413       chain.add(DoLTO, 'opt.' + bitcode_type)
414     elif env.getone('STRIP_MODE') != 'none':
415       chain.add(DoStrip, 'stripped.' + bitcode_type)
416
417     postopt_passes = []
418     if abi_simplify:
419       postopt_passes = ['-pnacl-abi-simplify-postopt'] + abi_simplify_opts
420       if not env.getbool('DISABLE_ABI_CHECK'):
421         postopt_passes += [
422             '-verify-pnaclabi-module',
423             '-verify-pnaclabi-functions',
424             # A flag for the above -verify-pnaclabi-* passes.
425             '-pnaclabi-allow-debug-metadata']
426     elif still_need_expand_byval:
427       # We may still need -expand-byval to match the PPAPI shim
428       # calling convention.
429       postopt_passes = ['-expand-byval']
430     if len(postopt_passes) != 0:
431       chain.add(DoLLVMPasses(postopt_passes),
432                 'simplify_postopt.' + bitcode_type)
433   else:
434     chain = DriverChain('', output, tng)
435
436   # If -arch is also specified, invoke pnacl-translate afterwards.
437   if arch_flag_given:
438     env.set('NATIVE_OBJECTS', *native_objects)
439     chain.add(DoTranslate, native_type)
440
441   chain.run()
442
443   if bitcode_type == 'pexe' and not arch_flag_given:
444     # Mark .pexe files as executable.
445     # Some versions of 'configure' expect this.
446     SetExecutableMode(output)
447   return 0
448
449 def FixPrivateLibs(user_libs):
450   """If not using the IRT or if private libraries are used:
451     - Place private libraries that can coexist before their public
452       equivalent (keep both);
453     - Replace public libraries that can't coexist with their private
454       equivalent.
455
456   This occurs before path resolution (important because public/private
457   libraries aren't always colocated) and assumes that -l:libfoo.a syntax
458   isn't used by the driver for relevant libraries.
459   """
460   special_libs = {
461       # Public library name: (private library name, can coexist?)
462       '-lnacl': ('-lnacl_sys_private', True),
463       '-lpthread': ('-lpthread_private', False),
464       }
465   private_libs = [v[0] for v in special_libs.values()]
466   public_libs = special_libs.keys()
467   private_lib_for = lambda user_lib: special_libs[user_lib][0]
468   can_coexist = lambda user_lib: special_libs[user_lib][1]
469
470   no_irt = not env.getbool('USE_IRT')
471   uses_private_libs = set(user_libs) & set(private_libs)
472
473   if not (no_irt or uses_private_libs):
474     return user_libs
475
476   result_libs = []
477   for user_lib in user_libs:
478     if user_lib in public_libs:
479       result_libs.append(private_lib_for(user_lib))
480       if can_coexist(user_lib):
481         result_libs.append(user_lib)
482     else:
483       result_libs.append(user_lib)
484   return result_libs
485
486 def SplitLinkLine(inputs):
487   """ Split the input list into bitcode and native objects (.o, .a)
488   """
489   normal = []
490   native = []
491   # Group flags need special handling because they need to go into the right
492   # list based on the type of the inputs in the group. If the group has both
493   # native and bitcode files (which is unfortunately the case for
494   # irt_browser_lib) then the group flags need to go in both lists.
495   if '--start-group' in inputs:
496     start_group = inputs.index('--start-group')
497     # Start with the inputs before the first group
498     normal, native = SplitLinkLine(inputs[:start_group])
499     try:
500       end_group = inputs.index('--end-group')
501     except ValueError:
502       Log.Fatal("Found --start-group without matching --end-group")
503     # Add the contents of the group together with the --{start,end}-group flags
504     norm_group, native_group = SplitLinkLine(inputs[start_group + 1:end_group])
505     if len(norm_group) > 0:
506       normal.extend(['--start-group'] + norm_group + ['--end-group'])
507     if len(native_group) > 0:
508       native.extend(['--start-group'] + native_group + ['--end-group'])
509     # Add the inputs after the first group
510     norm_last, native_last = SplitLinkLine(inputs[end_group + 1:])
511     return normal + norm_last, native + native_last
512
513   # If no groups, split the inputs based on their type.
514   for f in inputs:
515     if ldtools.IsFlag(f):
516       normal.append(f)
517     elif filetype.IsNativeArchive(f) or filetype.IsNativeObject(f):
518       native.append(f)
519     else:
520       normal.append(f)
521   return (normal, native)
522
523 def HasBitcodeInputs(inputs):
524   for f in inputs:
525     if ldtools.IsFlag(f):
526       continue
527     elif filetype.IsLLVMBitcode(f) or filetype.IsBitcodeArchive(f):
528       return True
529   return False
530
531 def CheckInputsArch(inputs):
532   count = 0
533   for f in inputs:
534     if ldtools.IsFlag(f):
535       continue
536     elif filetype.IsLLVMBitcode(f) or filetype.IsBitcodeArchive(f):
537       pass
538     elif filetype.IsNative(f):
539       ArchMerge(f, True)
540     else:
541       Log.Fatal("%s: Unexpected type of file for linking (%s)",
542                 pathtools.touser(f), filetype.FileType(f))
543     count += 1
544
545   if count == 0:
546     Log.Fatal("no input files")
547
548 def DoLLVMPasses(pass_list):
549   def Func(infile, outfile):
550     filtered_list = [pass_option for pass_option in pass_list
551                      if pass_option not in env.get('LLVM_PASSES_TO_DISABLE')]
552     RunDriver('pnacl-opt', filtered_list + [infile, '-o', outfile])
553   return Func
554
555 def DoLTO(infile, outfile):
556   opt_flags = env.get('OPT_FLAGS')
557   RunDriver('pnacl-opt', opt_flags + [ infile, '-o', outfile ])
558
559 def DoStrip(infile, outfile):
560   strip_flags = env.get('STRIP_FLAGS')
561   RunDriver('pnacl-strip', strip_flags + [ infile, '-o', outfile ])
562
563 def DoTranslate(infile, outfile):
564   args = env.get('TRANSLATE_FLAGS')
565   args += ['-Wl,'+s for s in env.get('LD_FLAGS_NATIVE')]
566   if infile:
567     args += [infile]
568   args += ['-Wl,'+s if ldtools.IsFlag(s) else s
569            for s in env.get('NATIVE_OBJECTS')]
570   args += ['-o', outfile]
571   RunDriver('pnacl-translate', args)
572
573 def LinkBC(inputs, output):
574   '''Input: a bunch of bc/o/lib input files
575      Output: a combined & optimized bitcode file
576   '''
577   # Produce combined bitcode file
578   RunWithEnv('${RUN_BCLD}',
579              inputs=inputs,
580              output=output)
581
582 def get_help(unused_argv):
583   return """Usage: pnacl-ld [options] <input files> -o <output>
584
585 Bitcode linker for PNaCl.  Similar to the binutils "ld" tool,
586 but links bitcode instead of native code.  Supports many of the
587 "ld" flags. Below are a subset of them.
588
589 OPTIONS:
590
591   -o <file>                   Set output file name
592   -l LIBNAME                  Search for library LIBNAME
593   -L DIRECTORY, --library-path DIRECTORY
594                               Add DIRECTORY to library search path
595
596   -r, -relocatable            Generate relocatable output
597
598   -O<opt-level>               Optimize output file
599   -M, --print-map             Print map file on standard output
600   --whole-archive             Include all objects from following archives
601   --no-whole-archive          Turn off --whole-archive
602   -s, --strip-all             Strip all symbols
603   -S, --strip-debug           Strip debugging symbols
604   -u SYM, --undefined=SYM     Start with undefined reference to SYM
605
606   -help | -h                  Output this help.
607 """