xref: /netbsd-src/external/gpl3/binutils/dist/ld/emultempl/armelf.em (revision 60ab2ca5c0570c0013b39de285ddaa91fe27d029)
1# This shell script emits a C file. -*- C -*-
2#   Copyright 1991, 1993, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003,
3#   2004, 2005, 2007, 2008
4#   Free Software Foundation, Inc.
5#
6# This file is part of the GNU Binutils.
7#
8# This program is free software; you can redistribute it and/or modify
9# it under the terms of the GNU General Public License as published by
10# the Free Software Foundation; either version 3 of the License, or
11# (at your option) any later version.
12#
13# This program is distributed in the hope that it will be useful,
14# but WITHOUT ANY WARRANTY; without even the implied warranty of
15# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16# GNU General Public License for more details.
17#
18# You should have received a copy of the GNU General Public License
19# along with this program; if not, write to the Free Software
20# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
21# MA 02110-1301, USA.
22#
23
24# This file is sourced from elf32.em, and defines extra arm-elf
25# specific routines.
26#
27test -z "$TARGET2_TYPE" && TARGET2_TYPE="rel"
28fragment <<EOF
29
30#include "ldctor.h"
31#include "elf/arm.h"
32
33static char *thumb_entry_symbol = NULL;
34static bfd *bfd_for_interwork;
35static int byteswap_code = 0;
36static int target1_is_rel = 0${TARGET1_IS_REL};
37static char *target2_type = "${TARGET2_TYPE}";
38static int fix_v4bx = 0;
39static int use_blx = 0;
40static bfd_arm_vfp11_fix vfp11_denorm_fix = BFD_ARM_VFP11_FIX_DEFAULT;
41static int no_enum_size_warning = 0;
42static int no_wchar_size_warning = 0;
43static int pic_veneer = 0;
44
45static void
46gld${EMULATION_NAME}_before_parse (void)
47{
48#ifndef TARGET_			/* I.e., if not generic.  */
49  ldfile_set_output_arch ("`echo ${ARCH}`", bfd_arch_unknown);
50#endif /* not TARGET_ */
51  config.dynamic_link = ${DYNAMIC_LINK-TRUE};
52  config.has_shared = `if test -n "$GENERATE_SHLIB_SCRIPT" ; then echo TRUE ; else echo FALSE ; fi`;
53}
54
55static void
56arm_elf_after_open (void)
57{
58  if (strstr (bfd_get_target (link_info.output_bfd), "arm") == NULL)
59    {
60      /* The arm backend needs special fields in the output hash structure.
61	 These will only be created if the output format is an arm format,
62	 hence we do not support linking and changing output formats at the
63	 same time.  Use a link followed by objcopy to change output formats.  */
64      einfo ("%F%X%P: error: cannot change output format whilst linking ARM binaries\n");
65      return;
66    }
67
68  {
69    LANG_FOR_EACH_INPUT_STATEMENT (is)
70      {
71	bfd_elf32_arm_add_glue_sections_to_bfd (is->the_bfd, & link_info);
72      }
73  }
74
75  /* Call the standard elf routine.  */
76  gld${EMULATION_NAME}_after_open ();
77}
78
79static void
80arm_elf_set_bfd_for_interworking (lang_statement_union_type *statement)
81{
82  if (statement->header.type == lang_input_section_enum)
83    {
84      asection *i = statement->input_section.section;
85
86      if (!((lang_input_statement_type *) i->owner->usrdata)->just_syms_flag
87	  && (i->flags & SEC_EXCLUDE) == 0)
88	{
89	  asection *output_section = i->output_section;
90
91	  ASSERT (output_section->owner == link_info.output_bfd);
92
93	  /* Don't attach the interworking stubs to a dynamic object, to
94	     an empty section, etc.  */
95	  if ((output_section->flags & SEC_HAS_CONTENTS) != 0
96	      && (i->flags & SEC_NEVER_LOAD) == 0
97	      && ! (i->owner->flags & DYNAMIC))
98	    bfd_for_interwork = i->owner;
99	}
100    }
101}
102
103static void
104arm_elf_before_allocation (void)
105{
106  if (link_info.input_bfds != NULL)
107    {
108      /* The interworking bfd must be the last one in the link.  */
109      bfd_for_interwork = NULL;
110
111      lang_for_each_statement (arm_elf_set_bfd_for_interworking);
112
113      /* If bfd_for_interwork is NULL, then there are no loadable sections
114	 with real contents to be linked, so we are not going to have to
115	 create any interworking stubs, so it is OK not to call
116	 bfd_elf32_arm_get_bfd_for_interworking.  */
117      if (bfd_for_interwork != NULL)
118	bfd_elf32_arm_get_bfd_for_interworking (bfd_for_interwork, &link_info);
119    }
120
121  bfd_elf32_arm_set_byteswap_code (&link_info, byteswap_code);
122
123  /* Choose type of VFP11 erratum fix, or warn if specified fix is unnecessary
124     due to architecture version.  */
125  bfd_elf32_arm_set_vfp11_fix (link_info.output_bfd, &link_info);
126
127  /* We should be able to set the size of the interworking stub section.  We
128     can't do it until later if we have dynamic sections, though.  */
129  if (! elf_hash_table (&link_info)->dynamic_sections_created)
130    {
131      /* Here we rummage through the found bfds to collect glue information.  */
132      LANG_FOR_EACH_INPUT_STATEMENT (is)
133	{
134          /* Initialise mapping tables for code/data.  */
135          bfd_elf32_arm_init_maps (is->the_bfd);
136
137	  if (!bfd_elf32_arm_process_before_allocation (is->the_bfd,
138							&link_info)
139	      || !bfd_elf32_arm_vfp11_erratum_scan (is->the_bfd, &link_info))
140	    /* xgettext:c-format */
141	    einfo (_("Errors encountered processing file %s"), is->filename);
142	}
143    }
144
145  /* Call the standard elf routine.  */
146  gld${EMULATION_NAME}_before_allocation ();
147
148  /* We have seen it all. Allocate it, and carry on.  */
149  bfd_elf32_arm_allocate_interworking_sections (& link_info);
150}
151
152static void
153arm_elf_after_allocation (void)
154{
155  /* Call the standard elf routine.  */
156  after_allocation_default ();
157
158  {
159    LANG_FOR_EACH_INPUT_STATEMENT (is)
160      {
161        /* Figure out where VFP11 erratum veneers (and the labels returning
162           from same) have been placed.  */
163        bfd_elf32_arm_vfp11_fix_veneer_locations (is->the_bfd, &link_info);
164      }
165  }
166}
167
168/* Fake input file for stubs.  */
169static lang_input_statement_type *stub_file;
170
171/* Whether we need to call gldarm_layout_sections_again.  */
172static int need_laying_out = 0;
173
174/* Maximum size of a group of input sections that can be handled by
175   one stub section.  A value of +/-1 indicates the bfd back-end
176   should use a suitable default size.  */
177static bfd_signed_vma group_size = 1;
178
179struct hook_stub_info
180{
181  lang_statement_list_type add;
182  asection *input_section;
183};
184
185/* Traverse the linker tree to find the spot where the stub goes.  */
186
187static bfd_boolean
188hook_in_stub (struct hook_stub_info *info, lang_statement_union_type **lp)
189{
190  lang_statement_union_type *l;
191  bfd_boolean ret;
192
193  for (; (l = *lp) != NULL; lp = &l->header.next)
194    {
195      switch (l->header.type)
196	{
197	case lang_constructors_statement_enum:
198	  ret = hook_in_stub (info, &constructor_list.head);
199	  if (ret)
200	    return ret;
201	  break;
202
203	case lang_output_section_statement_enum:
204	  ret = hook_in_stub (info,
205			      &l->output_section_statement.children.head);
206	  if (ret)
207	    return ret;
208	  break;
209
210	case lang_wild_statement_enum:
211	  ret = hook_in_stub (info, &l->wild_statement.children.head);
212	  if (ret)
213	    return ret;
214	  break;
215
216	case lang_group_statement_enum:
217	  ret = hook_in_stub (info, &l->group_statement.children.head);
218	  if (ret)
219	    return ret;
220	  break;
221
222	case lang_input_section_enum:
223	  if (l->input_section.section == info->input_section)
224	    {
225	      /* We've found our section.  Insert the stub immediately
226		 before its associated input section.  */
227	      *lp = info->add.head;
228	      *(info->add.tail) = l;
229	      return TRUE;
230	    }
231	  break;
232
233	case lang_data_statement_enum:
234	case lang_reloc_statement_enum:
235	case lang_object_symbols_statement_enum:
236	case lang_output_statement_enum:
237	case lang_target_statement_enum:
238	case lang_input_statement_enum:
239	case lang_assignment_statement_enum:
240	case lang_padding_statement_enum:
241	case lang_address_statement_enum:
242	case lang_fill_statement_enum:
243	  break;
244
245	default:
246	  FAIL ();
247	  break;
248	}
249    }
250  return FALSE;
251}
252
253
254/* Call-back for elf32_arm_size_stubs.  */
255
256/* Create a new stub section, and arrange for it to be linked
257   immediately before INPUT_SECTION.  */
258
259static asection *
260elf32_arm_add_stub_section (const char *stub_sec_name,
261			    asection *input_section)
262{
263  asection *stub_sec;
264  flagword flags;
265  asection *output_section;
266  const char *secname;
267  lang_output_section_statement_type *os;
268  struct hook_stub_info info;
269
270  flags = (SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE
271	   | SEC_HAS_CONTENTS | SEC_RELOC | SEC_IN_MEMORY | SEC_KEEP);
272  stub_sec = bfd_make_section_anyway_with_flags (stub_file->the_bfd,
273						 stub_sec_name, flags);
274  if (stub_sec == NULL)
275    goto err_ret;
276
277  bfd_set_section_alignment (stub_file->the_bfd, stub_sec, 3);
278
279  output_section = input_section->output_section;
280  secname = bfd_get_section_name (output_section->owner, output_section);
281  os = lang_output_section_find (secname);
282
283  info.input_section = input_section;
284  lang_list_init (&info.add);
285  lang_add_section (&info.add, stub_sec, os);
286
287  if (info.add.head == NULL)
288    goto err_ret;
289
290  if (hook_in_stub (&info, &os->children.head))
291    return stub_sec;
292
293 err_ret:
294  einfo ("%X%P: can not make stub section: %E\n");
295  return NULL;
296}
297
298/* Another call-back for elf_arm_size_stubs.  */
299
300static void
301gldarm_layout_sections_again (void)
302{
303  /* If we have changed sizes of the stub sections, then we need
304     to recalculate all the section offsets.  This may mean we need to
305     add even more stubs.  */
306  gld${EMULATION_NAME}_map_segments (TRUE);
307  need_laying_out = -1;
308}
309
310static void
311build_section_lists (lang_statement_union_type *statement)
312{
313  if (statement->header.type == lang_input_section_enum)
314    {
315      asection *i = statement->input_section.section;
316
317      if (!((lang_input_statement_type *) i->owner->usrdata)->just_syms_flag
318	  && (i->flags & SEC_EXCLUDE) == 0
319	  && i->output_section != NULL
320	  && i->output_section->owner == link_info.output_bfd)
321	elf32_arm_next_input_section (& link_info, i);
322    }
323}
324
325static void
326gld${EMULATION_NAME}_finish (void)
327{
328  struct bfd_link_hash_entry * h;
329
330  /* bfd_elf32_discard_info just plays with debugging sections,
331     ie. doesn't affect any code, so we can delay resizing the
332     sections.  It's likely we'll resize everything in the process of
333     adding stubs.  */
334  if (bfd_elf_discard_info (link_info.output_bfd, & link_info))
335    need_laying_out = 1;
336
337  /* If generating a relocatable output file, then we don't
338     have to examine the relocs.  */
339  if (stub_file != NULL && !link_info.relocatable)
340    {
341      int  ret = elf32_arm_setup_section_lists (link_info.output_bfd, & link_info);
342
343      if (ret != 0)
344	{
345	  if (ret < 0)
346	    {
347	      einfo ("%X%P: could not compute sections lists for stub generation: %E\n");
348	      return;
349	    }
350
351	  lang_for_each_statement (build_section_lists);
352
353	  /* Call into the BFD backend to do the real work.  */
354	  if (! elf32_arm_size_stubs (link_info.output_bfd,
355				      stub_file->the_bfd,
356				      & link_info,
357				      group_size,
358				      & elf32_arm_add_stub_section,
359				      & gldarm_layout_sections_again))
360	    {
361	      einfo ("%X%P: cannot size stub section: %E\n");
362	      return;
363	    }
364	}
365    }
366
367  if (need_laying_out != -1)
368    gld${EMULATION_NAME}_map_segments (need_laying_out);
369
370  if (! link_info.relocatable)
371    {
372      /* Now build the linker stubs.  */
373      if (stub_file->the_bfd->sections != NULL)
374	{
375	  if (! elf32_arm_build_stubs (& link_info))
376	    einfo ("%X%P: can not build stubs: %E\n");
377	}
378    }
379
380  finish_default ();
381
382  if (thumb_entry_symbol)
383    {
384      h = bfd_link_hash_lookup (link_info.hash, thumb_entry_symbol,
385				FALSE, FALSE, TRUE);
386    }
387  else
388    {
389      struct elf_link_hash_entry * eh;
390
391      if (!entry_symbol.name)
392	return;
393
394      h = bfd_link_hash_lookup (link_info.hash, entry_symbol.name,
395				FALSE, FALSE, TRUE);
396      eh = (struct elf_link_hash_entry *)h;
397      if (!h || ELF_ST_TYPE(eh->type) != STT_ARM_TFUNC)
398	return;
399    }
400
401
402  if (h != (struct bfd_link_hash_entry *) NULL
403      && (h->type == bfd_link_hash_defined
404	  || h->type == bfd_link_hash_defweak)
405      && h->u.def.section->output_section != NULL)
406    {
407      static char buffer[32];
408      bfd_vma val;
409
410      /* Special procesing is required for a Thumb entry symbol.  The
411	 bottom bit of its address must be set.  */
412      val = (h->u.def.value
413	     + bfd_get_section_vma (link_info.output_bfd,
414				    h->u.def.section->output_section)
415	     + h->u.def.section->output_offset);
416
417      val |= 1;
418
419      /* Now convert this value into a string and store it in entry_symbol
420	 where the lang_finish() function will pick it up.  */
421      buffer[0] = '0';
422      buffer[1] = 'x';
423
424      sprintf_vma (buffer + 2, val);
425
426      if (thumb_entry_symbol != NULL && entry_symbol.name != NULL
427	  && entry_from_cmdline)
428	einfo (_("%P: warning: '--thumb-entry %s' is overriding '-e %s'\n"),
429	       thumb_entry_symbol, entry_symbol.name);
430      entry_symbol.name = buffer;
431    }
432  else
433    einfo (_("%P: warning: cannot find thumb start symbol %s\n"),
434	   thumb_entry_symbol);
435}
436
437/* This is a convenient point to tell BFD about target specific flags.
438   After the output has been created, but before inputs are read.  */
439static void
440arm_elf_create_output_section_statements (void)
441{
442  bfd_elf32_arm_set_target_relocs (link_info.output_bfd, &link_info,
443				   target1_is_rel,
444				   target2_type, fix_v4bx, use_blx,
445				   vfp11_denorm_fix, no_enum_size_warning,
446				   no_wchar_size_warning,
447				   pic_veneer);
448
449  stub_file = lang_add_input_file ("linker stubs",
450 				   lang_input_file_is_fake_enum,
451 				   NULL);
452  stub_file->the_bfd = bfd_create ("linker stubs", link_info.output_bfd);
453  if (stub_file->the_bfd == NULL
454      || ! bfd_set_arch_mach (stub_file->the_bfd,
455 			      bfd_get_arch (link_info.output_bfd),
456 			      bfd_get_mach (link_info.output_bfd)))
457    {
458      einfo ("%X%P: can not create BFD %E\n");
459      return;
460    }
461
462  stub_file->the_bfd->flags |= BFD_LINKER_CREATED;
463  ldlang_add_file (stub_file);
464}
465
466/* Avoid processing the fake stub_file in vercheck, stat_needed and
467   check_needed routines.  */
468
469static void (*real_func) (lang_input_statement_type *);
470
471static void arm_for_each_input_file_wrapper (lang_input_statement_type *l)
472{
473  if (l != stub_file)
474    (*real_func) (l);
475}
476
477static void
478arm_lang_for_each_input_file (void (*func) (lang_input_statement_type *))
479{
480  real_func = func;
481  lang_for_each_input_file (&arm_for_each_input_file_wrapper);
482}
483
484#define lang_for_each_input_file arm_lang_for_each_input_file
485
486EOF
487
488# Define some shell vars to insert bits of code into the standard elf
489# parse_args and list_options functions.
490#
491PARSE_AND_LIST_PROLOGUE='
492#define OPTION_THUMB_ENTRY		301
493#define OPTION_BE8			302
494#define OPTION_TARGET1_REL		303
495#define OPTION_TARGET1_ABS		304
496#define OPTION_TARGET2			305
497#define OPTION_FIX_V4BX			306
498#define OPTION_USE_BLX			307
499#define OPTION_VFP11_DENORM_FIX		308
500#define OPTION_NO_ENUM_SIZE_WARNING	309
501#define OPTION_PIC_VENEER		310
502#define OPTION_FIX_V4BX_INTERWORKING	311
503#define OPTION_STUBGROUP_SIZE           312
504#define OPTION_NO_WCHAR_SIZE_WARNING	313
505'
506
507PARSE_AND_LIST_SHORTOPTS=p
508
509PARSE_AND_LIST_LONGOPTS='
510  { "no-pipeline-knowledge", no_argument, NULL, '\'p\''},
511  { "thumb-entry", required_argument, NULL, OPTION_THUMB_ENTRY},
512  { "be8", no_argument, NULL, OPTION_BE8},
513  { "target1-rel", no_argument, NULL, OPTION_TARGET1_REL},
514  { "target1-abs", no_argument, NULL, OPTION_TARGET1_ABS},
515  { "target2", required_argument, NULL, OPTION_TARGET2},
516  { "fix-v4bx", no_argument, NULL, OPTION_FIX_V4BX},
517  { "fix-v4bx-interworking", no_argument, NULL, OPTION_FIX_V4BX_INTERWORKING},
518  { "use-blx", no_argument, NULL, OPTION_USE_BLX},
519  { "vfp11-denorm-fix", required_argument, NULL, OPTION_VFP11_DENORM_FIX},
520  { "no-enum-size-warning", no_argument, NULL, OPTION_NO_ENUM_SIZE_WARNING},
521  { "pic-veneer", no_argument, NULL, OPTION_PIC_VENEER},
522  { "stub-group-size", required_argument, NULL, OPTION_STUBGROUP_SIZE },
523  { "no-wchar-size-warning", no_argument, NULL, OPTION_NO_WCHAR_SIZE_WARNING},
524'
525
526PARSE_AND_LIST_OPTIONS='
527  fprintf (file, _("  --thumb-entry=<sym>         Set the entry point to be Thumb symbol <sym>\n"));
528  fprintf (file, _("  --be8                       Oputput BE8 format image\n"));
529  fprintf (file, _("  --target1=rel               Interpret R_ARM_TARGET1 as R_ARM_REL32\n"));
530  fprintf (file, _("  --target1=abs               Interpret R_ARM_TARGET1 as R_ARM_ABS32\n"));
531  fprintf (file, _("  --target2=<type>            Specify definition of R_ARM_TARGET2\n"));
532  fprintf (file, _("  --fix-v4bx                  Rewrite BX rn as MOV pc, rn for ARMv4\n"));
533  fprintf (file, _("  --fix-v4bx-interworking     Rewrite BX rn branch to ARMv4 interworking veneer\n"));
534  fprintf (file, _("  --use-blx                   Enable use of BLX instructions\n"));
535  fprintf (file, _("  --vfp11-denorm-fix          Specify how to fix VFP11 denorm erratum\n"));
536  fprintf (file, _("  --no-enum-size-warning      Don'\''t warn about objects with incompatible"
537		   "                                enum sizes\n"));
538  fprintf (file, _("  --no-wchar-size-warning     Don'\''t warn about objects with incompatible"
539		   "                                wchar_t sizes\n"));
540  fprintf (file, _("  --pic-veneer                Always generate PIC interworking veneers\n"));
541  fprintf (file, _("\
542   --stub-group-size=N   Maximum size of a group of input sections that can be\n\
543                           handled by one stub section.  A negative value\n\
544                           locates all stubs before their branches (with a\n\
545                           group size of -N), while a positive value allows\n\
546                           two groups of input sections, one before, and one\n\
547                           after each stub section.  Values of +/-1 indicate\n\
548                           the linker should choose suitable defaults.\n"
549 		   ));
550'
551
552PARSE_AND_LIST_ARGS_CASES='
553    case '\'p\'':
554      /* Only here for backwards compatibility.  */
555      break;
556
557    case OPTION_THUMB_ENTRY:
558      thumb_entry_symbol = optarg;
559      break;
560
561    case OPTION_BE8:
562      byteswap_code = 1;
563      break;
564
565    case OPTION_TARGET1_REL:
566      target1_is_rel = 1;
567      break;
568
569    case OPTION_TARGET1_ABS:
570      target1_is_rel = 0;
571      break;
572
573    case OPTION_TARGET2:
574      target2_type = optarg;
575      break;
576
577    case OPTION_FIX_V4BX:
578      fix_v4bx = 1;
579      break;
580
581    case OPTION_FIX_V4BX_INTERWORKING:
582      fix_v4bx = 2;
583      break;
584
585    case OPTION_USE_BLX:
586      use_blx = 1;
587      break;
588
589    case OPTION_VFP11_DENORM_FIX:
590      if (strcmp (optarg, "none") == 0)
591        vfp11_denorm_fix = BFD_ARM_VFP11_FIX_NONE;
592      else if (strcmp (optarg, "scalar") == 0)
593        vfp11_denorm_fix = BFD_ARM_VFP11_FIX_SCALAR;
594      else if (strcmp (optarg, "vector") == 0)
595        vfp11_denorm_fix = BFD_ARM_VFP11_FIX_VECTOR;
596      else
597        einfo (_("Unrecognized VFP11 fix type '\''%s'\''.\n"), optarg);
598      break;
599
600    case OPTION_NO_ENUM_SIZE_WARNING:
601      no_enum_size_warning = 1;
602      break;
603
604    case OPTION_NO_WCHAR_SIZE_WARNING:
605      no_wchar_size_warning = 1;
606      break;
607
608    case OPTION_PIC_VENEER:
609      pic_veneer = 1;
610      break;
611
612    case OPTION_STUBGROUP_SIZE:
613      {
614	const char *end;
615
616        group_size = bfd_scan_vma (optarg, &end, 0);
617        if (*end)
618	  einfo (_("%P%F: invalid number `%s'\''\n"), optarg);
619      }
620      break;
621'
622
623# We have our own after_open and before_allocation functions, but they call
624# the standard routines, so give them a different name.
625LDEMUL_AFTER_OPEN=arm_elf_after_open
626LDEMUL_BEFORE_ALLOCATION=arm_elf_before_allocation
627LDEMUL_AFTER_ALLOCATION=arm_elf_after_allocation
628LDEMUL_CREATE_OUTPUT_SECTION_STATEMENTS=arm_elf_create_output_section_statements
629
630# Replace the elf before_parse function with our own.
631LDEMUL_BEFORE_PARSE=gld"${EMULATION_NAME}"_before_parse
632
633# Call the extra arm-elf function
634LDEMUL_FINISH=gld${EMULATION_NAME}_finish
635