* configure: Regenerate.
[deliverable/binutils-gdb.git] / ld / emultempl / xtensaelf.em
1 # This shell script emits a C file. -*- C -*-
2 # Copyright 2003, 2004, 2005
3 # Free Software Foundation, Inc.
4 #
5 # This file is part of GLD, the Gnu Linker.
6 #
7 # This program is free software; you can redistribute it and/or modify
8 # it under the terms of the GNU General Public License as published by
9 # the Free Software Foundation; either version 2 of the License, or
10 # (at your option) any later version.
11 #
12 # This program is distributed in the hope that it will be useful,
13 # but WITHOUT ANY WARRANTY; without even the implied warranty of
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 # GNU General Public License for more details.
16 #
17 # You should have received a copy of the GNU General Public License
18 # along with this program; if not, write to the Free Software
19 # Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.
20 #
21
22 # This file is sourced from elf32.em, and defines extra xtensa-elf
23 # specific routines.
24 #
25 cat >>e${EMULATION_NAME}.c <<EOF
26
27 #include <xtensa-config.h>
28 #include "../bfd/elf-bfd.h"
29 #include "../bfd/libbfd.h"
30 #include "elf/xtensa.h"
31 #include "bfd.h"
32
33 static void xtensa_wild_group_interleave (lang_statement_union_type *);
34 static void xtensa_colocate_output_literals (lang_statement_union_type *);
35
36
37 /* Flag for the emulation-specific "--no-relax" option. */
38 static bfd_boolean disable_relaxation = FALSE;
39
40 /* This number is irrelevant until we turn on use_literal_pages */
41 static bfd_vma xtensa_page_power = 12; /* 4K pages. */
42
43 /* To force a page break between literals and text, change
44 xtensa_use_literal_pages to "TRUE". */
45 static bfd_boolean xtensa_use_literal_pages = FALSE;
46
47 #define EXTRA_VALIDATION 0
48
49
50 static char *
51 elf_xtensa_choose_target (int argc ATTRIBUTE_UNUSED,
52 char **argv ATTRIBUTE_UNUSED)
53 {
54 if (XCHAL_HAVE_BE)
55 return "${BIG_OUTPUT_FORMAT}";
56 else
57 return "${LITTLE_OUTPUT_FORMAT}";
58 }
59
60
61 static void
62 elf_xtensa_before_parse (void)
63 {
64 /* Just call the default hook.... Tensilica's version of this function
65 does some other work that isn't relevant here. */
66 gld${EMULATION_NAME}_before_parse ();
67 }
68
69
70 static void
71 remove_section (bfd *abfd, asection *os)
72 {
73 asection **spp;
74 for (spp = &abfd->sections; *spp; spp = &(*spp)->next)
75 if (*spp == os)
76 {
77 *spp = os->next;
78 os->owner->section_count--;
79 break;
80 }
81 }
82
83
84 static bfd_boolean
85 replace_insn_sec_with_prop_sec (bfd *abfd,
86 const char *insn_sec_name,
87 const char *prop_sec_name,
88 char **error_message)
89 {
90 asection *insn_sec;
91 asection *prop_sec;
92 bfd_byte *prop_contents = NULL;
93 bfd_byte *insn_contents = NULL;
94 unsigned entry_count;
95 unsigned entry;
96 Elf_Internal_Shdr *symtab_hdr;
97 Elf_Internal_Rela *internal_relocs = NULL;
98 unsigned reloc_count;
99
100 *error_message = "";
101 insn_sec = bfd_get_section_by_name (abfd, insn_sec_name);
102 if (insn_sec == NULL)
103 return TRUE;
104 entry_count = insn_sec->size / 8;
105
106 prop_sec = bfd_get_section_by_name (abfd, prop_sec_name);
107 if (prop_sec != NULL && insn_sec != NULL)
108 {
109 *error_message = _("file already has property tables");
110 return FALSE;
111 }
112
113 if (insn_sec->size != 0)
114 {
115 insn_contents = (bfd_byte *) bfd_malloc (insn_sec->size);
116 if (insn_contents == NULL)
117 {
118 *error_message = _("out of memory");
119 goto cleanup;
120 }
121 if (! bfd_get_section_contents (abfd, insn_sec, insn_contents,
122 (file_ptr) 0, insn_sec->size))
123 {
124 *error_message = _("failed to read section contents");
125 goto cleanup;
126 }
127 }
128
129 /* Create a Property table section and relocation section for it. */
130 prop_sec_name = strdup (prop_sec_name);
131 prop_sec = bfd_make_section (abfd, prop_sec_name);
132 if (prop_sec == NULL
133 || ! bfd_set_section_flags (abfd, prop_sec,
134 bfd_get_section_flags (abfd, insn_sec))
135 || ! bfd_set_section_alignment (abfd, prop_sec, 2))
136 {
137 *error_message = _("could not create new section");
138 goto cleanup;
139 }
140
141 if (! bfd_set_section_flags (abfd, prop_sec,
142 bfd_get_section_flags (abfd, insn_sec))
143 || ! bfd_set_section_alignment (abfd, prop_sec, 2))
144 {
145 *error_message = _("could not set new section properties");
146 goto cleanup;
147 }
148 prop_sec->size = entry_count * 12;
149 prop_contents = (bfd_byte *) bfd_zalloc (abfd, prop_sec->size);
150 elf_section_data (prop_sec)->this_hdr.contents = prop_contents;
151
152 /* The entry size and size must be set to allow the linker to compute
153 the number of relocations since it does not use reloc_count. */
154 elf_section_data (prop_sec)->rel_hdr.sh_entsize =
155 sizeof (Elf32_External_Rela);
156 elf_section_data (prop_sec)->rel_hdr.sh_size =
157 elf_section_data (insn_sec)->rel_hdr.sh_size;
158
159 if (prop_contents == NULL && prop_sec->size != 0)
160 {
161 *error_message = _("could not allocate section contents");
162 goto cleanup;
163 }
164
165 /* Read the relocations. */
166 reloc_count = insn_sec->reloc_count;
167 if (reloc_count != 0)
168 {
169 /* If there is already an internal_reloc, then save it so that the
170 read_relocs function freshly allocates a copy. */
171 Elf_Internal_Rela *saved_relocs = elf_section_data (insn_sec)->relocs;
172
173 elf_section_data (insn_sec)->relocs = NULL;
174 internal_relocs =
175 _bfd_elf_link_read_relocs (abfd, insn_sec, NULL, NULL, FALSE);
176 elf_section_data (insn_sec)->relocs = saved_relocs;
177
178 if (internal_relocs == NULL)
179 {
180 *error_message = _("out of memory");
181 goto cleanup;
182 }
183 }
184
185 /* Create a relocation section for the property section. */
186 if (internal_relocs != NULL)
187 {
188 elf_section_data (prop_sec)->relocs = internal_relocs;
189 prop_sec->reloc_count = reloc_count;
190 }
191
192 /* Now copy each insn table entry to the prop table entry with
193 appropriate flags. */
194 for (entry = 0; entry < entry_count; ++entry)
195 {
196 unsigned value;
197 unsigned flags = (XTENSA_PROP_INSN | XTENSA_PROP_INSN_NO_TRANSFORM
198 | XTENSA_PROP_INSN_NO_REORDER);
199 value = bfd_get_32 (abfd, insn_contents + entry * 8 + 0);
200 bfd_put_32 (abfd, value, prop_contents + entry * 12 + 0);
201 value = bfd_get_32 (abfd, insn_contents + entry * 8 + 4);
202 bfd_put_32 (abfd, value, prop_contents + entry * 12 + 4);
203 bfd_put_32 (abfd, flags, prop_contents + entry * 12 + 8);
204 }
205
206 /* Now copy all of the relocations. Change offsets for the
207 instruction table section to offsets in the property table
208 section. */
209 if (internal_relocs)
210 {
211 unsigned i;
212 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
213
214 for (i = 0; i < reloc_count; i++)
215 {
216 Elf_Internal_Rela *rela;
217 unsigned r_offset;
218
219 rela = &internal_relocs[i];
220
221 /* If this relocation is to the .xt.insn section,
222 change the section number and the offset. */
223 r_offset = rela->r_offset;
224 r_offset += 4 * (r_offset / 8);
225 rela->r_offset = r_offset;
226 }
227 }
228
229 remove_section (abfd, insn_sec);
230
231 if (insn_contents)
232 free (insn_contents);
233
234 return TRUE;
235
236 cleanup:
237 if (prop_sec && prop_sec->owner)
238 remove_section (abfd, prop_sec);
239 if (insn_contents)
240 free (insn_contents);
241 if (internal_relocs)
242 free (internal_relocs);
243
244 return FALSE;
245 }
246
247
248 #define PROP_SEC_BASE_NAME ".xt.prop"
249 #define INSN_SEC_BASE_NAME ".xt.insn"
250 #define LINKONCE_SEC_OLD_TEXT_BASE_NAME ".gnu.linkonce.x."
251
252
253 static void
254 replace_instruction_table_sections (bfd *abfd, asection *sec)
255 {
256 char *message = "";
257 const char *insn_sec_name = NULL;
258 char *prop_sec_name = NULL;
259 char *owned_prop_sec_name = NULL;
260 const char *sec_name;
261
262 sec_name = bfd_get_section_name (abfd, sec);
263 if (strcmp (sec_name, INSN_SEC_BASE_NAME) == 0)
264 {
265 insn_sec_name = INSN_SEC_BASE_NAME;
266 prop_sec_name = PROP_SEC_BASE_NAME;
267 }
268 else if (strncmp (sec_name, LINKONCE_SEC_OLD_TEXT_BASE_NAME,
269 strlen (LINKONCE_SEC_OLD_TEXT_BASE_NAME)) == 0)
270 {
271 insn_sec_name = sec_name;
272 owned_prop_sec_name = (char *) xmalloc (strlen (sec_name) + 20);
273 prop_sec_name = owned_prop_sec_name;
274 strcpy (prop_sec_name, ".gnu.linkonce.prop.t.");
275 strcat (prop_sec_name,
276 sec_name + strlen (LINKONCE_SEC_OLD_TEXT_BASE_NAME));
277 }
278 if (insn_sec_name != NULL)
279 {
280 if (! replace_insn_sec_with_prop_sec (abfd, insn_sec_name, prop_sec_name,
281 &message))
282 {
283 einfo (_("%P: warning: failed to convert %s table in %B (%s); subsequent disassembly may be incomplete\n"),
284 insn_sec_name, abfd, message);
285 }
286 }
287 if (owned_prop_sec_name)
288 free (owned_prop_sec_name);
289 }
290
291
292 /* This is called after all input sections have been opened to convert
293 instruction tables (.xt.insn, gnu.linkonce.x.*) tables into property
294 tables (.xt.prop) before any section placement. */
295
296 static void
297 elf_xtensa_after_open (void)
298 {
299 bfd *abfd;
300
301 /* First call the ELF version. */
302 gld${EMULATION_NAME}_after_open ();
303
304 /* Now search the input files looking for instruction table sections. */
305 for (abfd = link_info.input_bfds;
306 abfd != NULL;
307 abfd = abfd->link_next)
308 {
309 asection *sec = abfd->sections;
310 asection *next_sec;
311
312 /* Do not use bfd_map_over_sections here since we are removing
313 sections as we iterate. */
314 while (sec != NULL)
315 {
316 next_sec = sec->next;
317 replace_instruction_table_sections (abfd, sec);
318 sec = next_sec;
319 }
320 }
321 }
322
323
324 /* This is called after the sections have been attached to output
325 sections, but before any sizes or addresses have been set. */
326
327 static void
328 elf_xtensa_before_allocation (void)
329 {
330 bfd *in_bfd;
331 bfd_boolean is_big_endian = XCHAL_HAVE_BE;
332
333 /* Check that the output endianness matches the Xtensa
334 configuration. The BFD library always includes both big and
335 little endian target vectors for Xtensa, but it only supports the
336 detailed instruction encode/decode operations (such as are
337 required to process relocations) for the selected Xtensa
338 configuration. */
339
340 if (is_big_endian && output_bfd->xvec->byteorder == BFD_ENDIAN_LITTLE)
341 {
342 einfo (_("%F%P: little endian output does not match "
343 "Xtensa configuration\n"));
344 }
345 if (!is_big_endian && output_bfd->xvec->byteorder == BFD_ENDIAN_BIG)
346 {
347 einfo (_("%F%P: big endian output does not match "
348 "Xtensa configuration\n"));
349 }
350
351 /* Check that the endianness for each input file matches the output.
352 The merge_private_bfd_data hook has already reported any mismatches
353 as errors, but those errors are not fatal. At this point, we
354 cannot go any further if there are any mismatches. */
355
356 for (in_bfd = link_info.input_bfds;
357 in_bfd != NULL;
358 in_bfd = in_bfd->link_next)
359 {
360 if ((is_big_endian && in_bfd->xvec->byteorder == BFD_ENDIAN_LITTLE)
361 || (!is_big_endian && in_bfd->xvec->byteorder == BFD_ENDIAN_BIG))
362 einfo (_("%F%P: cross-endian linking not supported\n"));
363 }
364
365 /* Enable relaxation by default if the "--no-relax" option was not
366 specified. This is done here instead of in the before_parse hook
367 because there is a check in main() to prohibit use of --relax and
368 -r together and that combination should be allowed for Xtensa. */
369
370 if (!disable_relaxation)
371 command_line.relax = TRUE;
372
373 gld${EMULATION_NAME}_before_allocation ();
374
375 xtensa_wild_group_interleave (stat_ptr->head);
376 if (command_line.relax)
377 xtensa_colocate_output_literals (stat_ptr->head);
378
379 /* TBD: We need to force the page alignments to here and only do
380 them as needed for the entire output section. Finally, if this
381 is a relocatable link then we need to add alignment notes so
382 that the literals can be separated later. */
383 }
384
385
386 typedef struct wildcard_list section_name_list;
387
388 typedef struct reloc_deps_e_t reloc_deps_e;
389 typedef struct reloc_deps_section_t reloc_deps_section;
390 typedef struct reloc_deps_graph_t reloc_deps_graph;
391
392
393 struct reloc_deps_e_t
394 {
395 asection *src; /* Contains l32rs. */
396 asection *tgt; /* Contains literals. */
397 reloc_deps_e *next;
398 };
399
400 /* Place these in the userdata field. */
401 struct reloc_deps_section_t
402 {
403 reloc_deps_e *preds;
404 reloc_deps_e *succs;
405 bfd_boolean is_only_literal;
406 };
407
408
409 struct reloc_deps_graph_t
410 {
411 size_t count;
412 size_t size;
413 asection **sections;
414 };
415
416 static void xtensa_layout_wild
417 (const reloc_deps_graph *, lang_wild_statement_type *);
418
419 typedef void (*deps_callback_t) (asection *, /* src_sec */
420 bfd_vma, /* src_offset */
421 asection *, /* target_sec */
422 bfd_vma, /* target_offset */
423 void *); /* closure */
424
425 extern bfd_boolean xtensa_callback_required_dependence
426 (bfd *, asection *, struct bfd_link_info *, deps_callback_t, void *);
427 static void xtensa_ldlang_clear_addresses (lang_statement_union_type *);
428 static bfd_boolean ld_local_file_relocations_fit
429 (lang_statement_union_type *, const reloc_deps_graph *);
430 static bfd_vma ld_assign_relative_paged_dot
431 (bfd_vma, lang_statement_union_type *, const reloc_deps_graph *,
432 bfd_boolean);
433 static bfd_vma ld_xtensa_insert_page_offsets
434 (bfd_vma, lang_statement_union_type *, reloc_deps_graph *, bfd_boolean);
435 #if EXTRA_VALIDATION
436 static size_t ld_count_children (lang_statement_union_type *);
437 #endif
438
439 extern lang_statement_list_type constructor_list;
440
441 /* Begin verbatim code from ldlang.c:
442 the following are copied from ldlang.c because they are defined
443 there statically. */
444
445 static void
446 lang_for_each_statement_worker (void (*func) (lang_statement_union_type *),
447 lang_statement_union_type *s)
448 {
449 for (; s != (lang_statement_union_type *) NULL; s = s->header.next)
450 {
451 func (s);
452
453 switch (s->header.type)
454 {
455 case lang_constructors_statement_enum:
456 lang_for_each_statement_worker (func, constructor_list.head);
457 break;
458 case lang_output_section_statement_enum:
459 lang_for_each_statement_worker
460 (func,
461 s->output_section_statement.children.head);
462 break;
463 case lang_wild_statement_enum:
464 lang_for_each_statement_worker
465 (func,
466 s->wild_statement.children.head);
467 break;
468 case lang_group_statement_enum:
469 lang_for_each_statement_worker (func,
470 s->group_statement.children.head);
471 break;
472 case lang_data_statement_enum:
473 case lang_reloc_statement_enum:
474 case lang_object_symbols_statement_enum:
475 case lang_output_statement_enum:
476 case lang_target_statement_enum:
477 case lang_input_section_enum:
478 case lang_input_statement_enum:
479 case lang_assignment_statement_enum:
480 case lang_padding_statement_enum:
481 case lang_address_statement_enum:
482 case lang_fill_statement_enum:
483 break;
484 default:
485 FAIL ();
486 break;
487 }
488 }
489 }
490
491 /* End of verbatim code from ldlang.c. */
492
493
494 static reloc_deps_section *
495 xtensa_get_section_deps (const reloc_deps_graph *deps ATTRIBUTE_UNUSED,
496 asection *sec)
497 {
498 /* We have a separate function for this so that
499 we could in the future keep a completely independent
500 structure that maps a section to its dependence edges.
501 For now, we place these in the sec->userdata field. */
502 reloc_deps_section *sec_deps = sec->userdata;
503 return sec_deps;
504 }
505
506 static void
507 xtensa_set_section_deps (const reloc_deps_graph *deps ATTRIBUTE_UNUSED,
508 asection *sec,
509 reloc_deps_section *deps_section)
510 {
511 sec->userdata = deps_section;
512 }
513
514
515 /* This is used to keep a list of all of the sections participating in
516 the graph so we can clean them up quickly. */
517
518 static void
519 xtensa_append_section_deps (reloc_deps_graph *deps, asection *sec)
520 {
521 if (deps->size <= deps->count)
522 {
523 asection **new_sections;
524 size_t i;
525 size_t new_size;
526
527 new_size = deps->size * 2;
528 if (new_size == 0)
529 new_size = 20;
530
531 new_sections = xmalloc (sizeof (asection *) * new_size);
532 memset (new_sections, 0, sizeof (asection *) * new_size);
533 for (i = 0; i < deps->count; i++)
534 {
535 new_sections[i] = deps->sections[i];
536 }
537 if (deps->sections != NULL)
538 free (deps->sections);
539 deps->sections = new_sections;
540 deps->size = new_size;
541 }
542 deps->sections[deps->count] = sec;
543 deps->count++;
544 }
545
546
547 static void
548 free_reloc_deps_graph (reloc_deps_graph *deps)
549 {
550 size_t i;
551 for (i = 0; i < deps->count; i++)
552 {
553 asection *sec = deps->sections[i];
554 reloc_deps_section *sec_deps;
555 sec_deps = xtensa_get_section_deps (deps, sec);
556 if (sec_deps)
557 {
558 reloc_deps_e *next;
559 while (sec_deps->succs != NULL)
560 {
561 next = sec_deps->succs->next;
562 free (sec_deps->succs);
563 sec_deps->succs = next;
564 }
565
566 while (sec_deps->preds != NULL)
567 {
568 next = sec_deps->preds->next;
569 free (sec_deps->preds);
570 sec_deps->preds = next;
571 }
572 free (sec_deps);
573 }
574 xtensa_set_section_deps (deps, sec, NULL);
575 }
576 if (deps->sections)
577 free (deps->sections);
578
579 free (deps);
580 }
581
582
583 static bfd_boolean
584 section_is_source (const reloc_deps_graph *deps ATTRIBUTE_UNUSED,
585 lang_statement_union_type *s)
586 {
587 asection *sec;
588 const reloc_deps_section *sec_deps;
589
590 if (s->header.type != lang_input_section_enum)
591 return FALSE;
592 sec = s->input_section.section;
593
594 sec_deps = xtensa_get_section_deps (deps, sec);
595 return sec_deps && sec_deps->succs != NULL;
596 }
597
598
599 static bfd_boolean
600 section_is_target (const reloc_deps_graph *deps ATTRIBUTE_UNUSED,
601 lang_statement_union_type *s)
602 {
603 asection *sec;
604 const reloc_deps_section *sec_deps;
605
606 if (s->header.type != lang_input_section_enum)
607 return FALSE;
608 sec = s->input_section.section;
609
610 sec_deps = xtensa_get_section_deps (deps, sec);
611 return sec_deps && sec_deps->preds != NULL;
612 }
613
614
615 static bfd_boolean
616 section_is_source_or_target (const reloc_deps_graph *deps ATTRIBUTE_UNUSED,
617 lang_statement_union_type *s)
618 {
619 return (section_is_source (deps, s)
620 || section_is_target (deps, s));
621 }
622
623
624 typedef struct xtensa_ld_iter_stack_t xtensa_ld_iter_stack;
625 typedef struct xtensa_ld_iter_t xtensa_ld_iter;
626
627 struct xtensa_ld_iter_t
628 {
629 lang_statement_union_type *parent; /* Parent of the list. */
630 lang_statement_list_type *l; /* List that holds it. */
631 lang_statement_union_type **loc; /* Place in the list. */
632 };
633
634 struct xtensa_ld_iter_stack_t
635 {
636 xtensa_ld_iter iterloc; /* List that hold it. */
637
638 xtensa_ld_iter_stack *next; /* Next in the stack. */
639 xtensa_ld_iter_stack *prev; /* Back pointer for stack. */
640 };
641
642
643 static void
644 ld_xtensa_move_section_after (xtensa_ld_iter *to, xtensa_ld_iter *current)
645 {
646 lang_statement_union_type *to_next;
647 lang_statement_union_type *current_next;
648 lang_statement_union_type **e;
649
650 #if EXTRA_VALIDATION
651 size_t old_to_count, new_to_count;
652 size_t old_current_count, new_current_count;
653 #endif
654
655 if (to == current)
656 return;
657
658 #if EXTRA_VALIDATION
659 old_to_count = ld_count_children (to->parent);
660 old_current_count = ld_count_children (current->parent);
661 #endif
662
663 to_next = *(to->loc);
664 current_next = (*current->loc)->header.next;
665
666 *(to->loc) = *(current->loc);
667
668 *(current->loc) = current_next;
669 (*(to->loc))->header.next = to_next;
670
671 /* reset "to" list tail */
672 for (e = &to->l->head; *e != NULL; e = &(*e)->header.next)
673 ;
674 to->l->tail = e;
675
676 /* reset "current" list tail */
677 for (e = &current->l->head; *e != NULL; e = &(*e)->header.next)
678 ;
679 current->l->tail = e;
680
681 #if EXTRA_VALIDATION
682 new_to_count = ld_count_children (to->parent);
683 new_current_count = ld_count_children (current->parent);
684
685 ASSERT ((old_to_count + old_current_count)
686 == (new_to_count + new_current_count));
687 #endif
688 }
689
690
691 /* Can only be called with lang_statements that have lists. Returns
692 FALSE if the list is empty. */
693
694 static bfd_boolean
695 iter_stack_empty (xtensa_ld_iter_stack **stack_p)
696 {
697 return *stack_p == NULL;
698 }
699
700
701 static bfd_boolean
702 iter_stack_push (xtensa_ld_iter_stack **stack_p,
703 lang_statement_union_type *parent)
704 {
705 xtensa_ld_iter_stack *stack;
706 lang_statement_list_type *l = NULL;
707
708 switch (parent->header.type)
709 {
710 case lang_output_section_statement_enum:
711 l = &parent->output_section_statement.children;
712 break;
713 case lang_wild_statement_enum:
714 l = &parent->wild_statement.children;
715 break;
716 case lang_group_statement_enum:
717 l = &parent->group_statement.children;
718 break;
719 default:
720 ASSERT (0);
721 return FALSE;
722 }
723
724 /* Empty. do not push. */
725 if (l->tail == &l->head)
726 return FALSE;
727
728 stack = xmalloc (sizeof (xtensa_ld_iter_stack));
729 memset (stack, 0, sizeof (xtensa_ld_iter_stack));
730 stack->iterloc.parent = parent;
731 stack->iterloc.l = l;
732 stack->iterloc.loc = &l->head;
733
734 stack->next = *stack_p;
735 stack->prev = NULL;
736 if (*stack_p != NULL)
737 (*stack_p)->prev = stack;
738 *stack_p = stack;
739 return TRUE;
740 }
741
742
743 static void
744 iter_stack_pop (xtensa_ld_iter_stack **stack_p)
745 {
746 xtensa_ld_iter_stack *stack;
747
748 stack = *stack_p;
749
750 if (stack == NULL)
751 {
752 ASSERT (stack != NULL);
753 return;
754 }
755
756 if (stack->next != NULL)
757 stack->next->prev = NULL;
758
759 *stack_p = stack->next;
760 free (stack);
761 }
762
763
764 /* This MUST be called if, during iteration, the user changes the
765 underlying structure. It will check for a NULL current and advance
766 accordingly. */
767
768 static void
769 iter_stack_update (xtensa_ld_iter_stack **stack_p)
770 {
771 if (!iter_stack_empty (stack_p)
772 && (*(*stack_p)->iterloc.loc) == NULL)
773 {
774 iter_stack_pop (stack_p);
775
776 while (!iter_stack_empty (stack_p)
777 && ((*(*stack_p)->iterloc.loc)->header.next == NULL))
778 {
779 iter_stack_pop (stack_p);
780 }
781 if (!iter_stack_empty (stack_p))
782 (*stack_p)->iterloc.loc = &(*(*stack_p)->iterloc.loc)->header.next;
783 }
784 }
785
786
787 static void
788 iter_stack_next (xtensa_ld_iter_stack **stack_p)
789 {
790 xtensa_ld_iter_stack *stack;
791 lang_statement_union_type *current;
792 stack = *stack_p;
793
794 current = *stack->iterloc.loc;
795 /* If we are on the first element. */
796 if (current != NULL)
797 {
798 switch (current->header.type)
799 {
800 case lang_output_section_statement_enum:
801 case lang_wild_statement_enum:
802 case lang_group_statement_enum:
803 /* If the list if not empty, we are done. */
804 if (iter_stack_push (stack_p, *stack->iterloc.loc))
805 return;
806 /* Otherwise increment the pointer as normal. */
807 break;
808 default:
809 break;
810 }
811 }
812
813 while (!iter_stack_empty (stack_p)
814 && ((*(*stack_p)->iterloc.loc)->header.next == NULL))
815 {
816 iter_stack_pop (stack_p);
817 }
818 if (!iter_stack_empty (stack_p))
819 (*stack_p)->iterloc.loc = &(*(*stack_p)->iterloc.loc)->header.next;
820 }
821
822
823 static lang_statement_union_type *
824 iter_stack_current (xtensa_ld_iter_stack **stack_p)
825 {
826 return *((*stack_p)->iterloc.loc);
827 }
828
829
830 /* The iter stack is a preorder. */
831
832 static void
833 iter_stack_create (xtensa_ld_iter_stack **stack_p,
834 lang_statement_union_type *parent)
835 {
836 iter_stack_push (stack_p, parent);
837 }
838
839
840 static void
841 iter_stack_copy_current (xtensa_ld_iter_stack **stack_p, xtensa_ld_iter *front)
842 {
843 *front = (*stack_p)->iterloc;
844 }
845
846
847 static void
848 xtensa_colocate_literals (reloc_deps_graph *deps,
849 lang_statement_union_type *statement)
850 {
851 /* Keep a stack of pointers to control iteration through the contours. */
852 xtensa_ld_iter_stack *stack = NULL;
853 xtensa_ld_iter_stack **stack_p = &stack;
854
855 xtensa_ld_iter front; /* Location where new insertion should occur. */
856 xtensa_ld_iter *front_p = NULL;
857
858 xtensa_ld_iter current; /* Location we are checking. */
859 xtensa_ld_iter *current_p = NULL;
860 bfd_boolean in_literals = FALSE;
861
862 if (deps->count == 0)
863 return;
864
865 iter_stack_create (stack_p, statement);
866
867 while (!iter_stack_empty (stack_p))
868 {
869 bfd_boolean skip_increment = FALSE;
870 lang_statement_union_type *l = iter_stack_current (stack_p);
871
872 switch (l->header.type)
873 {
874 case lang_assignment_statement_enum:
875 /* Any assignment statement should block reordering across it. */
876 front_p = NULL;
877 in_literals = FALSE;
878 break;
879
880 case lang_input_section_enum:
881 if (front_p == NULL)
882 {
883 in_literals = (section_is_target (deps, l)
884 && !section_is_source (deps, l));
885 if (in_literals)
886 {
887 front_p = &front;
888 iter_stack_copy_current (stack_p, front_p);
889 }
890 }
891 else
892 {
893 bfd_boolean is_target;
894 current_p = &current;
895 iter_stack_copy_current (stack_p, current_p);
896 is_target = (section_is_target (deps, l)
897 && !section_is_source (deps, l));
898
899 if (in_literals)
900 {
901 iter_stack_copy_current (stack_p, front_p);
902 if (!is_target)
903 in_literals = FALSE;
904 }
905 else
906 {
907 if (is_target)
908 {
909 /* Try to insert in place. */
910 ld_xtensa_move_section_after (front_p, current_p);
911 ld_assign_relative_paged_dot (0x100000,
912 statement,
913 deps,
914 xtensa_use_literal_pages);
915
916 /* We use this code because it's already written. */
917 if (!ld_local_file_relocations_fit (statement, deps))
918 {
919 /* Move it back. */
920 ld_xtensa_move_section_after (current_p, front_p);
921 /* Reset the literal placement. */
922 iter_stack_copy_current (stack_p, front_p);
923 }
924 else
925 {
926 /* Move front pointer up by one. */
927 front_p->loc = &(*front_p->loc)->header.next;
928
929 /* Do not increment the current pointer. */
930 skip_increment = TRUE;
931 }
932 }
933 }
934 }
935 break;
936 default:
937 break;
938 }
939
940 if (!skip_increment)
941 iter_stack_next (stack_p);
942 else
943 /* Be careful to update the stack_p if it now is a null. */
944 iter_stack_update (stack_p);
945 }
946
947 lang_for_each_statement_worker (xtensa_ldlang_clear_addresses, statement);
948 }
949
950
951 static void
952 xtensa_move_dependencies_to_front (reloc_deps_graph *deps,
953 lang_wild_statement_type *w)
954 {
955 /* Keep a front pointer and a current pointer. */
956 lang_statement_union_type **front;
957 lang_statement_union_type **current;
958
959 /* Walk to the end of the targets. */
960 for (front = &w->children.head;
961 (*front != NULL) && section_is_source_or_target (deps, *front);
962 front = &(*front)->header.next)
963 ;
964
965 if (*front == NULL)
966 return;
967
968 current = &(*front)->header.next;
969 while (*current != NULL)
970 {
971 if (section_is_source_or_target (deps, *current))
972 {
973 /* Insert in place. */
974 xtensa_ld_iter front_iter;
975 xtensa_ld_iter current_iter;
976
977 front_iter.parent = (lang_statement_union_type *) w;
978 front_iter.l = &w->children;
979 front_iter.loc = front;
980
981 current_iter.parent = (lang_statement_union_type *) w;
982 current_iter.l = &w->children;
983 current_iter.loc = current;
984
985 ld_xtensa_move_section_after (&front_iter, &current_iter);
986 front = &(*front)->header.next;
987 }
988 else
989 {
990 current = &(*current)->header.next;
991 }
992 }
993 }
994
995
996 static bfd_boolean
997 deps_has_sec_edge (const reloc_deps_graph *deps, asection *src, asection *tgt)
998 {
999 const reloc_deps_section *sec_deps;
1000 const reloc_deps_e *sec_deps_e;
1001
1002 sec_deps = xtensa_get_section_deps (deps, src);
1003 if (sec_deps == NULL)
1004 return FALSE;
1005
1006 for (sec_deps_e = sec_deps->succs;
1007 sec_deps_e != NULL;
1008 sec_deps_e = sec_deps_e->next)
1009 {
1010 ASSERT (sec_deps_e->src == src);
1011 if (sec_deps_e->tgt == tgt)
1012 return TRUE;
1013 }
1014 return FALSE;
1015 }
1016
1017
1018 static bfd_boolean
1019 deps_has_edge (const reloc_deps_graph *deps,
1020 lang_statement_union_type *src,
1021 lang_statement_union_type *tgt)
1022 {
1023 if (!section_is_source (deps, src))
1024 return FALSE;
1025 if (!section_is_target (deps, tgt))
1026 return FALSE;
1027
1028 if (src->header.type != lang_input_section_enum)
1029 return FALSE;
1030 if (tgt->header.type != lang_input_section_enum)
1031 return FALSE;
1032
1033 return deps_has_sec_edge (deps, src->input_section.section,
1034 tgt->input_section.section);
1035 }
1036
1037
1038 static void
1039 add_deps_edge (reloc_deps_graph *deps, asection *src_sec, asection *tgt_sec)
1040 {
1041 reloc_deps_section *src_sec_deps;
1042 reloc_deps_section *tgt_sec_deps;
1043
1044 reloc_deps_e *src_edge;
1045 reloc_deps_e *tgt_edge;
1046
1047 if (deps_has_sec_edge (deps, src_sec, tgt_sec))
1048 return;
1049
1050 src_sec_deps = xtensa_get_section_deps (deps, src_sec);
1051 if (src_sec_deps == NULL)
1052 {
1053 /* Add a section. */
1054 src_sec_deps = xmalloc (sizeof (reloc_deps_section));
1055 memset (src_sec_deps, 0, sizeof (reloc_deps_section));
1056 src_sec_deps->is_only_literal = 0;
1057 src_sec_deps->preds = NULL;
1058 src_sec_deps->succs = NULL;
1059 xtensa_set_section_deps (deps, src_sec, src_sec_deps);
1060 xtensa_append_section_deps (deps, src_sec);
1061 }
1062
1063 tgt_sec_deps = xtensa_get_section_deps (deps, tgt_sec);
1064 if (tgt_sec_deps == NULL)
1065 {
1066 /* Add a section. */
1067 tgt_sec_deps = xmalloc (sizeof (reloc_deps_section));
1068 memset (tgt_sec_deps, 0, sizeof (reloc_deps_section));
1069 tgt_sec_deps->is_only_literal = 0;
1070 tgt_sec_deps->preds = NULL;
1071 tgt_sec_deps->succs = NULL;
1072 xtensa_set_section_deps (deps, tgt_sec, tgt_sec_deps);
1073 xtensa_append_section_deps (deps, tgt_sec);
1074 }
1075
1076 /* Add the edges. */
1077 src_edge = xmalloc (sizeof (reloc_deps_e));
1078 memset (src_edge, 0, sizeof (reloc_deps_e));
1079 src_edge->src = src_sec;
1080 src_edge->tgt = tgt_sec;
1081 src_edge->next = src_sec_deps->succs;
1082 src_sec_deps->succs = src_edge;
1083
1084 tgt_edge = xmalloc (sizeof (reloc_deps_e));
1085 memset (tgt_edge, 0, sizeof (reloc_deps_e));
1086 tgt_edge->src = src_sec;
1087 tgt_edge->tgt = tgt_sec;
1088 tgt_edge->next = tgt_sec_deps->preds;
1089 tgt_sec_deps->preds = tgt_edge;
1090 }
1091
1092
1093 static void
1094 build_deps_graph_callback (asection *src_sec,
1095 bfd_vma src_offset ATTRIBUTE_UNUSED,
1096 asection *target_sec,
1097 bfd_vma target_offset ATTRIBUTE_UNUSED,
1098 void *closure)
1099 {
1100 reloc_deps_graph *deps = closure;
1101
1102 /* If the target is defined. */
1103 if (target_sec != NULL)
1104 add_deps_edge (deps, src_sec, target_sec);
1105 }
1106
1107
1108 static reloc_deps_graph *
1109 ld_build_required_section_dependence (lang_statement_union_type *s)
1110 {
1111 reloc_deps_graph *deps;
1112 xtensa_ld_iter_stack *stack = NULL;
1113
1114 deps = xmalloc (sizeof (reloc_deps_graph));
1115 deps->sections = NULL;
1116 deps->count = 0;
1117 deps->size = 0;
1118
1119 for (iter_stack_create (&stack, s);
1120 !iter_stack_empty (&stack);
1121 iter_stack_next (&stack))
1122 {
1123 lang_statement_union_type *l = iter_stack_current (&stack);
1124
1125 if (l->header.type == lang_input_section_enum)
1126 {
1127 lang_input_section_type *input;
1128 input = &l->input_section;
1129 xtensa_callback_required_dependence (input->section->owner,
1130 input->section,
1131 &link_info,
1132 /* Use the same closure. */
1133 build_deps_graph_callback,
1134 deps);
1135 }
1136 }
1137 return deps;
1138 }
1139
1140
1141 #if EXTRA_VALIDATION
1142 static size_t
1143 ld_count_children (lang_statement_union_type *s)
1144 {
1145 size_t count = 0;
1146 xtensa_ld_iter_stack *stack = NULL;
1147 for (iter_stack_create (&stack, s);
1148 !iter_stack_empty (&stack);
1149 iter_stack_next (&stack))
1150 {
1151 lang_statement_union_type *l = iter_stack_current (&stack);
1152 ASSERT (l != NULL);
1153 count++;
1154 }
1155 return count;
1156 }
1157 #endif /* EXTRA_VALIDATION */
1158
1159
1160 static void
1161 xtensa_wild_group_interleave_callback (lang_statement_union_type *statement)
1162 {
1163 lang_wild_statement_type *w;
1164 reloc_deps_graph *deps;
1165 if (statement->header.type == lang_wild_statement_enum)
1166 {
1167 #if EXTRA_VALIDATION
1168 size_t old_child_count;
1169 size_t new_child_count;
1170 #endif
1171 bfd_boolean no_reorder;
1172
1173 w = &statement->wild_statement;
1174
1175 no_reorder = FALSE;
1176
1177 /* If it has 0 or 1 section bound, then do not reorder. */
1178 if (w->children.head == NULL
1179 || (w->children.head->header.type == lang_input_section_enum
1180 && w->children.head->header.next == NULL))
1181 no_reorder = TRUE;
1182
1183 if (w->filenames_sorted)
1184 no_reorder = TRUE;
1185
1186 /* Check for sorting in a section list wildcard spec as well. */
1187 if (!no_reorder)
1188 {
1189 struct wildcard_list *l;
1190 for (l = w->section_list; l != NULL; l = l->next)
1191 {
1192 if (l->spec.sorted == TRUE)
1193 {
1194 no_reorder = TRUE;
1195 break;
1196 }
1197 }
1198 }
1199
1200 /* Special case until the NOREORDER linker directive is supported:
1201 *(.init) output sections and *(.fini) specs may NOT be reordered. */
1202
1203 /* Check for sorting in a section list wildcard spec as well. */
1204 if (!no_reorder)
1205 {
1206 struct wildcard_list *l;
1207 for (l = w->section_list; l != NULL; l = l->next)
1208 {
1209 if (l->spec.name
1210 && ((strcmp (".init", l->spec.name) == 0)
1211 || (strcmp (".fini", l->spec.name) == 0)))
1212 {
1213 no_reorder = TRUE;
1214 break;
1215 }
1216 }
1217 }
1218
1219 #if EXTRA_VALIDATION
1220 old_child_count = ld_count_children (statement);
1221 #endif
1222
1223 /* It is now officially a target. Build the graph of source
1224 section -> target section (kept as a list of edges). */
1225 deps = ld_build_required_section_dependence (statement);
1226
1227 /* If this wildcard does not reorder.... */
1228 if (!no_reorder && deps->count != 0)
1229 {
1230 /* First check for reverse dependences. Fix if possible. */
1231 xtensa_layout_wild (deps, w);
1232
1233 xtensa_move_dependencies_to_front (deps, w);
1234 #if EXTRA_VALIDATION
1235 new_child_count = ld_count_children (statement);
1236 ASSERT (new_child_count == old_child_count);
1237 #endif
1238
1239 xtensa_colocate_literals (deps, statement);
1240
1241 #if EXTRA_VALIDATION
1242 new_child_count = ld_count_children (statement);
1243 ASSERT (new_child_count == old_child_count);
1244 #endif
1245 }
1246
1247 /* Clean up. */
1248 free_reloc_deps_graph (deps);
1249 }
1250 }
1251
1252
1253 static void
1254 xtensa_wild_group_interleave (lang_statement_union_type *s)
1255 {
1256 lang_for_each_statement_worker (xtensa_wild_group_interleave_callback, s);
1257 }
1258
1259
1260 static void
1261 xtensa_layout_wild (const reloc_deps_graph *deps, lang_wild_statement_type *w)
1262 {
1263 /* If it does not fit initially, we need to do this step. Move all
1264 of the wild literal sections to a new list, then move each of
1265 them back in just before the first section they depend on. */
1266 lang_statement_union_type **s_p;
1267 #if EXTRA_VALIDATION
1268 size_t old_count, new_count;
1269 size_t ct1, ct2;
1270 #endif
1271
1272 lang_wild_statement_type literal_wild;
1273 literal_wild.header.next = NULL;
1274 literal_wild.header.type = lang_wild_statement_enum;
1275 literal_wild.filename = NULL;
1276 literal_wild.filenames_sorted = FALSE;
1277 literal_wild.section_list = NULL;
1278 literal_wild.keep_sections = FALSE;
1279 literal_wild.children.head = NULL;
1280 literal_wild.children.tail = &literal_wild.children.head;
1281
1282 #if EXTRA_VALIDATION
1283 old_count = ld_count_children ((lang_statement_union_type*) w);
1284 #endif
1285
1286 s_p = &w->children.head;
1287 while (*s_p != NULL)
1288 {
1289 lang_statement_union_type *l = *s_p;
1290 if (l->header.type == lang_input_section_enum)
1291 {
1292 if (section_is_target (deps, l)
1293 && ! section_is_source (deps, l))
1294 {
1295 /* Detach. */
1296 *s_p = l->header.next;
1297 if (*s_p == NULL)
1298 w->children.tail = s_p;
1299 l->header.next = NULL;
1300
1301 /* Append. */
1302 *literal_wild.children.tail = l;
1303 literal_wild.children.tail = &l->header.next;
1304 continue;
1305 }
1306 }
1307 s_p = &(*s_p)->header.next;
1308 }
1309
1310 #if EXTRA_VALIDATION
1311 ct1 = ld_count_children ((lang_statement_union_type*) w);
1312 ct2 = ld_count_children ((lang_statement_union_type*) &literal_wild);
1313
1314 ASSERT (old_count == (ct1 + ct2));
1315 #endif
1316
1317 /* Now place them back in front of their dependent sections. */
1318
1319 while (literal_wild.children.head != NULL)
1320 {
1321 lang_statement_union_type *lit = literal_wild.children.head;
1322 bfd_boolean placed = FALSE;
1323
1324 #if EXTRA_VALIDATION
1325 ASSERT (ct2 > 0);
1326 ct2--;
1327 #endif
1328
1329 /* Detach. */
1330 literal_wild.children.head = lit->header.next;
1331 if (literal_wild.children.head == NULL)
1332 literal_wild.children.tail = &literal_wild.children.head;
1333 lit->header.next = NULL;
1334
1335 /* Find a spot to place it. */
1336 for (s_p = &w->children.head; *s_p != NULL; s_p = &(*s_p)->header.next)
1337 {
1338 lang_statement_union_type *src = *s_p;
1339 if (deps_has_edge (deps, src, lit))
1340 {
1341 /* Place it here. */
1342 lit->header.next = *s_p;
1343 *s_p = lit;
1344 placed = TRUE;
1345 break;
1346 }
1347 }
1348
1349 if (!placed)
1350 {
1351 /* Put it at the end. */
1352 *w->children.tail = lit;
1353 w->children.tail = &lit->header.next;
1354 }
1355 }
1356
1357 #if EXTRA_VALIDATION
1358 new_count = ld_count_children ((lang_statement_union_type*) w);
1359 ASSERT (new_count == old_count);
1360 #endif
1361 }
1362
1363
1364 static void
1365 xtensa_colocate_output_literals_callback (lang_statement_union_type *statement)
1366 {
1367 lang_output_section_statement_type *os;
1368 reloc_deps_graph *deps;
1369 if (statement->header.type == lang_output_section_statement_enum)
1370 {
1371 /* Now, we walk over the contours of the output section statement.
1372
1373 First we build the literal section dependences as before.
1374
1375 At the first uniquely_literal section, we mark it as a good
1376 spot to place other literals. Continue walking (and counting
1377 sizes) until we find the next literal section. If this
1378 section can be moved to the first one, then we move it. If
1379 we every find a modification of ".", start over. If we find
1380 a labeling of the current location, start over. Finally, at
1381 the end, if we require page alignment, add page alignments. */
1382
1383 #if EXTRA_VALIDATION
1384 size_t old_child_count;
1385 size_t new_child_count;
1386 #endif
1387 bfd_boolean no_reorder = FALSE;
1388
1389 os = &statement->output_section_statement;
1390
1391 #if EXTRA_VALIDATION
1392 old_child_count = ld_count_children (statement);
1393 #endif
1394
1395 /* It is now officially a target. Build the graph of source
1396 section -> target section (kept as a list of edges). */
1397
1398 deps = ld_build_required_section_dependence (statement);
1399
1400 /* If this wildcard does not reorder.... */
1401 if (!no_reorder)
1402 {
1403 /* First check for reverse dependences. Fix if possible. */
1404 xtensa_colocate_literals (deps, statement);
1405
1406 #if EXTRA_VALIDATION
1407 new_child_count = ld_count_children (statement);
1408 ASSERT (new_child_count == old_child_count);
1409 #endif
1410 }
1411
1412 /* Insert align/offset assignment statement. */
1413 if (xtensa_use_literal_pages)
1414 {
1415 ld_xtensa_insert_page_offsets (0, statement, deps,
1416 xtensa_use_literal_pages);
1417 lang_for_each_statement_worker (xtensa_ldlang_clear_addresses,
1418 statement);
1419 }
1420
1421 /* Clean up. */
1422 free_reloc_deps_graph (deps);
1423 }
1424 }
1425
1426
1427 static void
1428 xtensa_colocate_output_literals (lang_statement_union_type *s)
1429 {
1430 lang_for_each_statement_worker (xtensa_colocate_output_literals_callback, s);
1431 }
1432
1433
1434 static void
1435 xtensa_ldlang_clear_addresses (lang_statement_union_type *statement)
1436 {
1437 switch (statement->header.type)
1438 {
1439 case lang_input_section_enum:
1440 {
1441 asection *bfd_section = statement->input_section.section;
1442 bfd_section->output_offset = 0;
1443 }
1444 break;
1445 default:
1446 break;
1447 }
1448 }
1449
1450
1451 static bfd_vma
1452 ld_assign_relative_paged_dot (bfd_vma dot,
1453 lang_statement_union_type *s,
1454 const reloc_deps_graph *deps ATTRIBUTE_UNUSED,
1455 bfd_boolean lit_align)
1456 {
1457 /* Walk through all of the input statements in this wild statement
1458 assign dot to all of them. */
1459
1460 xtensa_ld_iter_stack *stack = NULL;
1461 xtensa_ld_iter_stack **stack_p = &stack;
1462
1463 bfd_boolean first_section = FALSE;
1464 bfd_boolean in_literals = FALSE;
1465
1466 for (iter_stack_create (stack_p, s);
1467 !iter_stack_empty (stack_p);
1468 iter_stack_next (stack_p))
1469 {
1470 lang_statement_union_type *l = iter_stack_current (stack_p);
1471
1472 switch (l->header.type)
1473 {
1474 case lang_input_section_enum:
1475 {
1476 asection *section = l->input_section.section;
1477 size_t align_pow = section->alignment_power;
1478 bfd_boolean do_xtensa_alignment = FALSE;
1479
1480 if (lit_align)
1481 {
1482 bfd_boolean sec_is_target = section_is_target (deps, l);
1483 bfd_boolean sec_is_source = section_is_source (deps, l);
1484
1485 if (section->size != 0
1486 && (first_section
1487 || (in_literals && !sec_is_target)
1488 || (!in_literals && sec_is_target)))
1489 {
1490 do_xtensa_alignment = TRUE;
1491 }
1492 first_section = FALSE;
1493 if (section->size != 0)
1494 in_literals = (sec_is_target && !sec_is_source);
1495 }
1496
1497 if (do_xtensa_alignment && xtensa_page_power != 0)
1498 dot += (1 << xtensa_page_power);
1499
1500 dot = align_power (dot, align_pow);
1501 section->output_offset = dot;
1502 dot += section->size;
1503 }
1504 break;
1505 case lang_fill_statement_enum:
1506 dot += l->fill_statement.size;
1507 break;
1508 case lang_padding_statement_enum:
1509 dot += l->padding_statement.size;
1510 break;
1511 default:
1512 break;
1513 }
1514 }
1515 return dot;
1516 }
1517
1518
1519 static bfd_boolean
1520 ld_local_file_relocations_fit (lang_statement_union_type *statement,
1521 const reloc_deps_graph *deps ATTRIBUTE_UNUSED)
1522 {
1523 /* Walk over all of the dependencies that we identified and make
1524 sure that IF the source and target are here (addr != 0):
1525 1) target addr < source addr
1526 2) (roundup(source + source_size, 4) - rounddown(target, 4))
1527 < (256K - (1 << bad align))
1528 Need a worst-case proof.... */
1529
1530 xtensa_ld_iter_stack *stack = NULL;
1531 xtensa_ld_iter_stack **stack_p = &stack;
1532 size_t max_align_power = 0;
1533 size_t align_penalty = 256;
1534 reloc_deps_e *e;
1535 size_t i;
1536
1537 /* Find the worst-case alignment requirement for this set of statements. */
1538 for (iter_stack_create (stack_p, statement);
1539 !iter_stack_empty (stack_p);
1540 iter_stack_next (stack_p))
1541 {
1542 lang_statement_union_type *l = iter_stack_current (stack_p);
1543 if (l->header.type == lang_input_section_enum)
1544 {
1545 lang_input_section_type *input = &l->input_section;
1546 asection *section = input->section;
1547 if (section->alignment_power > max_align_power)
1548 max_align_power = section->alignment_power;
1549 }
1550 }
1551
1552 /* Now check that everything fits. */
1553 for (i = 0; i < deps->count; i++)
1554 {
1555 asection *sec = deps->sections[i];
1556 const reloc_deps_section *deps_section =
1557 xtensa_get_section_deps (deps, sec);
1558 if (deps_section)
1559 {
1560 /* We choose to walk through the successors. */
1561 for (e = deps_section->succs; e != NULL; e = e->next)
1562 {
1563 if (e->src != e->tgt
1564 && e->src->output_section == e->tgt->output_section
1565 && e->src->output_offset != 0
1566 && e->tgt->output_offset != 0)
1567 {
1568 bfd_vma l32r_addr =
1569 align_power (e->src->output_offset + e->src->size, 2);
1570 bfd_vma target_addr = e->tgt->output_offset & ~3;
1571 if (l32r_addr < target_addr)
1572 {
1573 fprintf (stderr, "Warning: "
1574 "l32r target section before l32r\n");
1575 return FALSE;
1576 }
1577
1578 if (l32r_addr - target_addr > 256 * 1024 - align_penalty)
1579 return FALSE;
1580 }
1581 }
1582 }
1583 }
1584
1585 return TRUE;
1586 }
1587
1588
1589 static bfd_vma
1590 ld_xtensa_insert_page_offsets (bfd_vma dot,
1591 lang_statement_union_type *s,
1592 reloc_deps_graph *deps,
1593 bfd_boolean lit_align)
1594 {
1595 xtensa_ld_iter_stack *stack = NULL;
1596 xtensa_ld_iter_stack **stack_p = &stack;
1597
1598 bfd_boolean first_section = FALSE;
1599 bfd_boolean in_literals = FALSE;
1600
1601 if (!lit_align)
1602 return FALSE;
1603
1604 for (iter_stack_create (stack_p, s);
1605 !iter_stack_empty (stack_p);
1606 iter_stack_next (stack_p))
1607 {
1608 lang_statement_union_type *l = iter_stack_current (stack_p);
1609
1610 switch (l->header.type)
1611 {
1612 case lang_input_section_enum:
1613 {
1614 asection *section = l->input_section.section;
1615 bfd_boolean do_xtensa_alignment = FALSE;
1616
1617 if (lit_align)
1618 {
1619 if (section->size != 0
1620 && (first_section
1621 || (in_literals && !section_is_target (deps, l))
1622 || (!in_literals && section_is_target (deps, l))))
1623 {
1624 do_xtensa_alignment = TRUE;
1625 }
1626 first_section = FALSE;
1627 if (section->size != 0)
1628 {
1629 in_literals = (section_is_target (deps, l)
1630 && !section_is_source (deps, l));
1631 }
1632 }
1633
1634 if (do_xtensa_alignment && xtensa_page_power != 0)
1635 {
1636 /* Create an expression that increments the current address,
1637 i.e., "dot", by (1 << xtensa_align_power). */
1638 etree_type *name_op = exp_nameop (NAME, ".");
1639 etree_type *addend_op = exp_intop (1 << xtensa_page_power);
1640 etree_type *add_op = exp_binop ('+', name_op, addend_op);
1641 etree_type *assign_op = exp_assop ('=', ".", add_op);
1642
1643 lang_assignment_statement_type *assign_stmt;
1644 lang_statement_union_type *assign_union;
1645 lang_statement_list_type tmplist;
1646 lang_statement_list_type *old_stat_ptr = stat_ptr;
1647
1648 /* There is hidden state in "lang_add_assignment". It
1649 appends the new assignment statement to the stat_ptr
1650 list. Thus, we swap it before and after the call. */
1651
1652 tmplist.head = NULL;
1653 tmplist.tail = &tmplist.head;
1654
1655 stat_ptr = &tmplist;
1656 /* Warning: side effect; statement appended to stat_ptr. */
1657 assign_stmt = lang_add_assignment (assign_op);
1658 assign_union = (lang_statement_union_type *) assign_stmt;
1659 stat_ptr = old_stat_ptr;
1660
1661 assign_union->header.next = l;
1662 *(*stack_p)->iterloc.loc = assign_union;
1663 iter_stack_next (stack_p);
1664 }
1665 }
1666 break;
1667 default:
1668 break;
1669 }
1670 }
1671 return dot;
1672 }
1673
1674 EOF
1675
1676 # Define some shell vars to insert bits of code into the standard ELF
1677 # parse_args and list_options functions.
1678 #
1679 PARSE_AND_LIST_PROLOGUE='
1680 #define OPTION_OPT_SIZEOPT (300)
1681 #define OPTION_NO_RELAX (OPTION_OPT_SIZEOPT + 1)
1682 #define OPTION_LITERAL_MOVEMENT (OPTION_NO_RELAX + 1)
1683 #define OPTION_NO_LITERAL_MOVEMENT (OPTION_LITERAL_MOVEMENT + 1)
1684 extern int elf32xtensa_size_opt;
1685 extern int elf32xtensa_no_literal_movement;
1686 '
1687
1688 PARSE_AND_LIST_LONGOPTS='
1689 { "size-opt", no_argument, NULL, OPTION_OPT_SIZEOPT},
1690 { "no-relax", no_argument, NULL, OPTION_NO_RELAX},
1691 { "literal-movement", no_argument, NULL, OPTION_LITERAL_MOVEMENT},
1692 { "no-literal-movement", no_argument, NULL, OPTION_NO_LITERAL_MOVEMENT},
1693 '
1694
1695 PARSE_AND_LIST_OPTIONS='
1696 fprintf (file, _(" --size-opt\t\tWhen relaxing longcalls, prefer size optimization\n\t\t\t over branch target alignment\n"));
1697 fprintf (file, _(" --no-relax\t\tDo not relax branches or coalesce literals\n"));
1698 '
1699
1700 PARSE_AND_LIST_ARGS_CASES='
1701 case OPTION_OPT_SIZEOPT:
1702 elf32xtensa_size_opt = 1;
1703 break;
1704 case OPTION_NO_RELAX:
1705 disable_relaxation = TRUE;
1706 break;
1707 case OPTION_LITERAL_MOVEMENT:
1708 elf32xtensa_no_literal_movement = 0;
1709 break;
1710 case OPTION_NO_LITERAL_MOVEMENT:
1711 elf32xtensa_no_literal_movement = 1;
1712 break;
1713 '
1714
1715 # Replace some of the standard ELF functions with our own versions.
1716 #
1717 LDEMUL_BEFORE_PARSE=elf_xtensa_before_parse
1718 LDEMUL_AFTER_OPEN=elf_xtensa_after_open
1719 LDEMUL_CHOOSE_TARGET=elf_xtensa_choose_target
1720 LDEMUL_BEFORE_ALLOCATION=elf_xtensa_before_allocation
1721
This page took 0.065436 seconds and 4 git commands to generate.