* emultempl/aix.em: Add missing prototype.
[binutils-gdb.git] / ld / emultempl / beos.em
1 # This shell script emits a C file. -*- C -*-
2 # It does some substitutions.
3 if [ -z "$MACHINE" ]; then
4 OUTPUT_ARCH=${ARCH}
5 else
6 OUTPUT_ARCH=${ARCH}:${MACHINE}
7 fi
8 cat >e${EMULATION_NAME}.c <<EOF
9 /* This file is part of GLD, the Gnu Linker.
10 Copyright 1995, 1996, 1997, 1998, 2000, 2001
11 Free Software Foundation, Inc.
12
13 This program is free software; you can redistribute it and/or modify
14 it under the terms of the GNU General Public License as published by
15 the Free Software Foundation; either version 2 of the License, or
16 (at your option) any later version.
17
18 This program is distributed in the hope that it will be useful,
19 but WITHOUT ANY WARRANTY; without even the implied warranty of
20 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 GNU General Public License for more details.
22
23 You should have received a copy of the GNU General Public License
24 along with this program; if not, write to the Free Software
25 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
26
27 /* For WINDOWS_NT */
28 /* The original file generated returned different default scripts depending
29 on whether certain switches were set, but these switches pertain to the
30 Linux system and that particular version of coff. In the NT case, we
31 only determine if the subsystem is console or windows in order to select
32 the correct entry point by default. */
33
34 #include "bfd.h"
35 #include "sysdep.h"
36 #include "bfdlink.h"
37 #include "getopt.h"
38 #include "libiberty.h"
39 #include "ld.h"
40 #include "ldmain.h"
41 #include "ldgram.h"
42 #include "ldexp.h"
43 #include "ldlang.h"
44 #include "ldfile.h"
45 #include "ldemul.h"
46 #include "ldlex.h"
47 #include "ldmisc.h"
48 #include "ldctor.h"
49 #include "coff/internal.h"
50 #include "../bfd/libcoff.h"
51
52 #define TARGET_IS_${EMULATION_NAME}
53
54 static void gld_${EMULATION_NAME}_set_symbols PARAMS ((void));
55 static void gld_${EMULATION_NAME}_after_open PARAMS ((void));
56 static void gld_${EMULATION_NAME}_before_parse PARAMS ((void));
57 static void gld_${EMULATION_NAME}_before_allocation PARAMS ((void));
58 static boolean gld${EMULATION_NAME}_place_orphan
59 PARAMS ((lang_input_statement_type *, asection *));
60 static char *gld_${EMULATION_NAME}_get_script PARAMS ((int *));
61 static int gld_${EMULATION_NAME}_parse_args PARAMS ((int, char **));
62
63 #if 0 /* argument to qsort so don't prototype */
64 static int sort_by_file_name PARAMS ((void *, void *));
65 static int sort_by_section_name PARAMS ((void *, void *));
66 #endif
67 static lang_statement_union_type **sort_sections_1
68 PARAMS ((lang_statement_union_type **, lang_statement_union_type *, int,
69 int (*)()));
70 static void sort_sections PARAMS ((lang_statement_union_type *));
71
72 static void set_pe_name PARAMS ((char *, long int));
73 static void set_pe_subsystem PARAMS ((void));
74 static void set_pe_value PARAMS ((char *));
75 static void set_pe_stack_heap PARAMS ((char *, char *));
76
77 static struct internal_extra_pe_aouthdr pe;
78 static int dll;
79
80 extern const char *output_filename;
81
82 static void
83 gld_${EMULATION_NAME}_before_parse()
84 {
85 const bfd_arch_info_type *arch = bfd_scan_arch ("${OUTPUT_ARCH}");
86 if (arch)
87 {
88 ldfile_output_architecture = arch->arch;
89 ldfile_output_machine = arch->mach;
90 ldfile_output_machine_name = arch->printable_name;
91 }
92 else
93 ldfile_output_architecture = bfd_arch_${ARCH};
94 output_filename = "a.exe";
95 }
96 \f
97 /* PE format extra command line options. */
98
99 /* Used for setting flags in the PE header. */
100 #define OPTION_BASE_FILE (300 + 1)
101 #define OPTION_DLL (OPTION_BASE_FILE + 1)
102 #define OPTION_FILE_ALIGNMENT (OPTION_DLL + 1)
103 #define OPTION_IMAGE_BASE (OPTION_FILE_ALIGNMENT + 1)
104 #define OPTION_MAJOR_IMAGE_VERSION (OPTION_IMAGE_BASE + 1)
105 #define OPTION_MAJOR_OS_VERSION (OPTION_MAJOR_IMAGE_VERSION + 1)
106 #define OPTION_MAJOR_SUBSYSTEM_VERSION (OPTION_MAJOR_OS_VERSION + 1)
107 #define OPTION_MINOR_IMAGE_VERSION (OPTION_MAJOR_SUBSYSTEM_VERSION + 1)
108 #define OPTION_MINOR_OS_VERSION (OPTION_MINOR_IMAGE_VERSION + 1)
109 #define OPTION_MINOR_SUBSYSTEM_VERSION (OPTION_MINOR_OS_VERSION + 1)
110 #define OPTION_SECTION_ALIGNMENT (OPTION_MINOR_SUBSYSTEM_VERSION + 1)
111 #define OPTION_STACK (OPTION_SECTION_ALIGNMENT + 1)
112 #define OPTION_SUBSYSTEM (OPTION_STACK + 1)
113 #define OPTION_HEAP (OPTION_SUBSYSTEM + 1)
114
115 static struct option longopts[] = {
116 /* PE options */
117 {"base-file", required_argument, NULL, OPTION_BASE_FILE},
118 {"dll", no_argument, NULL, OPTION_DLL},
119 {"file-alignment", required_argument, NULL, OPTION_FILE_ALIGNMENT},
120 {"heap", required_argument, NULL, OPTION_HEAP},
121 {"image-base", required_argument, NULL, OPTION_IMAGE_BASE},
122 {"major-image-version", required_argument, NULL, OPTION_MAJOR_IMAGE_VERSION},
123 {"major-os-version", required_argument, NULL, OPTION_MAJOR_OS_VERSION},
124 {"major-subsystem-version", required_argument, NULL, OPTION_MAJOR_SUBSYSTEM_VERSION},
125 {"minor-image-version", required_argument, NULL, OPTION_MINOR_IMAGE_VERSION},
126 {"minor-os-version", required_argument, NULL, OPTION_MINOR_OS_VERSION},
127 {"minor-subsystem-version", required_argument, NULL, OPTION_MINOR_SUBSYSTEM_VERSION},
128 {"section-alignment", required_argument, NULL, OPTION_SECTION_ALIGNMENT},
129 {"stack", required_argument, NULL, OPTION_STACK},
130 {"subsystem", required_argument, NULL, OPTION_SUBSYSTEM},
131 {NULL, no_argument, NULL, 0}
132 };
133
134
135 /* PE/WIN32; added routines to get the subsystem type, heap and/or stack
136 parameters which may be input from the command line */
137
138 typedef struct {
139 void *ptr;
140 int size;
141 int value;
142 char *symbol;
143 int inited;
144 } definfo;
145
146 #define D(field,symbol,def) {&pe.field,sizeof(pe.field), def, symbol,0}
147
148 static definfo init[] =
149 {
150 /* imagebase must be first */
151 #define IMAGEBASEOFF 0
152 D(ImageBase,"__image_base__", BEOS_EXE_IMAGE_BASE),
153 #define DLLOFF 1
154 {&dll, sizeof(dll), 0, "__dll__", 0},
155 D(SectionAlignment,"__section_alignment__", PE_DEF_SECTION_ALIGNMENT),
156 D(FileAlignment,"__file_alignment__", PE_DEF_FILE_ALIGNMENT),
157 D(MajorOperatingSystemVersion,"__major_os_version__", 4),
158 D(MinorOperatingSystemVersion,"__minor_os_version__", 0),
159 D(MajorImageVersion,"__major_image_version__", 1),
160 D(MinorImageVersion,"__minor_image_version__", 0),
161 D(MajorSubsystemVersion,"__major_subsystem_version__", 4),
162 D(MinorSubsystemVersion,"__minor_subsystem_version__", 0),
163 D(Subsystem,"__subsystem__", 3),
164 D(SizeOfStackReserve,"__size_of_stack_reserve__", 0x2000000),
165 D(SizeOfStackCommit,"__size_of_stack_commit__", 0x1000),
166 D(SizeOfHeapReserve,"__size_of_heap_reserve__", 0x100000),
167 D(SizeOfHeapCommit,"__size_of_heap_commit__", 0x1000),
168 D(LoaderFlags,"__loader_flags__", 0x0),
169 { NULL, 0, 0, NULL, 0 }
170 };
171
172
173 static void
174 set_pe_name (name, val)
175 char *name;
176 long val;
177 {
178 int i;
179 /* Find the name and set it. */
180 for (i = 0; init[i].ptr; i++)
181 {
182 if (strcmp (name, init[i].symbol) == 0)
183 {
184 init[i].value = val;
185 init[i].inited = 1;
186 return;
187 }
188 }
189 abort();
190 }
191
192
193 static void
194 set_pe_subsystem ()
195 {
196 const char *sver;
197 int len;
198 int i;
199 static const struct
200 {
201 const char *name;
202 const int value;
203 const char *entry;
204 }
205 v[] =
206 {
207 { "native", 1, "_NtProcessStartup" },
208 { "windows", 2, "_WinMainCRTStartup" },
209 { "wwindows", 2, "_wWinMainCRTStartup" },
210 { "console", 3, "_mainCRTStartup" },
211 { "wconsole", 3, "_wmainCRTStartup" },
212 #if 0
213 /* The Microsoft linker does not recognize this. */
214 { "os2", 5, "" },
215 #endif
216 { "posix", 7, "___PosixProcessStartup"},
217 { 0, 0, 0 }
218 };
219
220 sver = strchr (optarg, ':');
221 if (sver == NULL)
222 len = strlen (optarg);
223 else
224 {
225 char *end;
226
227 len = sver - optarg;
228 set_pe_name ("__major_subsystem_version__",
229 strtoul (sver + 1, &end, 0));
230 if (*end == '.')
231 set_pe_name ("__minor_subsystem_version__",
232 strtoul (end + 1, &end, 0));
233 if (*end != '\0')
234 einfo ("%P: warning: bad version number in -subsystem option\n");
235 }
236
237 for (i = 0; v[i].name; i++)
238 {
239 if (strncmp (optarg, v[i].name, len) == 0
240 && v[i].name[len] == '\0')
241 {
242 set_pe_name ("__subsystem__", v[i].value);
243
244 /* If the subsystem is windows, we use a different entry
245 point. We also register the entry point as an undefined
246 symbol. from lang_add_entry() The reason we do
247 this is so that the user
248 doesn't have to because they would have to use the -u
249 switch if they were specifying an entry point other than
250 _mainCRTStartup. Specifically, if creating a windows
251 application, entry point _WinMainCRTStartup must be
252 specified. What I have found for non console
253 applications (entry not _mainCRTStartup) is that the .obj
254 that contains mainCRTStartup is brought in since it is
255 the first encountered in libc.lib and it has other
256 symbols in it which will be pulled in by the link
257 process. To avoid this, adding -u with the entry point
258 name specified forces the correct .obj to be used. We
259 can avoid making the user do this by always adding the
260 entry point name as an undefined symbol. */
261 lang_add_entry (v[i].entry, 1);
262
263 return;
264 }
265 }
266 einfo ("%P%F: invalid subsystem type %s\n", optarg);
267 }
268
269
270
271 static void
272 set_pe_value (name)
273 char *name;
274
275 {
276 char *end;
277 set_pe_name (name, strtoul (optarg, &end, 0));
278 if (end == optarg)
279 {
280 einfo ("%P%F: invalid hex number for PE parameter '%s'\n", optarg);
281 }
282
283 optarg = end;
284 }
285
286 static void
287 set_pe_stack_heap (resname, comname)
288 char *resname;
289 char *comname;
290 {
291 set_pe_value (resname);
292 if (*optarg == ',')
293 {
294 optarg++;
295 set_pe_value (comname);
296 }
297 else if (*optarg)
298 {
299 einfo ("%P%F: strange hex info for PE parameter '%s'\n", optarg);
300 }
301 }
302
303
304
305 static int
306 gld_${EMULATION_NAME}_parse_args(argc, argv)
307 int argc;
308 char **argv;
309 {
310 int longind;
311 int optc;
312 int prevoptind = optind;
313 int prevopterr = opterr;
314 int wanterror;
315 static int lastoptind = -1;
316
317 if (lastoptind != optind)
318 opterr = 0;
319 wanterror = opterr;
320
321 lastoptind = optind;
322
323 optc = getopt_long_only (argc, argv, "-", longopts, &longind);
324 opterr = prevopterr;
325
326 switch (optc)
327 {
328 default:
329 if (wanterror)
330 xexit (1);
331 optind = prevoptind;
332 return 0;
333
334 case OPTION_BASE_FILE:
335 link_info.base_file = (PTR) fopen (optarg, FOPEN_WB);
336 if (link_info.base_file == NULL)
337 {
338 fprintf (stderr, "%s: Can't open base file %s\n",
339 program_name, optarg);
340 xexit (1);
341 }
342 break;
343
344 /* PE options */
345 case OPTION_HEAP:
346 set_pe_stack_heap ("__size_of_heap_reserve__", "__size_of_heap_commit__");
347 break;
348 case OPTION_STACK:
349 set_pe_stack_heap ("__size_of_stack_reserve__", "__size_of_stack_commit__");
350 break;
351 case OPTION_SUBSYSTEM:
352 set_pe_subsystem ();
353 break;
354 case OPTION_MAJOR_OS_VERSION:
355 set_pe_value ("__major_os_version__");
356 break;
357 case OPTION_MINOR_OS_VERSION:
358 set_pe_value ("__minor_os_version__");
359 break;
360 case OPTION_MAJOR_SUBSYSTEM_VERSION:
361 set_pe_value ("__major_subsystem_version__");
362 break;
363 case OPTION_MINOR_SUBSYSTEM_VERSION:
364 set_pe_value ("__minor_subsystem_version__");
365 break;
366 case OPTION_MAJOR_IMAGE_VERSION:
367 set_pe_value ("__major_image_version__");
368 break;
369 case OPTION_MINOR_IMAGE_VERSION:
370 set_pe_value ("__minor_image_version__");
371 break;
372 case OPTION_FILE_ALIGNMENT:
373 set_pe_value ("__file_alignment__");
374 break;
375 case OPTION_SECTION_ALIGNMENT:
376 set_pe_value ("__section_alignment__");
377 break;
378 case OPTION_DLL:
379 set_pe_name ("__dll__", 1);
380 break;
381 case OPTION_IMAGE_BASE:
382 set_pe_value ("__image_base__");
383 break;
384 }
385 return 1;
386 }
387 \f
388 /* Assign values to the special symbols before the linker script is
389 read. */
390
391 static void
392 gld_${EMULATION_NAME}_set_symbols()
393 {
394 /* Run through and invent symbols for all the
395 names and insert the defaults. */
396 int j;
397 lang_statement_list_type *save;
398
399 if (!init[IMAGEBASEOFF].inited)
400 {
401 if (link_info.relocateable)
402 init[IMAGEBASEOFF].value = 0;
403 else if (init[DLLOFF].value)
404 init[IMAGEBASEOFF].value = BEOS_DLL_IMAGE_BASE;
405 else
406 init[IMAGEBASEOFF].value = BEOS_EXE_IMAGE_BASE;
407 }
408
409 /* Don't do any symbol assignments if this is a relocateable link. */
410 if (link_info.relocateable)
411 return;
412
413 /* Glue the assignments into the abs section */
414 save = stat_ptr;
415
416 stat_ptr = &(abs_output_section->children);
417
418 for (j = 0; init[j].ptr; j++)
419 {
420 long val = init[j].value;
421 lang_add_assignment (exp_assop ('=' ,init[j].symbol, exp_intop (val)));
422 if (init[j].size == sizeof(short))
423 *(short *)init[j].ptr = val;
424 else if (init[j].size == sizeof(int))
425 *(int *)init[j].ptr = val;
426 else if (init[j].size == sizeof(long))
427 *(long *)init[j].ptr = val;
428 /* This might be a long long or other special type. */
429 else if (init[j].size == sizeof(bfd_vma))
430 *(bfd_vma *)init[j].ptr = val;
431 else abort();
432 }
433 /* Restore the pointer. */
434 stat_ptr = save;
435
436 if (pe.FileAlignment >
437 pe.SectionAlignment)
438 {
439 einfo ("%P: warning, file alignment > section alignment.\n");
440 }
441 }
442
443 static void
444 gld_${EMULATION_NAME}_after_open()
445 {
446 /* Pass the wacky PE command line options into the output bfd.
447 FIXME: This should be done via a function, rather than by
448 including an internal BFD header. */
449 if (!coff_data(output_bfd)->pe)
450 {
451 einfo ("%F%P: PE operations on non PE file.\n");
452 }
453
454 pe_data(output_bfd)->pe_opthdr = pe;
455 pe_data(output_bfd)->dll = init[DLLOFF].value;
456
457 }
458 \f
459 /* Callback functions for qsort in sort_sections. */
460
461 static int
462 sort_by_file_name (a, b)
463 void *a;
464 void *b;
465 {
466 lang_statement_union_type **ra = a;
467 lang_statement_union_type **rb = b;
468 int i, a_sec, b_sec;
469
470 i = strcmp ((*ra)->input_section.ifile->the_bfd->my_archive->filename,
471 (*rb)->input_section.ifile->the_bfd->my_archive->filename);
472 if (i != 0)
473 return i;
474
475 i = strcmp ((*ra)->input_section.ifile->filename,
476 (*rb)->input_section.ifile->filename);
477 if (i != 0)
478 return i;
479 /* the tail idata4/5 are the only ones without relocs to an
480 idata$6 section unless we are importing by ordinal,
481 so sort them to last to terminate the IAT
482 and HNT properly. if no reloc this one is import by ordinal
483 so we have to sort by section contents */
484
485 if ( ((*ra)->input_section.section->reloc_count + (*rb)->input_section.section->reloc_count) )
486 {
487 i = (((*ra)->input_section.section->reloc_count >
488 (*rb)->input_section.section->reloc_count) ? -1 : 0);
489 if ( i != 0)
490 return i;
491
492 return (((*ra)->input_section.section->reloc_count >
493 (*rb)->input_section.section->reloc_count) ? 0 : 1);
494 }
495 else
496 {
497 if ( (strcmp( (*ra)->input_section.section->name, ".idata$6") == 0) )
498 return 0; /* don't sort .idata$6 or .idata$7 FIXME dlltool eliminate .idata$7 */
499
500 if (! bfd_get_section_contents ((*ra)->input_section.ifile->the_bfd,
501 (*ra)->input_section.section, &a_sec, (file_ptr) 0, (bfd_size_type)sizeof(a_sec)))
502 einfo ("%F%B: Can't read contents of section .idata: %E\n",
503 (*ra)->input_section.ifile->the_bfd);
504
505 if (! bfd_get_section_contents ((*rb)->input_section.ifile->the_bfd,
506 (*rb)->input_section.section, &b_sec, (file_ptr) 0, (bfd_size_type)sizeof(b_sec) ))
507 einfo ("%F%B: Can't read contents of section .idata: %E\n",
508 (*rb)->input_section.ifile->the_bfd);
509
510 i = ((a_sec < b_sec) ? -1 : 0);
511 if ( i != 0)
512 return i;
513 return ((a_sec < b_sec) ? 0 : 1);
514 }
515 return 0;
516 }
517
518 static int
519 sort_by_section_name (a, b)
520 void *a;
521 void *b;
522 {
523 lang_statement_union_type **ra = a;
524 lang_statement_union_type **rb = b;
525 int i;
526 i = strcmp ((*ra)->input_section.section->name,
527 (*rb)->input_section.section->name);
528 /* this is a hack to make .stab and .stabstr last, so we don't have
529 to fix strip/objcopy for .reloc sections.
530 FIXME stripping images with a .rsrc section still needs to be fixed */
531 if ( i != 0)
532 {
533 if ((strncmp ((*ra)->input_section.section->name, ".stab", 5) == 0)
534 && (strncmp ((*rb)->input_section.section->name, ".stab", 5) != 0))
535 return 1;
536 return i;
537 }
538 return i;
539 }
540
541 /* Subroutine of sort_sections to a contiguous subset of a list of sections.
542 NEXT_AFTER is the element after the last one to sort.
543 The result is a pointer to the last element's "next" pointer. */
544
545 static lang_statement_union_type **
546 sort_sections_1 (startptr, next_after, count, sort_func)
547 lang_statement_union_type **startptr,*next_after;
548 int count;
549 int (*sort_func) ();
550 {
551 lang_statement_union_type **vec;
552 lang_statement_union_type *p;
553 int i;
554 lang_statement_union_type **ret;
555
556 if (count == 0)
557 return startptr;
558
559 vec = ((lang_statement_union_type **)
560 xmalloc (count * sizeof (lang_statement_union_type *)));
561
562 for (p = *startptr, i = 0; i < count; i++, p = p->header.next)
563 vec[i] = p;
564
565 qsort (vec, count, sizeof (vec[0]), sort_func);
566
567 /* Fill in the next pointers again. */
568 *startptr = vec[0];
569 for (i = 0; i < count - 1; i++)
570 vec[i]->header.next = vec[i + 1];
571 vec[i]->header.next = next_after;
572 ret = &vec[i]->header.next;
573 free (vec);
574 return ret;
575 }
576
577 /* Sort the .idata\$foo input sections of archives into filename order.
578 The reason is so dlltool can arrange to have the pe dll import information
579 generated correctly - the head of the list goes into dh.o, the tail into
580 dt.o, and the guts into ds[nnnn].o. Note that this is only needed for the
581 .idata section.
582 FIXME: This may no longer be necessary with grouped sections. Instead of
583 sorting on dh.o, ds[nnnn].o, dt.o, one could, for example, have dh.o use
584 .idata\$4h, have ds[nnnn].o use .idata\$4s[nnnn], and have dt.o use .idata\$4t.
585 This would have to be elaborated upon to handle multiple dll's
586 [assuming such an eloboration is possible of course].
587
588 We also sort sections in '\$' wild statements. These are created by the
589 place_orphans routine to implement grouped sections. */
590
591 static void
592 sort_sections (s)
593 lang_statement_union_type *s;
594 {
595 for (; s ; s = s->header.next)
596 switch (s->header.type)
597 {
598 case lang_output_section_statement_enum:
599 sort_sections (s->output_section_statement.children.head);
600 break;
601 case lang_wild_statement_enum:
602 {
603 lang_statement_union_type **p = &s->wild_statement.children.head;
604 struct wildcard_list *sec;
605
606 for (sec = s->wild_statement.section_list; sec; sec = sec->next)
607 {
608 /* Is this the .idata section? */
609 if (sec->spec.name != NULL
610 && strncmp (sec->spec.name, ".idata", 6) == 0)
611 {
612 /* Sort the children. We want to sort any objects in
613 the same archive. In order to handle the case of
614 including a single archive multiple times, we sort
615 all the children by archive name and then by object
616 name. After sorting them, we re-thread the pointer
617 chain. */
618
619 while (*p)
620 {
621 lang_statement_union_type *start = *p;
622 if (start->header.type != lang_input_section_enum
623 || !start->input_section.ifile->the_bfd->my_archive)
624 p = &(start->header.next);
625 else
626 {
627 lang_statement_union_type *end;
628 int count;
629
630 for (end = start, count = 0;
631 end && (end->header.type
632 == lang_input_section_enum);
633 end = end->header.next)
634 count++;
635
636 p = sort_sections_1 (p, end, count,
637 sort_by_file_name);
638 }
639 }
640 break;
641 }
642
643 /* If this is a collection of grouped sections, sort them.
644 The linker script must explicitly mention "*(.foo\$)" or
645 "*(.foo\$*)". Don't sort them if \$ is not the last
646 character (not sure if this is really useful, but it
647 allows explicitly mentioning some \$ sections and letting
648 the linker handle the rest). */
649 if (sec->spec.name != NULL)
650 {
651 char *q = strchr (sec->spec.name, '\$');
652
653 if (q != NULL
654 && (q[1] == '\0'
655 || (q[1] == '*' && q[2] == '\0')))
656 {
657 lang_statement_union_type *end;
658 int count;
659
660 for (end = *p, count = 0; end; end = end->header.next)
661 {
662 if (end->header.type != lang_input_section_enum)
663 abort ();
664 count++;
665 }
666 (void) sort_sections_1 (p, end, count,
667 sort_by_section_name);
668 }
669 break;
670 }
671 }
672 }
673 break;
674 default:
675 break;
676 }
677 }
678
679 static void
680 gld_${EMULATION_NAME}_before_allocation()
681 {
682 extern lang_statement_list_type *stat_ptr;
683
684 #ifdef TARGET_IS_ppcpe
685 /* Here we rummage through the found bfds to collect toc information */
686 {
687 LANG_FOR_EACH_INPUT_STATEMENT (is)
688 {
689 if (!ppc_process_before_allocation(is->the_bfd, &link_info))
690 {
691 einfo("Errors encountered processing file %s\n", is->filename);
692 }
693 }
694 }
695
696 /* We have seen it all. Allocate it, and carry on */
697 ppc_allocate_toc_section (&link_info);
698 #else
699 #ifdef TARGET_IS_armpe
700 /* FIXME: we should be able to set the size of the interworking stub
701 section.
702
703 Here we rummage through the found bfds to collect glue
704 information. FIXME: should this be based on a command line
705 option? krk@cygnus.com */
706 {
707 LANG_FOR_EACH_INPUT_STATEMENT (is)
708 {
709 if (!arm_process_before_allocation (is->the_bfd, & link_info))
710 {
711 einfo ("Errors encountered processing file %s", is->filename);
712 }
713 }
714 }
715
716 /* We have seen it all. Allocate it, and carry on */
717 arm_allocate_interworking_sections (& link_info);
718 #endif /* TARGET_IS_armpe */
719 #endif /* TARGET_IS_ppcpe */
720
721 sort_sections (stat_ptr->head);
722 }
723 \f
724 /* Place an orphan section. We use this to put sections with a '\$' in them
725 into the right place. Any section with a '\$' in them (e.g. .text\$foo)
726 gets mapped to the output section with everything from the '\$' on stripped
727 (e.g. .text).
728 See the Microsoft Portable Executable and Common Object File Format
729 Specification 4.1, section 4.2, Grouped Sections.
730
731 FIXME: This is now handled by the linker script using wildcards,
732 but I'm leaving this here in case we want to enable it for sections
733 which are not mentioned in the linker script. */
734
735 /*ARGSUSED*/
736 static boolean
737 gld${EMULATION_NAME}_place_orphan (file, s)
738 lang_input_statement_type *file;
739 asection *s;
740 {
741 const char *secname;
742 char *output_secname, *ps;
743 lang_output_section_statement_type *os;
744 lang_statement_union_type *l;
745
746 if ((s->flags & SEC_ALLOC) == 0)
747 return false;
748
749 /* Don't process grouped sections unless doing a final link.
750 If they're marked as COMDAT sections, we don't want .text\$foo to
751 end up in .text and then have .text disappear because it's marked
752 link-once-discard. */
753 if (link_info.relocateable)
754 return false;
755
756 secname = bfd_get_section_name (s->owner, s);
757
758 /* Everything from the '\$' on gets deleted so don't allow '\$' as the
759 first character. */
760 if (*secname == '\$')
761 einfo ("%P%F: section %s has '\$' as first character\n", secname);
762 if (strchr (secname + 1, '\$') == NULL)
763 return false;
764
765 /* Look up the output section. The Microsoft specs say sections names in
766 image files never contain a '\$'. Fortunately, lang_..._lookup creates
767 the section if it doesn't exist. */
768 output_secname = xstrdup (secname);
769 ps = strchr (output_secname + 1, '\$');
770 *ps = 0;
771 os = lang_output_section_statement_lookup (output_secname);
772
773 /* Find the '\$' wild statement for this section. We currently require the
774 linker script to explicitly mention "*(.foo\$)".
775 FIXME: ppcpe.sc has .CRT\$foo in the .rdata section. According to the
776 Microsoft docs this isn't correct so it's not (currently) handled. */
777
778 ps[0] = '\$';
779 ps[1] = 0;
780 for (l = os->children.head; l; l = l->header.next)
781 if (l->header.type == lang_wild_statement_enum)
782 {
783 struct wildcard_list *sec;
784
785 for (sec = l->wild_statement.section_list; sec; sec = sec->next)
786 if (sec->spec.name && strcmp (sec->spec.name, output_secname) == 0)
787 break;
788 if (sec)
789 break;
790 }
791 ps[0] = 0;
792 if (l == NULL)
793 #if 1
794 einfo ("%P%F: *(%s\$) missing from linker script\n", output_secname);
795 #else /* FIXME: This block is untried. It exists to convey the intent,
796 should one decide to not require *(.foo\$) to appear in the linker
797 script. */
798 {
799 lang_wild_statement_type *new;
800 struct wildcard_list *tmp;
801
802 tmp = (struct wildcard_list *) xmalloc (sizeof *tmp);
803 tmp->next = NULL;
804 tmp->spec.name = xmalloc (strlen (output_secname) + 2);
805 sprintf (tmp->spec.name, "%s\$", output_secname);
806 tmp->spec.exclude_name_list = NULL;
807 tmp->sorted = false;
808 new = new_stat (lang_wild_statement, &os->children);
809 new->filename = NULL;
810 new->filenames_sorted = false;
811 new->section_list = tmp;
812 new->keep_sections = false;
813 lang_list_init (&new->children);
814 l = new;
815 }
816 #endif
817
818 /* Link the input section in and we're done for now.
819 The sections still have to be sorted, but that has to wait until
820 all such sections have been processed by us. The sorting is done by
821 sort_sections. */
822 lang_add_section (&l->wild_statement.children, s, os, file);
823
824 return true;
825 }
826 \f
827 static char *
828 gld_${EMULATION_NAME}_get_script(isfile)
829 int *isfile;
830 EOF
831 # Scripts compiled in.
832 # sed commands to quote an ld script as a C string.
833 sc="-f stringify.sed"
834
835 cat >>e${EMULATION_NAME}.c <<EOF
836 {
837 *isfile = 0;
838
839 if (link_info.relocateable == true && config.build_constructors == true)
840 return
841 EOF
842 sed $sc ldscripts/${EMULATION_NAME}.xu >> e${EMULATION_NAME}.c
843 echo ' ; else if (link_info.relocateable == true) return' >> e${EMULATION_NAME}.c
844 sed $sc ldscripts/${EMULATION_NAME}.xr >> e${EMULATION_NAME}.c
845 echo ' ; else if (!config.text_read_only) return' >> e${EMULATION_NAME}.c
846 sed $sc ldscripts/${EMULATION_NAME}.xbn >> e${EMULATION_NAME}.c
847 echo ' ; else if (!config.magic_demand_paged) return' >> e${EMULATION_NAME}.c
848 sed $sc ldscripts/${EMULATION_NAME}.xn >> e${EMULATION_NAME}.c
849 echo ' ; else return' >> e${EMULATION_NAME}.c
850 sed $sc ldscripts/${EMULATION_NAME}.x >> e${EMULATION_NAME}.c
851 echo '; }' >> e${EMULATION_NAME}.c
852
853 cat >>e${EMULATION_NAME}.c <<EOF
854
855
856 struct ld_emulation_xfer_struct ld_${EMULATION_NAME}_emulation =
857 {
858 gld_${EMULATION_NAME}_before_parse,
859 syslib_default,
860 hll_default,
861 after_parse_default,
862 gld_${EMULATION_NAME}_after_open,
863 after_allocation_default,
864 set_output_arch_default,
865 ldemul_default_target,
866 gld_${EMULATION_NAME}_before_allocation,
867 gld_${EMULATION_NAME}_get_script,
868 "${EMULATION_NAME}",
869 "${OUTPUT_FORMAT}",
870 NULL, /* finish */
871 NULL, /* create output section statements */
872 NULL, /* open dynamic archive */
873 gld${EMULATION_NAME}_place_orphan,
874 gld_${EMULATION_NAME}_set_symbols,
875 gld_${EMULATION_NAME}_parse_args,
876 NULL, /* unrecognized file */
877 NULL, /* list options */
878 NULL, /* recognized file */
879 NULL /* find_potential_libraries */
880 };
881 EOF